2017-08-25 227 views
1

我有一個自定義的授權屬性見下面,我試圖編寫一個單元測試來測試它的功能。單元測試模擬HttpActionContext

public override void OnAuthorization(System.Web.Http.Controllers.HttpActionContext actionContext) 
    { 
     if (actionContext.Request.Headers.Authorization != null) 
     { 
      // get the Authorization header value from the request and base64 decode it 
      string userInfo = Encoding.Default.GetString(Convert.FromBase64String(actionContext.Request.Headers.Authorization.Parameter)); 

      // custom authentication logic 
      if (string.Equals(userInfo, string.Format("{0}:{1}", "user", "pass"))) 
      { 
       IsAuthorized(actionContext); 
      } 
      else 
      { 
       HandleUnauthorizedRequest(actionContext); 
      } 
     } 
     else 
     { 
      HandleUnauthorizedRequest(actionContext); 
     } 
    } 

    protected override void HandleUnauthorizedRequest(System.Web.Http.Controllers.HttpActionContext actionContext) 
    { 
     actionContext.Response = new HttpResponseMessage(System.Net.HttpStatusCode.Unauthorized) 
     { 
      ReasonPhrase = "Unauthorized" 
     }; 
    } 

我的問題是,當我試圖測試這個我得到「System.NullReferenceException:未將對象引用設置到對象的實例」我試圖設置actionContext的request.headers.authorization值,但它沒有setter。當我嘗試嘲笑HttpActionContext時,它說它不能從模擬的HttpActionContext轉換爲真實的。下面是我的測試代碼

public class HttpBasicAuthorizeAttributeTest 
{ 
    private HttpBasicAuthorizeAttribute ClassUnderTest { get; set; } 

    private HttpActionContext actionContext { get; set; } 

    [TestMethod] 
    public void HttpBasicAuthorizeAttribute_OnAuthorize_WithAuthorizedUser_ReturnsAuthorization() 
    { 
     var context = new Mock<HttpActionContext>(); 
     context.Setup(x => x.Request.Headers.Authorization.Parameter).Returns("bzUwkDal="); 
     ClassUnderTest.OnAuthorization(context); 
    } 

    [TestInitialize] 
    public void Initialize() 
    { 
     ClassUnderTest = new HttpBasicAuthorizeAttribute(); 
     actionContext = new HttpActionContext(); 
    } 
} 

*冷落的斷言,直到我甚至可以得到HttpActionContext工作

+0

您調用模擬對象這樣'ClassUnderTest.OnAuthorization(context.Object);'你還需要模擬其他授權明智空校驗將 – Nkosi

+0

您使用的起訂量永遠是假的呢?上次我使用moq時,我不得不使用.Object字段,在你的情況下:ClassUnderTest.OnAuthorization(context.Object); – pmezykowski

回答

2

您可以使用實際的對象,並以行使測試方法提供了模擬因爲Moq無法模擬非虛擬成員。

[TestMethod] 
public void HttpBasicAuthorizeAttribute_OnAuthorize_WithAuthorizedUser_ReturnsAuthorization() { 
    //Arrange 
    var context = new HttpActionContext(); 
    var headerValue = new AuthenticationHeaderValue("Basic", "bzUwkDal="); 
    var request = new HttpRequestMessage(); 
    request.Headers.Authorization = headerValue; 
    var controllerContext = new HttpControllerContext(); 
    controllerContext.Request = request; 
    context.ControllerContext = controllerContext; 

    //Act 
    ClassUnderTest.OnAuthorization(context); 

    //Assert 
    //... 
} 
+0

謝謝,這是正確地將它傳遞給方法。但是我掙扎着找到要反對的東西,因爲這個方法是無效的並且沒有返回 –

+1

Assert.IsNull(context.Response)似乎能夠工作,因爲如果它到了HandleUnauthorizedRequest方法中它只會被分配一個響應 –