17

我在 .NET 方面有全面的背景,但最近一直在使用 Python 和 Ruby。我发现自己在思考如何最好地为 Ruby 中需要它们的对象提供依赖关系。

起初,我实际上并不认为 DI 和 IoC 框架需要与依赖项进行交互,因为动态语言(例如重新定义、mixins、存根等)的宽松性。然而,然后,我遇到了为什么动态语言不需要DI/IoC 框架的答案。提供的理由对我来说不太合适。我希望我能看到一个可以解决问题的例子。

我有点不同意的推荐建议:

原因 1:可以在运行时更改依赖类(想想测试)

为什么动态语言不需要 IOC 容器中,我们看到依赖类(非注入)X可以在测试中被存根或模拟。当然,但这需要我们知道我们System Under Test依赖于一个叫做X. 如果我们System Under Test突然依赖于N而不是X,我们现在必须记住要模拟N而不是X。使用 DI 的好处是我们永远不会意外地使用生产依赖项运行测试,因为我们总是会传入模拟依赖项。

原因二:子类化或者使用构造函数注入进行测试

在每个人最喜欢的关于 DI + Ruby、 LEGO、Play-Doh 和 Programming的所有东西的 goto 资源中,我们看到了一个将被测系统子类化以模拟依赖关系的示例。或者,我们可以使用构造函数注入。好的,所以B取决于A. 我们调用B.get_dependencywhich 提供B了一个A. 但是如果A取决于N哪个取决于X呢?我们必须调用get_dependency链中的每个连续对象吗?

原因3:依赖可以混入或者monkeypatched

Fabio 提到我们可以只使用 mixins/monkeypatch。所以X混入到N. 但问题是如果X取决于A哪个取决于B?我们是否只对链下的每个依赖项使用 mixins?我知道它是如何工作的,但它很快就会变得混乱和混乱。


旁注:许多用户说动态语言不需要 DI 框架。然而,Angular.JS 确实受益于实现了一个非常可靠的 DI 系统。Angular 是基于 JavaScript 构建的,这是一种动态语言。这种方法可以与 Ruby 或 Python 相媲美吗?

请记住,我并不是说我想将DI/IoC强制转换为 Ruby、Python 等。

4

1 回答 1

2

虽然许多人认为不需要 DI,但我同意你的观点,它确实非常需要;但有时它会与 Python 提供的其他技术混合使用。我建议你看看venusian,它可能有点冗长,但如果你来自 .NET,你会看到这种关系。一句话:venusian 允许你在不改变它们的行为的情况下注释你的方法。因此,您可以编写 venusian 装饰器,这样您的单元测试就不会受到影响。例如, Pyramid使用 venusian 来注释视图。

于 2012-12-17T16:57:32.047 回答