gpt4 book ai didi

wcf - 模拟 PostSharp 属性的最简单方法

转载 作者:行者123 更新时间:2023-12-04 12:55:52 25 4
gpt4 key购买 nike

我正在使用 PostSharp 方法属性对我的 WCF 服务进行授权和审核。它工作正常,但现在我正试图让我的单元测试与属性一起工作,并且正在努力寻找一种方法来模拟和注入(inject)属性上的属性。

我的属性如下。

[Serializable]
[AttributeUsage(AttributeTargets.Method, AllowMultiple = false, Inherited = false)]
public class AuthoriseAndAuditAttribute : OnMethodBoundaryAspect
{
private static ILog logger = AppState.logger;

private static Ninject.IKernel _kernel = MyKernel.Kernel;

private UserRoleTypesEnum _requiredRole = UserRoleTypesEnum.None;

[Inject]
public IServiceAuthToken _serviceAuthToken { get; set; }

[Inject]
public UserSessionDataLayer _userSessionDataLayer { get; set; }

public AuthoriseAndAuditAttribute(UserRoleTypesEnum role = UserRoleTypesEnum.None)
{
_requiredRole = role;
_kernel.Inject(this);
}

public override void OnEntry(MethodExecutionArgs args)
{
// Get the user's session from cookie.
UserSession userSession = GetUserSession();

// Check that user is in the required role.
bool isAuthorised = (_requiredRole == UserRoleTypesEnum.None || (userSession != null && userSession.Roles.Contains(_requiredRole)));

if (!isAuthorised)
{
logger.Warn("Not authorised for " + args.Method.Name + ".");
throw new UnauthorizedAccessException();
}
else if (userSession != null)
{
Thread.CurrentPrincipal = new MyPrincipal(userSession);
}
}

private UserSession GetUserSession()
{
if (_serviceAuthToken != null)
{
string sessionID = _serviceAuthToken.GetSessionID();

if (!sessionID.IsNullOrBlank())
{
return _userSessionDataLayer.GetForSessionID(sessionID);
}
}

return null;
}
}

我有一个设置 Ninject 内核的单例类:
public class MyKernel
{
public static StandardKernel Kernel { get; set; }

static MyKernel()
{
Kernel = new StandardKernel();
Kernel.Bind<IServiceAuthToken>().To<ServiceAuthToken>();
Kernel.Bind<UserSessionDataLayer>().To<UserSessionDataLayer>();
}
}

在我的 WCF 服务中,我使用 PostSharp 属性,如下所示:
[AuthoriseAndAudit(UserRoleTypesEnum.Operator)]
public JSONResult<bool> IsAliveAuthorised()
{
return new JSONResult<bool>() { Success = true, Result = true };
}

在我的单元测试中,我使用 RhinoMocks 来尝试模拟属性中的两个 DI 属性。
 [TestMethod]
public void IsAliveAuthorisedIsAuthorisedTest()
{
var mockServiceAuthToken = MockRepository.GenerateStrictMock<ServiceAuthToken>();
mockServiceAuthToken.Stub(x => x.GetSessionID()).Return("x");
var mockUserSessionDataLayer = MockRepository.GenerateStrictMock<UserSessionDataLayer>();
mockUserSessionDataLayer.Stub(x => x.GetForSessionID(Arg<string>.Is.Anything)).Return(new UserSession());

MyKernel.Kernel.Bind<ServiceAuthToken>().ToConstant(mockServiceAuthToken);
MyKernel.Kernel.Bind<UserSessionDataLayer>().ToConstant(mockUserSessionDataLayer);

var service = new MyService();
Assert.IsTrue(service.IsAliveAuthorised().Result);
}

我遇到的问题是单元测试中的模拟对象永远不会被设置为属性的属性。我做错了什么,或者相反,有没有更好的方法对 PostSharp 属性进行单元测试?还要记住,我真的想尽量减少 Ninject DI 的使用。

最佳答案

不要在属性上使用 [Inject] 属性,而是像这样重新定义它们:

    public IServiceAuthToken _serviceAuthToken { get { return _kernel.Get<IServiceAuthToken>(); } }

public UserSessionDataLayer _userSessionDataLayer { get { return _kernel.Get<UserSessionDataLayer>(); } }

此外,在您的测试方法中,您需要重新绑定(bind)(另请注意,您在第一次绑定(bind)中使用的是具体类型 ServiceAuthToken 而不是接口(interface) IServiceAuthToken):
MyKernel.Kernel.Rebind<IServiceAuthToken>().ToConstant(mockServiceAuthToken);
MyKernel.Kernel.Rebind<UserSessionDataLayer>().ToConstant(mockUserSessionDataLayer);

关于wcf - 模拟 PostSharp 属性的最简单方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8920962/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com