1

Caliburn.MicroとNinjectを使用したMVVMに基づくWPFアプリケーションがあります。ShellViewModelというルートビューモデルがあります。CaliburnのBootstrapperで構成されているいくつかの依存関係(コンストラクターを介して注入)があります。ここまでは順調ですね。

どこかに、いくつかのボタンを備えたMenuViewModelがあり、それらは独自の依存関係を持つ他のビューモデルを開きます。これらのビューモデルはルートオブジェクトの作成中には作成されませんが、IoCコンテナから依存関係を注入したいと思います。

サービスロケーターと依存性注入に関するこの質問を読み、指摘されている点を理解しています。

ただし、動的に作成されているビューモデルを適切に挿入するには、MenuViewModelがIoCコンテナにアクセスできる必要があるという印象を受けています。これは避けようとしていることです。別の方法はありますか?

4

1 に答える 1

1

はい、私はあなたがもう少し良いことをすることができると信じています。

オンデマンド要件がない場合MenuViewModelは、オブジェクトグラフ()のルートに到達しShellViewModel、コンテナがすべてを接続するまで、これらのビューモデルをチェーンの依存関係などにすることができることを考慮してください。

MenuViewModel依存関係自体をの依存関係を構築できるものに置き換えることで、オブジェクトグラフに「ファイアウォール」を配置できます。コンテナはこの仕事の明白な選択であり、実用的な観点からは、これはそれほど純粋ではない場合でも十分な解決策です。

ただし、コンテナの代わりに専用の工場を代用することもできます。このファクトリはコンテナへの依存関係を取り、の実際の依存関係に対して読み取り専用プロパティを提供しますMenuViewModel。プロパティにアクセスすると、コンテナがオブジェクトを解決して返すようになります(プロパティの代わりにアクセサメソッドも機能します。より適切なのは完全に別の議論なので、あなたがより良いと思うものを使用してください)。

現状を実際に変更していないように見えるかもしれませんがMenuViewModel、コンテナに直接依存している場合と同じ状況ではありません。MenuViewModelその場合、パブリックインターフェイスを見ると、実際の依存関係が何であるかわかりませんが、次のようなものに依存関係があることがわかります。

interface IMenuViewModelDependencyFactory
{
    public RealDependencyA { get; }
    public RealDependencyB { get; }
}

これははるかに有益です。MenuViewModelDependencyFactoryそして、具体的なもののパブリックインターフェイスを見ると、はるかに優れています。

class MenuViewModelDependencyFactory : IMenuViewModelDependencyFactory
{
    private Container container;

    public MenuViewModelDependencyFactory(Container container) { ... }

    public RealDependencyA { get { ... } }
    public RealDependencyB { get { ... } }
}

MenuViewModelDependencyFactory非常に高度に専門化されているため、ここでコンテナをどのように処理するかについて混乱することはありません。

于 2012-05-06T23:23:30.963 に答える