2011-08-03 8 views
2

シナリオ我々は新しいMVC Webプロジェクトを開発していると、この記事で説明したように、私たちはスキニーControllerパターンに準拠しようとしているモッキングのHttpContext **外**コントローラーの

http://codebetter.com/iancooper/2008/12/03/the-fat-controller/

私たちの行動の一環として、キャッシュからいくつかのナビゲーションデータ(メニュー構造)を取得しています。

問題私たちは私たちが試みていると私たちは次のコードを使用して、作品を知っているViewModelに、キャッシュ・チェック・コールをしたいのですスキニーコントローラパターンを維持するために

var cachedCategories = (List<Category>)HttpContext.Current.Cache["Categories"]; 
if (cachedCategories == null) { 
     cachedCategories = _service.GetCategories().ToList<Category>(); 
     HttpContext.Current.Cache["Categories"] = cachedCategories; 
} 

ただし、単体テストになると問題が発生します。 がHttpContextをViewModelに渡すのではないので、HttpContextをどうやって嘲笑うかわからない。

私たちはMoqを使用していますが、いくつかのオプションがあります(1つはインスタンシエーション時にコントローラのコンテキストをviewmodelに渡すものです)。これらのオプションでは、テストを動作させるためにコードを変更する必要があります。

誰にも提案はありますか?

+0

ローカル変数に割り当てることができるコントローラにプロパティを設定できます。nullの場合はHttpContect.Currentが割り当てられ、HttpContextBaseが返され、テストからHttpContextBaseを割り当てることができます。それが意味をなさないならば。 – Phill

+0

IoCフレームワークを使用している場合、自動的にHttpContext.CurrentをHttpContextBaseプロパティ(またはコンストラクタ)に割り当てることができます。フィールドまたは自動プロパティを持つことができます。 (私が思うには、ブログの投稿がこれに当たると思う;)) – Phill

+0

テスト目的のためだけにプロパティを追加することは、私たちが思いついたオプションの1つですが、それをやりたいとは思いません。純粋にテストのためにコードを追加するのを避けようとしています。 – Morgeh

答えて

1

私たちは最終的にテストを容易にするためにコードを変更することを選択します。

元の質問で述べたように、インスタンス化時にViewModelにHttpContextを渡すことでこれを実現しました。

1

モックHttpContextはあなたの人生全般で見られる最大のオブジェクトの1つですので、巨大な作業ですので、おそらくそれを嘲笑しないでください(http://volaresystems.com/Blog/post/Dont -mock-HttpContext.aspx) とにかく、MVCcontrib(http://www.codeplex.com/mvcContrib)の中で、MvcMockHelpsがどのように行われているかを示すファイルを使用することができます。

+0

テストをオブジェクト参照例外で失敗させるため、これはオプションではありません。 – Morgeh

+0

あなたはのHttpContextあなたは私がMvcContribで簡単にのぞき見を持っていた –

+0

:-) MvcMockHelpsのために行くだろうあまりにも 模擬すべき依存関係の百を持っている私の答え に示したようMvcContribプロジェクト であるMvcMockHelpsを使用することができます私はそれが非常に便利だと私は同意するが、私はそれがこのインスタンスで私を助けることができる方法を理解していないか分からない。 「TestHelperは、内部データメンバーが正しく初期化されたコントローラを作成するコントローラファクトリを提供することによって支援します。私の問題は、ViewModel内部のコントローラの**外部**のHttpContextをモックしようとしていることです。 – Morgeh