2016-07-28 10 views
5

私は抽象クラスを模擬して、クラスの具象メソッドを以下のようにテストしました。UnitManagerのUserManagerとRoleManagerをどうやって模擬するのですか?

var mock = new Mock<BaseTestController>(); 
mock.CallBase = true; 
var ta = mock.Object; 

ta.ControllerContext = new HttpControllerContext { Request = new HttpRequestMessage() };   
var owinMock = new Mock<IOwinContext>(); 
owinMock.Setup(o => o.Authentication.User).Returns(new ClaimsPrincipal()); 
owinMock.Setup(o => o.Request).Returns(new Mock<OwinRequest>().Object); 
owinMock.Setup(o => o.Response).Returns(new Mock<OwinResponse>().Object); 
owinMock.Setup(o => o.Environment).Returns(new Dictionary<string, object> { { "key1", 123 } }); 
var traceMock = new Mock<TextWriter>(); 
owinMock.Setup(o => o.TraceOutput).Returns(traceMock.Object); 

ta.Request.SetOwinContext(owinMock.Object); 
var result = await ta.ActivateDeactive("[email protected]", true); 

問題:私は私の上記のモックコードでTestUserManager and TestRoleManagerを模擬することができますどのように

public TestUserManager UserService 
{ 
    get 
    { 
     return _userService ?? Request.GetOwinContext().GetUserManager<TestUserManager>(); 
    } 

    private set 
    { 
     _userService = value; 
    } 
} 

public TestRoleManager RoleService 
{ 
    get 
    { 
     return _roleService ?? Request.GetOwinContext().Get<TestRoleManager>(); 
    } 

    private set 
    { 
     _roleService = value; 
    } 
} 

を次のように 私の抽象クラスを使用Entity Framework 6 and Asp.Net Identity UserManager and RoleManager

私は次の方法を試しましたが、controllerContextを使用して接続する方法がありませんでした。

var userStore = new Mock<IUserStore<TestUser>>(); 
var userManager = new TestUserManager(userStore.Object); 

これはTestUserManagerUserManaerを導出し、実装する方法です

アレクセイ・L.によって以下尋ねた質問への答え。

public class TestUserManager : UserManager<TestUser> 
{ 
    public TestUserManager(IUserStore<TestUser> store) 
     : base(store) 
    { 
    } 
    public static TestUserManager Create(IdentityFactoryOptions<TestUserManager> options, IOwinContext context) 
    { 
     TestUserManager manager = new TestUserManager(new UserStore<TestUser>(context.Get<AuthContext>())); 
     setValidationRules(manager); 

     IDataProtectionProvider dataProtectionProvider = options.DataProtectionProvider; 
     if (dataProtectionProvider == null) 
      dataProtectionProvider = new DpapiDataProtectionProvider(); 
     manager.UserTokenProvider = new DataProtectorTokenProvider<TestUser>(dataProtectionProvider.Create("ASP.NET Identity")) { TokenLifespan = TimeSpan.FromDays(expiryTime) }; 

     return manager; 
    } 

    public static TestUserManager CreateLocal(AuthContext context) 
    { 
     TestUserManager manager = new TestUserManager(new UserStore<TestUser>(context)); 
     setValidationRules(manager); 

     IDataProtectionProvider dataProtectionProvider = new DpapiDataProtectionProvider(); 
     manager.UserTokenProvider = new DataProtectorTokenProvider<TestUser>(dataProtectionProvider.Create("ASP.NET Identity")); 

     return manager; 
    } 

    private static void setValidationRules(ApplicationUserManager manager) 
    { 
     manager.UserValidator = new UserValidator<TestUser>(manager) 
     { 
      AllowOnlyAlphanumericUserNames = false, 
      RequireUniqueEmail = true 
     }; 

     manager.PasswordValidator = new ApplicationPasswordValidator 
     { 
      RequiredLength = 30, 
      MaximumCharacters = 30, 
      RequireNonLetterOrDigit = false, 
      RequireDigit = true, 
      RequireLowercase = false, 
      RequireUppercase = false 
     }; 
    } 
} 

コントローラコード

public async Task<IHttpActionResult> ActivateDeactive(string studentId, bool active) 
{ 
    IdentityResult result; 
    _accountService = new AccountMgtService(UserService, RoleService); 
    result = await _accountService.ActiveDeactiveUser(userId, active); 

} 
+0

は、コントローラは 'UserManager' –

+0

をどのように使用するかを表示する私の更新の質問を確認してください - あなたに最後の部分の答えを質問。 – immirza

+0

私はコントローラのコードを意味します。 'UserManager'を呼び出すコード –

答えて

5

あなたがTestUserManagerを実装しようとしている理由はわからないし、それをからかっていません。

var owinContext = Request.GetOwinContext(); 
var userManager = owinContext.GetUserManager<ApplicationUserManager>(); 
var applicationUser = userManager.FindById("testId"); 

あなたはモックユーザーストアをこのように注入することができます:緯度さんは、私たちは、コントローラのコードを次していると言う

var owinMock = new Mock<IOwinContext>(); 

var userStoreMock = new Mock<IUserStore<ApplicationUser>>(); 
userStoreMock.Setup(s => s.FindByIdAsync("testId")).ReturnsAsync(new ApplicationUser 
{ 
    Id = "testId", 
    Email = "[email protected]" 
}); 
var applicationUserManager = new ApplicationUserManager(userStoreMock.Object); 

owinMock.Setup(o => o.Get<ApplicationUserManager>(It.IsAny<string>())).Returns(applicationUserManager); 

ta.Request.SetOwinContext(owinMock.Object); 
+0

優れています。しかし、今私は別の問題で終わった...なぜApplicationUser user = UserManager.FindById(userId); nullを返しますか?たとえuserIdがデータベーステーブルに存在するとしても?私は嘲笑でもっと何かをする必要がありますか? – immirza

+1

もちろん、モックのユーザーストアを設定する必要があります。更新された回答をご覧ください。また、質問からすべての冗長なものを削除することができますので、他の人には理解しやすくなります –

+0

Excellent Aleksey L.それほど簡単ではないと思ったことはありません。ありがとう – immirza

関連する問題