First, you are missing this line in your test:
Thread.CurrentPrincipal = cp.Object;
(and then cleaning it up in TearDown).
Second, as @trailmax mentioned, mocking principal objects is impractical. In your case, ClaimsPrincipal.FindFirst
(according to decompiled source) looks into private fields of its instance, that's the reason mocking didn't help.
I prefer using two simple classes that allow me to unit test claims-based functionality:
public class TestPrincipal : ClaimsPrincipal
{
public TestPrincipal(params Claim[] claims) : base(new TestIdentity(claims))
{
}
}
public class TestIdentity : ClaimsIdentity
{
public TestIdentity(params Claim[] claims) : base(claims)
{
}
}
then your test shrinks down to:
[Test]
public void TestGetName()
{
// Arrange
var sut = new HomeController();
Thread.CurrentPrincipal = new TestPrincipal(new Claim("name", "John Doe"));
// Act
var viewresult = sut.GetName() as ContentResult;
// Assert
Assert.That(viewresult.Content, Is.EqualTo("John Doe"));
}
and it now passes, I've just verified.
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…