Asp.net mvc 单元测试自定义授权属性
我已经编写了一个自定义的claims authorizatize属性,我想对我编写的代码进行单元测试,但是一直找不到我想要的东西 例如,这是我的自定义授权属性类:Asp.net mvc 单元测试自定义授权属性,asp.net-mvc,unit-testing,bdd,authorize-attribute,Asp.net Mvc,Unit Testing,Bdd,Authorize Attribute,我已经编写了一个自定义的claims authorizatize属性,我想对我编写的代码进行单元测试,但是一直找不到我想要的东西 例如,这是我的自定义授权属性类: using System.Collections.Generic; using System.IdentityModel.Tokens.Jwt; using System.Linq; using System.Security.Claims; using System.Web; using System.Web.Mvc; using
using System.Collections.Generic;
using System.IdentityModel.Tokens.Jwt;
using System.Linq;
using System.Security.Claims;
using System.Web;
using System.Web.Mvc;
using System.Web.Security;
using IPD2.MVC.Interfaces.Providers;
using IPD2.MVC.Providers;
namespace IPD2.MVC.Attribute
{
public class ClaimsAuthorizeAttribute : AuthorizeAttribute
{
private readonly string _claimValue;
private readonly string _claimType;
private readonly ITokenProvider _tokenProvider;
public ClaimsAuthorizeAttribute(string type, string value)
{
_claimType = type;
_claimValue = value;
_tokenProvider = new TokenProvider();
}
public override void OnAuthorization(AuthorizationContext filterContext)
{
var jwt = _tokenProvider.ApiToken as JwtSecurityToken;
if (jwt == null)
{
HandleUnauthorizedRequest(filterContext);
}
else
{
var claim = jwt.Claims.FirstOrDefault(expr => expr.Value == _claimValue);
var authCookie = HttpContext.Current.Request.Cookies[FormsAuthentication.FormsCookieName];
if (authCookie != null)
{
var formsAuthenticationTicket = FormsAuthentication.Decrypt(authCookie.Value);
if (formsAuthenticationTicket != null && !formsAuthenticationTicket.Expired)
{
var roles = formsAuthenticationTicket.UserData.Split(',');
HttpContext.Current.User = new System.Security.Principal.GenericPrincipal(new FormsIdentity(formsAuthenticationTicket), roles);
}
}
if (claim != null)
{
base.OnAuthorization(filterContext);
}
else
{
HandleUnauthorizedRequest(filterContext);
}
}
}
}
}
测试代码
public class GivenCallingClaimAuthorizationAttribute : SpecsFor<ClaimsAuthorizeAttribute>
{
//HttpActionContext actionContext;
//IPrincipal originalPrincipal;
protected override void Given()
{
SUT = new ClaimsAuthorizeAttribute(ClaimTypes.Role, "ImNotAllowedToUseController :(");
}
public class WhenUserIsNotAllowedToAccessController : GivenCallingClaimAuthorizationAttribute
{
protected override void When()
{
SUT.OnAuthorization(
new AuthorizationContext()
);
}
}
[Test]
public void ThenAssertSomethingBasedOnCodeInTest()
{
//todo: some assert
}
}
public类给定CallingClaimauAuthorizationAttribute:规范
{
//HttpActionContext-actionContext;
//i原则原创原则;
给定的受保护覆盖无效()
{
SUT=新的ClaimsAuthorizeAttribute(ClaimTypes.Role,“ImNotAllowedToUseController:(”);
}
当用户未安装LowedtoAccessController时的公共类:givenCallingClaimauAuthorization属性
{
受保护的覆盖在()时无效
{
SUT.授权(
新授权上下文()
);
}
}
[测试]
public void TheAssertSomeThingBasedOnCodeIntest()
{
//todo:一些断言
}
}
我已经用BDD框架的规范编写了这个基本的测试类,但我不确定成功测试它需要什么
关于如何测试这一点有什么想法吗?正如您所看到的,我正在测试类本身,而不是具有该属性的控制器。我不确定有什么好的方法来测试这一点。如果您想执行BDD,请考虑您的类的行为。它应该能够执行什么样的操作 例如,也许它应该:
-授权当前用户
-筛选票证已过期的用户
-为授权用户分配正确的角色
-等等 假设我们要看第二张票,因为它很有趣,我会问你,“你能给我一张票什么时候到期的例子吗?” 然后你说,“是的,超时时间是500毫秒,所以超过这个时间的任何东西都会过期。”或者你说,“这些是足球比赛的门票,每年都会发放。”(我不知道什么是门票,但这段对话可以帮我解决这个问题。) 那么我们可以写一个例子:
Given we've got a handler for unauthorized tickets
Given Fred's ticket expired on 2017-05-14
And it's now 2017-05-14
When we try to authenticate Fred
Then Fred should not be authenticated
And the handler should be given Fred's details
接下来,我想把这些放在代码中的注释中,以“应该”作为测试的标题。之后,只需设置上下文(在给定的上下文中),将其传递给代码进行练习(时间),并验证结果(然后)
但是,您可以看到您的Specs框架只允许一个给定的!这不是很好,因为我已经确定了几个需要不同上下文的场景。如果您使用Specs的方式使用它,您将不得不为我的每个场景创建一个类,而且它们不太容易阅读
我强烈建议改为使用第二种样式,从给定的、何时开始,然后在注释中开始
问题是,与完整系统BDD场景相比,单元测试的步骤实际上没有被重用多少,在这种场景中,上下文通常会被多次调用以获得不同的功能。一个代码单元(或类)倾向于履行一项职责,或者以这种方式进行重构,并且它的上下文不会因为模拟而流入其他类
所以,我发现,仅仅在评论中给出,什么时候,然后给出就足够了
因此,我建议你改用“老派”的方式做我在本页(底部)看到的事情,从评论开始。看看你是怎么做的
顺便说一句,如果你真的想正确地进行BDD,那么你想用BDD的行为示例来驱动开发,并逐步地填充代码使这些示例工作,而不是把它们写下来。这本书将对你非常有帮助