2016-05-12 41 views
1

Rhino Mocks与使用依赖注入和构造函数注入的设计模式紧密耦合,但我通常不遵循依赖注入范例,也不喜欢为我的测试工具重新构建我的解决方案。使用虚拟受保护的工厂方法来模拟在类中创建的对象?

采取这样的场景:

class MyClass{ 
    public void MyMethod(...){ 
     var x = new Something(...); 
     x.A(); 
     x.B(); 
     x.C(); 
    } 
} 

难道是比较典型的和可以接受的,而不是做到以下几点,因为这不是我一般会想注入依赖的情况下 - 它可以是所考虑的一部分MyClass'行为/逻辑。

class MyClass{ 
    public void MyMethod(...){ 
     var x = NewSomething(...); 
     x.A(); 
     x.B(); 
     x.C(); 
    } 
    virtual protected Something NewSomething(...){ 
     return new Something(...); 
    } 
} 

现在我可以(我认为)延长MyClass无论是在我的测试项目的具体类,或使用犀牛...对不对?这是否是正确的b)合理的,普通的做事方式?

另一种方法,我可以看到比其他DI可能是因为我其实在我的项目,该项目产生的所有实例根据需要ClassFactory类;那么我会找到一种方法在我的测试中模拟/存根。但是这对我来说似乎'很臭',尽管我知道这是一些人使用的模式。

+2

这是什么东西?如果你在你的构造函数中接受某种SomethingFactory(例如,只是一个'Func '),它肯定会更灵活......基本上你的prod代码现在仍然与'Something'紧密耦合......我会尝试开始考虑这是一个依赖。 –

+0

@JonSkeet是的,这将消除这个问题,但我没有在批发DI上出售。让我们不要在这里讨论这个讨论(!),但是感谢您指出了另一种方法,这当然是有效的。 –

+0

那么这是一个奇怪的问题 - 那么你的方法的“合理性”肯定与其他方法的合理性有关 - 但你不愿意讨论这些方法。如果你只是问“这个代码是否工作”,那么答案是“是”,但你可以自己尝试过...... –

回答

1

试图让旧代码的可测试性,当我有这个用了好几次,但它真的很喜欢回来,后来咬你。

基本上,嘲笑/赝品/ testdoubles是你的敌人。你应该恨他们,并避免他们(编辑注:我不是说不使用它们,我只是说,只有当你有使用它们)。从范例来看,所有代码都是不好的代码,我们应该尽可能少地编写代码来完成任务。有大量的测试双打覆盖虚拟方法会使你的代码非常僵化。即使您的生产代码只在一个地方调用该方法,也会使更改方法签名变得非常痛苦,因为您的测试双打也会中断。这也使得后来清理垃圾并实际上注入依赖关系变得很痛苦(是的,我认为注入的东西是Objectively Better(tm))。

什么它归结为是基本上是:是的,这么做可以使你的代码的可测试性,但没有任何的好处,你通常得到测试。你wn't得到更好的设计,你就会有刚性码等

我不会真的指向任何的手指虽然,因为我喜欢我说的都用这个有时只是为了得到一个测试最多见,如果事情作品。它可以是一个“足够好”的临时解决方案,但我最终的答案是“如果你完全可以避免它(并且还有测试代码),可能不会。”

0

你会用你建议的方法来牺牲单一责任模式(SRP),并且可以说让你的代码难以阅读,理解和维护,在我们谈论之前就有一种气味存在试验。

如果您打算运行测试,但同时不遵循SOLID principles,那么您在哪里节省时间,可读性或灵活性? (我真的很想知道)。

什么DI原则让你做的是完全脱离你的依赖运行测试,这是你想要做什么。

面向对象的固体原理有很多很好的理由,但我总是愿意学习和错误,但我必须说,我可能已经被几年的固体代码蒙蔽了,并且成千上万的绿色单元测试确保我的项目。

+0

它很臭,但我会说重新构建我的整个代码库以适合测试工具是多臭多臭。我也不想让我的课变得更加难以作为回报,使它们更容易_test_,这似乎倒退了! –

+0

我听到你的声音。重新设计一个巨石永远不会在一次单程操作中完成。但是,没有任何东西可以阻止你垂直进行管道。记住SOLID原则是为了让代码更易于阅读和理解。您可能认为让这些类对其他类有依赖关系会更方便,但从长远来看,它会在后面咬你。如果您的NewSomething类需要更改,那么您将被迫在使用它的任何地方执行该更改。那时你不再有气味,但是恶臭恶臭:) –

相关问题