在没有控制反转的情况下隔离依赖性

时间:2009-07-14 21:35:10

标签: testing mocking typemock isolation

我正在开发一个严重依赖于消息队列,com +,数据库,httpcontext,静态实用程序类等的企业应用程序。

由于我们系统中有600个项目,因此重写使用控制反转似乎是不切实际的。 Typemock声称它们是doesn't require you to rewrite your code to use IOC唯一的隔离框架。

有人知道TypeMock如何实现这一级别的功能以及是否有其他选择?即使我要重写我的应用程序以使用控制反转,我也必须为消息队列,httpcontext等编写包装类。对我来说这听起来很荒谬,我认为Typemock是我唯一可行的选择是对还是错场景。

谢谢

4 个答案:

答案 0 :(得分:1)

Mocking non-virtual methods in C#

如果不深入挖掘,答案就是AOP技术。由于您可以在事后拦截方法调用或更改方法调用,因此很有可能添加模拟类/实例。

这是对AOP的巧妙使用。

如果你想自己做这件事(我确定有一些陷阱......),抓住一个开源的Aspect weaver框架:http://csharp-source.net/open-source/aspect-oriented-frameworks

答案 1 :(得分:1)

你认为TypeMock(或其他类似的模拟工具)是唯一可行的选择是正确的。

总是可以直接使用AOP工具来提供依赖关系的隔离,但这样做所需的工作量很大,这使得它在实践中不可行。

对于Java,JMockit工具包可以隔离所有类型的依赖项,而无需对生产代码进行任何必要的更改。

在内部,JMockit使用java.lang.instrument API提供的功能。基本上,它允许方法/构造函数在运行时重新定义。重新定义意味着替换实现方法/构造函数的字节码。对于相同的方法,这可以进行任何次数。此外,类可以在加载时转换(即,类中定义的任何方法或构造函数可以在类可用于JVM之前更改其字节码。)

答案 2 :(得分:1)

如果你有这样的课程:

public class MotherClass
{
    private SubClass _subClass;

    public MotherClass()
    {
        _subClass = new SubClass();
    }
}

public class SubClass
{
    public string SomeMethod()
    {
        return "Hello";
    }
}

没有IoC。但是使用Typemock Isolator,您仍然可以通过以下方式替换它:

    [TestMethod]
    public void TestMethod()
    {
        var fake = Isolate.Fake.Instance<SubClass>();
        Isolate.Swap.NextInstance<SubClass>().With(fake);
    }

甚至可以像这样换掉SomeMethod的结果:

        var fake = Isolate.Fake.Instance<SubClass>();
        Isolate.WhenCalled(() => fake.SomeMethod()).WillReturn("Bye");

答案 3 :(得分:0)

大多数模拟框架确实依赖某种形式的IOC。这是因为IOC实际上是一种很好的做法。除了测试之外,假设你有一个查找数据库连接的类(而不是注入它),现在数据库连接类发生了变化。您不必重新编译代码 - 您应该只能更改注入的依赖项。从测试的角度来看,你可以做同样的事情,注入模拟数据库服务。

为了更好地解决您的问题。我将专注于逐步重构注入而不是硬编码查找框架。从数据库和其他第三方服务等大块开始。当你重构它们时,你可以使用任何模拟框架(我使用过EasyMock,我喜欢它,但还有其他的 - JMock,Mockito)。这些框架不需要包装类,但通常依赖于代理对象。在创建模拟时,您实际上是在创建一个代理(这是您正在模拟的类类型的实例)。

字节码操作(例如,面向方面,因为Typemock使用)可能很重要。很多时候,您可能还有其他工具也可以操作字节代码(代码覆盖工具经常这样做),多字节代码操作可能会导致意外行为。

最后,您可以查看Groovy等语言。 Groovy适用于Java(它可以编译为字节码)并且在语言中内置了模拟功能。一些Google使用Groovy搜索模拟对象应该会返回一些好的结果。