简体   繁体   English

使用AWS开发工具包和Moq时无法类型转换Mock的对象

[英]Unable to typecast Mock's object when using the AWS SDK and Moq

I'm attempting to write unit tests around a service which will manage communication with various SQS queues. 我试图围绕服务编写单元测试,该服务将管理与各种SQS队列的通信。 I'm unable to inject Mocked versions of the IAmazonSQS into my class. 我无法将模拟的IAmazonSQS版本注入我的班级。 I have the following constructor: 我有以下构造函数:

private AmazonSQSClient client;

public SqsQueue(IAmazonSQS client, string queueUrl)
{
    this.client = (AmazonSQSClient)client;
    this.queueUrl = queueUrl;
}

The problem line is the assignment to this.client. 问题行是对此this.client的分配。 I get this exception: Additional information: Unable to cast object of type 'Castle.Proxies.IAmazonSQSProxy' to type 'Amazon.SQS.AmazonSQSClient'. 我收到此异常: Additional information: Unable to cast object of type 'Castle.Proxies.IAmazonSQSProxy' to type 'Amazon.SQS.AmazonSQSClient'. When I change that line to this: 当我将该行更改为此:

this.client = client as AmazonSQSClient;

this.client is set to null. this.client设置为null。

This is the relevant Unit Test code: 这是相关的单元测试代码:

public void Setup()
{
    this.mockClient = new Mock<IAmazonSQS>();
    this.queueUrl = "testUrl";
}

public void GetMessageCount_WhenMessagesExist_ReturnsCount()
{
    // Arrange
    var sqsQueue = new SqsQueue<IMessage>(this.mockClient.Object, this.queueUrl); // Calls into the constructor above.
} 

Am I missing something obvious here? 我在这里错过明显的东西吗?

I know you self-answered, but I figured I'd give my answer as well. 我知道您会自动回答,但我想我也会给出答案。

The problem is that your constructor is accepting an interface, then you are casting that interface to a discrete class. 问题在于您的构造函数正在接受一个接口,然后将该接口转换为离散类。 While this works for normal operations, it will not work in your unit testing, because your actual discrete class is not an AmazonSQSClient and has no relationship to it. 尽管这对于正常操作是有效的,但在您的单元测试中将不起作用,因为您实际的离散类不是 AmazonSQSClientAmazonSQSClient没有任何关系。 The only commonality between AmazonSQSClient and your mock object is that they both implement the IAmazonSQS interface. AmazonSQSClient和您的模拟对象之间的唯一共同点是它们都实现了IAmazonSQS接口。

To use the Amazon clients, all you need is the interface. 要使用Amazon客户端,您需要的只是界面。 So, change your member variable to the interface, and avoid the casting: 因此,将您的成员变量更改为接口,并避免强制转换:

private IAmazonSQS client;

public SqsQueue(IAmazonSQS client, string queueUrl)
{
    this.client = client;
    this.queueUrl = queueUrl;
}

I believe the issue was the typecasting itself. 我相信问题是打字本身。 I changed my class to have a private IAmazonSQS client rather than private AmazonSQSClient client . 我将类更改为具有private IAmazonSQS client而不是private AmazonSQSClient client That removes the necessity for the problematic typecasting and allows the tests to run. 这消除了有问题的类型转换的必要性,并允许运行测试。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM