Moq +单元测试+ System.Reflection.TargetParameterCountException:参数计数不匹配

时间:2015-05-11 16:40:33

标签: unit-testing moq

我在尝试模拟ApiClient时收到“System.Reflection.TargetParameterCountException:Parameter Count mismatch”异常。

我使用以下代码来设置Moq响应

/security/limits.conf

我试图模拟的iApiClient接口是

private void SetupApiClientForGetZones(IEnumerable<Zone> zone)
{
    this.MockHubApiClient.Setup(x => x.GetAsync<IEnumerable<Zone>>(It.IsAny<string>(), It.IsAny<IDictionary<string, string>>()))
                .Returns(
                    (string name) =>
                    {
                        return zone == null ? Task.FromResult<IEnumerable<Zone>>(null) : Task.Run(() => zone);
                    });

            this.MockApiClientFactory.Setup(x => x.CreateClient(It.IsAny<string>()))
                .Returns(this.MockHubApiClient.Object);
        }

我的单元测试是

public interface IApiClientAsync : IApiClient
    {
        Task<string> GetAsync(string apiController);

        Task<T> GetAsync<T>(string apiController) where T : class;

        Task<string> GetAsync(string apiController, IDictionary<string, string> param, string queryString);

        Task<T> GetAsync<T>(string apiController, IDictionary<string, string> param) where T : class;
}

我发现许多其他帖子都有相同的例外,但没有一个解决方案或示例与我的相同。

在调用只有单字符串参数的GetAsync方法时,我能够成功模拟响应。

[Test]
public void GetZonesNotCached()
{
    var data = new List<Zone> { new Zone { ZoneId = 1, ZoneName = "Test Zone 1" }, new Zone { ZoneId = 2, ZoneName = "Test Zone 2" } };

    this.SetupApiClientForGetZones(data);

    this.MockCache.Setup(x => x.GetItemFromCache<IEnumerable<Zone>>(It.IsAny<string>()));

    var organisationService = new OrganisationService(this.MockUnitOfWorkAsync.Object, this.MockApiClientFactory.Object, this.MockCache.Object);

    var results = organisationService.GetZones(1, 1).ToList();

    Assert.IsNotNull(results);
    Assert.AreEqual(3, results.Count, "There should be 3 records returned");

    this.MockCache.Verify(x => x.GetItemFromCache<IEnumerable<Zone>>(It.IsAny<string>()), Times.Once());
    this.MockHubApiClient.Verify(x => x.GetAsync<IEnumerable<Zone>>(It.IsAny<string>(), It.IsAny<IDictionary<string, string>>()), Times.Once());
}

任何想法?

1 个答案:

答案 0 :(得分:3)

如果在.Returns中使用表达式而不是值,则表达式的参数必须与您正在模拟的方法签名的参数匹配。

例如,我在 SetupApiClientForGetZones 中找到了这个:

this.MockHubApiClient.Setup(x => x.GetAsync<IEnumerable<Zone>>(It.IsAny<string>(), It.IsAny<IDictionary<string, string>>()))
                .Returns(
                    (string name) =>
                      {
                        return zone == null ? Task.FromResult<IEnumerable<Zone>>(null) : Task.Run(() => zone);
                      });

真的应该是:

this.MockHubApiClient.Setup(x => x.GetAsync<IEnumerable<Zone>>(It.IsAny<string>(), It.IsAny<IDictionary<string, string>>()))
                .Returns<string, IDictionary<string, string>>(
                    (name, dict) =>
                      {
                        return zone == null ? Task.FromResult<IEnumerable<Zone>>(null) : Task.Run(() => zone);
                      });