[seasar-dotnet:906] Re: [S2Container.NET] ASP.NET での Web フォームに対する DI

[E-MAIL ADDRESS DELETED] [E-MAIL ADDRESS DELETED]
2008年 7月 31日 (木) 17:01:29 JST


ももたろです。
久保さん、回答ありがとうございました。

> PageクラスからFacadeと呼ぶsingletonなビジネスロジッククラス
> を呼び出していましたが、PageクラスからContainerの
> GetComponentでFacadeを取得していました。
これは、Pageクラス以外のクラスとでコンポーネントの使い方が
変わってしまうので開発者が混乱しそう、ということで最後の案に
とっておきます。

> 今だったら、QuillでPageクラスにInjectionすると思います。
MasterPageを使っているので、そこから共通的にInjectionできそう、
ということでやってみました。

Protected Sub Page_Init _
    (ByVal sender As Object, ByVal e As System.EventArgs) _
    Handles Me.Init
  QuillInjector.GetInstance().Inject(Me.ContentPlaceHolder1.Page)
End Sub

上記のような感じで、無事にsingletonなビジネスロジッククラスを
DIすることができたのですが、Quill自身の制限が今回の要件には
マッチしなさそうなので、今回は泣く泣くあきらめました。。。


で、いろいろ試行錯誤してみたのですが、以下のようにすることで(3)以外
については一応の解決を見たのでご報告です。
S2HttpModule相当のクラスを自分でつくり、ASPXのコンポーネントがS2Container
に無ければ追加する、というようにしてみました。
ついでに、コンポーネント名の大文字/小文字を区別しなくて済むように
ToLowerしています。

Private Sub context_AcquireRequestState _
    (ByVal sender As Object, ByVal e As EventArgs)
  Dim ha As HttpApplication = CType(sender, HttpApplication)
  Dim handler As IHttpHandler = ha.Context.Handler

  Dim container As IS2Container = _
    SingletonS2ContainerFactory.Container
  container.HttpContext = HttpContext.Current

  Dim componentName As String = ha.Request.Path.ToLower()
  'コンポーネントが見つからなければ登録
  If Not container.HasComponentDef(componentName) Then
    Dim cd As IComponentDef = _
      New ComponentDefImpl(Nothing, componentName)
    cd.AutoBindingMode = ContainerConstants.AUTO_BINDING_AUTO
    cd.InstanceMode = ContainerConstants.INSTANCE_OUTER
    container.Register(cd)
  End If
  container.InjectDependency(handler, componentName)
End Sub

ちょっと乱暴な気がしているので、よりよい方法があれば
教えてください。

On Wed, 30 Jul 2008 11:35:59 +0900
kubo <[E-MAIL ADDRESS DELETED]> wrote:

> 久保(jflute)です。
>
> ももたろさん、こんにちは
>
> ちょっと具体的な回答はできなくて参考にならないかもですが、
> 自分が、ASP.NET使っていた時は、
>
> PageクラスからFacadeと呼ぶsingletonなビジネスロジッククラス
> を呼び出していましたが、PageクラスからContainerの
> GetComponentでFacadeを取得していました。
> 実際にはSingletonS2ContainerFactoryを隠蔽するstaticなクラス経由です。
> つまり、非常に単純な構造でやっていました。
> トランザクションはFacadeに掛けていました。
> 今だったら、QuillでPageクラスにInjectionすると思います。
>
> Pageクラス自体をどうにかしてS2コンポーネントにしたいと
> 色々試行錯誤しましたが、いまいち中途半端になってしまうので、
> 上記の単純構造でやったという記憶があります。
>
> 2008/7/30  <[E-MAIL ADDRESS DELETED]>:
> > はじめまして。ももたろと申します。
> >
> > ASP.NETからS2Dao.NETが使いたくて、まずはS2Container.NETをASP.NETで
> > 使用できるように環境を整えています。
> >
> > 今回の目的としては、WebフォームにsingletonなビジネスロジッククラスをDIして
> > 呼び出したいと考えています。
> > (そもそも、こんなことしないよ、とかあれば指摘してくださると嬉しいです)
> >
> > それを実現するためにWebフォームをコンポーネント登録しようとした場合、
> > 以下の点ではまってしまいましたので要望&相談させてください。
> >
> > (1) Webフォームをコンポーネント登録する際に仮想パスを書かないといけない。
> > アプリケーションルートからのパスを書けばよいものと思い、
> >
> >  <component name="/Default.aspx" instance="outer" />
> >
> > と書いていてずっと悩んでいました。
> > ドキュメントに「仮想パス」と明記してあるのに気付かなかった
> > 私が悪いのですが、変更する可能性のあるアプリケーションルートまで
> > 記述しないといけないのは、不便に感じました。
> > 「~/Default.aspx」などのルート演算子が使えるとうれしいと思います。
> >
> >
> > (2) 大文字小文字を区別する。
> >
> >  <component name="/WebSite1/Default.aspx" instance="outer" />
> >
> > と仮想パスを記述することで、意図するように動作したのですが、
> > 例えば、http://localhost/WebSite1/default.aspx などのように、
> > 大文字小文字が違っているURLでアクセスするとDIしてくれなく
> > なってしまいました。
> >
> > ユーザからは大文字でアクセスされるか小文字でアクセスされるかは
> > 分からないため、大文字小文字は無視されていて欲しいです。
> >
> > (3) Server.TransferするとDIされない。
> >
> >  Server.Transfer("~/Default.aspx")
> >
> > などとしてTransferした場合、Default.aspxにDIしてくれません。
> > 改めてS2HttpModuleを通らないので、このようになってしまうとは
> > 思うのですが、何らかの方法で改善されると嬉しいです。
> > とりあえず、代わりにRedirectを使用することで回避しようと
> > 思っています。
> >
> > (4) Webフォームを自動登録するよい方法は?
> > 画面数が増えた場合に、やはりWebフォームもAutoRegister等で自動登録
> > したいです。どのようなアプローチが考えられるでしょうか?
> >
> > 以上です。
> > つらつらと書いてしまいましたが、よろしくお願いします。


seasar-dotnet メーリングリストの案内