0

私はApiControllerの単体テストを書こうとしていて、いくつかの問題に直面しています。ここでWeb apiでRequest.formを模擬する方法

は、これは私のコントローラのコードである私のtestMethod

 [TestMethod] 
     public void CustomerController_AddUnitTest() 
     { 


      var custid = Guid.NewGuid(); 
      var customers = new Customer() { CustomerName = "Enterprise", CustomerId = custid }; 
      var rmContext = MockRepository.GenerateMock<HttpContextBase>(); 
      var rmRequest = MockRepository.GenerateMock<HttpRequestBase>(); 
      rmContext.Stub(x => x.Request).Return(rmRequest); 
      var FormData = new NameValueCollection { { "FirstName", "Jonathan" }, { "LastName", "Danylko" } }; 
      rmRequest.Stub(r => r.Form).Return(FormData); 
      rmContext.Stub(p => p.Request).Return(rmRequest); 
      var forms = rmContext.Request.Form; 

> // here i am able to get forms value but i couldn't pass these value 
> to main controller 

      var mockRepository = MockRepository.GenerateMock<ICustomerService>(); 
      mockRepository.Stub(x => x.Add(new Customer())).IgnoreArguments().Return(1); 
      _customerController = new CustomerController(mockRepository); 
      var result = _customerController.CustomerAdd(); 
      Assert.IsNotNull(result); 
     } 

である私はvar formData = HttpContext.Current.Request.Form["FormData"];

にモックデータを渡したい

public int CustomerAdd() 
    { 
     var localhost = HttpContext.Current.Request.Url.Authority; 
     var formData = HttpContext.Current.Request.Form["FormData"]; 
     JavaScriptSerializer json_serializer = new JavaScriptSerializer(); 
     var customer = json_serializer.Deserialize<Customer>(formData); 
     if (HttpContext.Current.Request.Files.Count > 0) 
     { 
      HttpPostedFile file = HttpContext.Current.Request.Files[0]; 
      string fileName = customer.CustomerName.Trim() + "_" + file.FileName; 
      var filePath = HttpContext.Current.Server.MapPath(Constants.FileUploadImagePath + fileName); 
      file.SaveAs(filePath); 
      customer.Logo = fileName; 
     } 
     return _iCustomerService.Add(customer); 
    } 

のように見える誰もがこの問題を解決するためのアイデアを持っていることができます私は文字通りこの仕事に疲れました。

+0

テスト中のメソッドが設計されておらず、静的な依存関係と緊密に結合されているためテストが困難です。あなたのコードを 'HttpContext'に強く結合するのを避けてください。 – Nkosi

+0

はい私はそれを知っていた。しかし、私はこのコード行を模擬する方法を知らない。 –

+0

var formData = HttpContext.Current.Request.Form ["FormData"]; –

答えて

0

ラインを別の(バーチャル)メソッドに引き出し、テストでは、モックデータを返す新しいメソッドをスタブしたコントローラの部分モックを使用します。 (これはFYIの「テストシーム」と呼ばれます)。このような

何か:

public int CustomerAdd() 
{ 
    var localhost = HttpContext.Current.Request.Url.Authority; 
    var formData = GetFormData()["FormData"]; 
    JavaScriptSerializer json_serializer = new JavaScriptSerializer(); 
    var customer = json_serializer.Deserialize<Customer>(formData); 
    if (HttpContext.Current.Request.Files.Count > 0) 
    { 
     HttpPostedFile file = HttpContext.Current.Request.Files[0]; 
     string fileName = customer.CustomerName.Trim() + "_" + file.FileName; 
     var filePath = HttpContext.Current.Server.MapPath(Constants.FileUploadImagePath + fileName); 
     file.SaveAs(filePath); 
     customer.Logo = fileName; 
    } 
    return _iCustomerService.Add(customer); 
} 

public virtual NameValueCollection GetFormDatat() 
{ 
    return HttpContext.Current.Request.Form; 
} 

次に、あなたのテストでこれを使用します。

_customerController = MockRepository.GeneratePartialMock<CustomerContoller>(); 
_customerController.Stub(c => c.GetFormData()).Return(yourFakeFormData); 

また、あなたが同じことを行うが、Contextオブジェクトの用途に可能性があります。

+0

一般的な注意として、あなたの生産コードがモックフレームワークタイプへの参照を直接取ることは決してありません。元の投稿では、モックリポジトリをコンストラクタパラメータとして取るコントローラクラスを表示します。これは決して起こらないはずです。モックフレームワークは実際に使用しているタイプを模倣して、プロダクションがテストコードを知る必要がないようにするためのものです。 –

関連する問題