【问题标题】:Moq says Constructor arguments cannot be passed for interface mocksMoq 说不能为接口模拟传递构造函数参数
【发布时间】:2017-09-06 03:59:46
【问题描述】:

我在测试这样的应用程序 ASP.NET MVC 5 时遇到了一些问题

Castle.Proxies.IdentityUserLogin: : EntityType 'IdentityUserLogin' 没有定义键。定义此 EntityType 的键。 Castle.Proxies.IdentityUserRole: : EntityType 'IdentityUserRole' 没有定义键。定义此 EntityType 的键。 IdentityUserLogins:EntityType:EntitySet 'IdentityUserLogins' 基于没有定义键的类型'IdentityUserLogin'。 IdentityUserRoles: EntityType: EntitySet 'IdentityUserRoles' 基于没有定义键的类型'IdentityUserRole'。

我测试了 UserService,我使用的是 Moq 和 NUnit 框架。当我添加这个时,我解决了所有问题:

var mockContext = new Mock<SomeContext>() { CallBase = true };

但现在我遇到了这个问题:

消息:System.ArgumentException:无法为接口模拟传递构造函数参数。

如果你愿意,你可以在下面查看我的代码,但我认为问题只在“mockContext”中

[Test, TestCaseSource(typeof(UserServiceTestData), nameof(UserServiceTestData.WrongCreateUserTestCases))]
    public void ShouldWrongUserCreationTest(UserDTO userDto)
    {
        //Arrange
        var user = new ApplicationUser
        {
            Email = "test",
            Roles = { new IdentityUserRole { UserId = "test", RoleId = "test" } },
            ClientProfile = new ClientProfile { Name = "test" }
        };

        var mockStore = new Mock<IUserStore<ApplicationUser>>();
        mockStore.Setup(x => x.FindByIdAsync(It.IsAny<string>())).Returns(Task.FromResult(user));
        mockStore.As<IUserEmailStore<ApplicationUser>>().Setup(x => x.FindByEmailAsync("existed")).Returns(Task.FromResult((ApplicationUser)null));
        mockStore.As<IUserPasswordStore<ApplicationUser>>();
        mockStore.As<IUserRoleStore<ApplicationUser>>().Setup(x => x.AddToRoleAsync(It.IsAny<ApplicationUser>(), It.IsAny<string>()))
            .Returns(Task.FromResult(IdentityResult.Success));
        mockStore.As<IUserRoleStore<ApplicationUser>>().Setup(x => x.GetRolesAsync(It.IsAny<ApplicationUser>()))
           .Returns(Task.FromResult((IList<string>)new List<string>()));
        mockStore.Setup(x => x.CreateAsync(It.IsAny<ApplicationUser>()))
            .Returns(Task.FromResult(IdentityResult.Success));

        var mockDbSet = new Mock<DbSet<ClientProfile>>(MockBehavior.Strict);
        mockDbSet.Setup(x => x.Add(It.IsAny<ClientProfile>())).Returns(new ClientProfile());

        var userManager = new ApplicationUserManager(mockStore.Object);
        var mockContext = new Mock<AuthenticationContext>() { CallBase = true };
        var mock = new Mock<IIdentityUnitOfWork>(mockContext.Object);
        mock.Setup(a => a.UserManager).Returns(userManager);

        //Act
        var userService = new UserService(mock.Object);
        OperationDetails result = userService.Create(userDto);

        //Assert
        Assert.That(result.Succedeed, Is.False);
    }

【问题讨论】:

    标签: asp.net-mvc unit-testing authentication moq


    【解决方案1】:

    我猜问题出在这一行:

    var mock = new Mock<IIdentityUnitOfWork>(mockContext.Object);
    

    moq 基于 IIdentityUnitOfWork 创建的动态类只有默认构造函数,它不知道如何处理 mockContext.Object。 从模拟构造函数中删除 mockContext.Object 应该可以解决您的问题。

    【讨论】:

    • 是的!我决定了问题!你也是对的,但测试数据不正确,我已经了解它是如何工作的。感谢您的帮助
    猜你喜欢
    • 2017-11-04
    • 1970-01-01
    • 2011-02-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-10-24
    • 2014-06-03
    • 2011-11-16
    相关资源
    最近更新 更多