编写unit testing在ASP.NET Web API中使用User.Identity.Name的方法

我正在使用ASP.NET Web API的unit testing编写testing用例。

现在我有一个动作,它调用了我在服务层中定义的一些方法,我已经使用了下面这行代码。

string username = User.Identity.Name; // do something with username // return something 

现在我如何创build这个unit testing方法,我得到空引用exception。 编写unit testing和东西我有点新意。

我只想使用unit testing。

请帮我解决这个问题。 谢谢。

下面的一个只是这样做的一个方法:

 public class FooController : ApiController { public string Get() { return User.Identity.Name; } } public class FooTest { [Fact] public void Foo() { var identity = new GenericIdentity("tugberk"); Thread.CurrentPrincipal = new GenericPrincipal(identity, null); var controller = new FooController(); Assert.Equal(controller.Get(), identity.Name); } } 

这是我在NerdDinnertesting教程中find的另一种方法。 它在我的情况下工作:

 DinnersController CreateDinnersControllerAs(string userName) { var mock = new Mock<ControllerContext>(); mock.SetupGet(p => p.HttpContext.User.Identity.Name).Returns(userName); mock.SetupGet(p => p.HttpContext.Request.IsAuthenticated).Returns(true); var controller = CreateDinnersController(); controller.ControllerContext = mock.Object; return controller; } [TestMethod] public void EditAction_Should_Return_EditView_When_ValidOwner() { // Arrange var controller = CreateDinnersControllerAs("SomeUser"); // Act var result = controller.Edit(1) as ViewResult; // Assert Assert.IsInstanceOfType(result.ViewData.Model, typeof(DinnerFormViewModel)); } 

请确保您阅读完整部分: 嘲笑User.Identity.Name属性

它使用Moq模拟框架,您可以使用NuGet在您的Test project安装: http : //nuget.org/packages/moq

与WebApi 5.0这个略有不同。 你现在可以做:

 controller.User = new ClaimsPrincipal( new GenericPrincipal(new GenericIdentity("user"), null)); 

这一切都没有为我工作,我用另一个问题的解决scheme,使用Moq在ControllerContext中设置一个用户名: https : //stackoverflow.com/a/6752924/347455

如果你有很多控制器来testing,那么我会build议创build一个基类,并在构造函数中创build一个GenericIdentityGenericPrincipal并设置Thread.CurrentPrincipal

 GenericPrincipal principal = new GenericPrincipal(new GenericIdentity("UserName"),null); Thread.CurrentPrincipal = principal; 

然后inheritance那个类。这样,每个unit testing类将有原则对象集

 [TestClass] public class BaseUnitTest { public BaseUnitTest() { GenericPrincipal principal = new GenericPrincipal(new GenericIdentity("UserName"),null); Thread.CurrentPrincipal = principal; } } [TestClass] public class AdminUnitTest : BaseUnitTest { [TestMethod] public void Admin_Application_GetAppliction() { } } 

在这里,我find了解决scheme的另一种方法,即如何从testing方法中设置控制器级别testing的用户身份名称。

 public static void SetUserIdentityName(string userId) { IPrincipal principal = null; principal = new GenericPrincipal(new GenericIdentity(userId), new string[0]); Thread.CurrentPrincipal = principal; if (HttpContext.Current != null) { HttpContext.Current.User = principal; } } 

当我运行unit testing – 在我的情况下,它使用Windows身份validation和Identity.Name是我的域名,我也想要更改testing。 所以我在IAuthenticationFilter中使用这种方法来“窃取”我想要的东西