你怎么嘲笑一个密封的课吗?
-
08-06-2019 - |
解决方案
我一般的经验法则是,对象我需要的模拟应该有一个共同的接口。我认为这是正确的设计和使得测试一个很容易(而且通常是你得到的是什么如果你做TTD).更多关于这个可以读谷歌测试的博客 最新发表的文章 (参见第9点).
此外,我已经工作主要是在Java在过去4年来,我可以说,我可以数上一只手的次数,我已经创建了一个最终的(密封的)类。另一条规则在这里是我应该总是有一个很好的理由密封的一类,而不是密封的默认。
其他提示
为。净,你可以用的东西喜欢 TypeMock, ,它使用的分析API,并允许你挂钩的呼吁,几乎任何事情。
我相信, 摩尔, 从Microsoft的研究,允许你这样做。从摩尔页:
摩尔可以用来绕道任。净 方法,包括非虚拟/静 方法是在密封的类型。
更新: 有一个新框架,称为"假",在即将到来的VS11释放而设计的替换摩尔:
的 假货框架Visual Studio11 是下一代的摩尔&存根,并将最终取代它。伪造是不同于摩尔,然而,让人感动的从摩尔假货将需要一些修改你的代码。指导这种迁移将在稍后的日期。
要求:Visual Studio11最终的,.净额4.5
该问题与TypeMock的是,它借口糟糕的设计。现在,我知道,这是经常 别人的 糟糕的设计,它是隐藏的,但允许它进入你的发展过程中可能导致非常容易地允许你自己不好的设计。
我觉得如果你要用一个嘲讽的框架,应使用一个传统的人(如最低采购量),并创建一个隔离层周围unmockable的事情,和模拟的隔离层代替。
我几乎总是避免依赖于外部类内心深处我的代码。相反,我宁愿使用的适配器/桥他们交谈。这样,我处理我的语义和痛苦的翻译被孤立在一个类。
它还可以更容易地交换我的依赖关系在长期运行。
我碰到这个问题最近在阅读/搜索网,似乎没有简单的方法周围除了使用其他工具,如上文所述。或粗处理事情如我所做的:
- 创建的实例封类没有得到constructor称为。
系统。运行时间。序列化。FormatterServices.GetUninitializedObject(instanceType);
分配值,你的性能/领域通过反射
- YourObject.GetType().GetProperty("属性名").设定值(也可与检,newValue,null);
- YourObject.GetType().GetField("FieldName").设定值(也可与检,newValue);
我通常采取的路线创建一个接口适配器/代理类,以方便嘲笑的封类型。然而,我也尝试过跳过创建的接口,并使代理类型的非密封与的虚拟的方法。这个工作以及当代理是真正的自然基类封装和用户部分的密封舱。
在处理与代码所需要的这种适应,我厌倦了执行同行动创建的接口和代理类型,因此我实现了一个图书馆自动执行的任务。
代码是有更复杂的样品鉴于在文章中引用,因为它会产生一个大会(而不是源代码),可使用代码生成能进行任何类型,而不需要尽可能多的配置。
欲了解更多信息,请参阅 这页.
这是完全合理的模拟一封类,因为许多类框架都是密封的。
在我的情况下,我想到嘲笑。净的如流这样我可以TDD我的异常优美的处理逻辑。
如果任何人有想法就如何克服最低采购量的错误,关于"无效设定一个不可复盖的成员",请让我知道。
代码:
[TestMethod]
public void Test()
{
Queue<Message> messages = new Queue<Message>();
Action<Message> sendDelegate = msg => messages.Enqueue(msg);
Func<TimeSpan, MessageQueueTransaction, Message> receiveDelegate =
(v1, v2) =>
{
throw new Exception("Test Exception to simulate a failed queue read.");
};
MessageQueue mockQueue = QueueMonitorHelper.MockQueue(sendDelegate, receiveDelegate).Object;
}
public static Mock<MessageQueue> MockQueue
(Action<Message> sendDelegate, Func<TimeSpan, MessageQueueTransaction, Message> receiveDelegate)
{
Mock<MessageQueue> mockQueue = new Mock<MessageQueue>(MockBehavior.Strict);
Expression<Action<MessageQueue>> sendMock = (msmq) => msmq.Send(It.IsAny<Message>()); //message => messages.Enqueue(message);
mockQueue.Setup(sendMock).Callback<Message>(sendDelegate);
Expression<Func<MessageQueue, Message>> receiveMock = (msmq) => msmq.Receive(It.IsAny<TimeSpan>(), It.IsAny<MessageQueueTransaction>());
mockQueue.Setup(receiveMock).Returns<TimeSpan, MessageQueueTransaction>(receiveDelegate);
return mockQueue;
}
尽管其目前仅在测试版,我认为它值得牢记的 垫片 功能的新的 假货框架 (的一部分 Visual Studio11 测试释放)。
垫片类型提供了一个机制来绕道任。净的方法来定义的用户代表。垫片类型的代码生成的假发生器,以及他们使用的各位代表,我们呼垫片的种类,指定新的方法实现。引擎盖下、垫片类型使用的回调注射在运行的方法集机构。
我个人是在寻找使用这个模拟的方法密封的框架类别,如DrawingContext.
有没有办法实现一个密封类从一个接口...和模拟的接口,而不是?
在我的东西感觉的是,具有密封类是错误的,在第一位,但这只是我:)