【问题标题】:Is this code testable?这段代码可以测试吗?
【发布时间】:2018-04-30 22:34:16
【问题描述】:

假设我有一个构造函数:

public Something(A a) {
    this.a = a;
    this.b = a.someLogicMethod();
    this.c = b.someLogicMethod();
}
@Autowired
private Class d;

此代码可测试吗?如果不是,我应该更改什么以使其可测试并保持 b 的初始化通过对象 a 的方法,我将其作为我的类的构造函数的参数。

我想将 classB 的对象(我在测试类中创建的)传递给 Something 类,问题是应该模拟Something 并且模拟对象 a,所以我不能改变 a 的行为使用 when&thenReturn 因此,当调用 a.someLogicMethod 时,它将返回我在测试类中创建的 classB 对象,因为当模拟Something 时,将在调用 a.someLogicMethod() 并且 b 之后调用 when&thenReturn 逻辑放。 我也不能有 b 对象的设置器,因为它应该用 a.someLogicMethod() 初始化。 我需要模拟的原因是因为我希望对象 d 将被模拟。

谢谢。

【问题讨论】:

  • 是的,它是可测试的。尝试测试它怎么样?这不是回答你的问题吗?或者至少让它对你更有用?
  • @JBNizet 实际上我做到了,问题是我想要模拟 a 对象,这对 b 来说是个问题。你怎么看?
  • 我认为模拟 A 对象没有任何问题。去做吧,如果你有具体的问题,用相关的代码解释一下。
  • 我注意到您的问题仍然是“开放的”:您没有接受答案。请查看并决定是否要accept 回答。或者让我知道我是否可以做些什么来增强我的输入以使其被接受。接受有助于未来的读者确定问题是否得到解决,并对花时间回答你的人表示感谢。
  • @GhostCat ,如果可以的话,我会删除这个问题,因为我不记得我想做什么以及到底是什么问题。当我现在阅读这个问题时,我不明白自己的问题,因为如果我想使用“某事”类作为 Mock 来测试另一个类,我不应该关心 a、b、c、d,因为 a、b ,c,d 可能是“Something”类的方法中使用的字段,如果我模拟这个类,那么我可以存根每个方法,所以我不需要这些字段。

标签: unit-testing testing mockito tdd


【解决方案1】:

您将A 注入Something,所以只需模拟A,然后在调用someLogicMethod() 时让A 返回模拟的B

例如:

A mockA = Mockito.mock(A.class);
B mockB = Mockito.mock(B.class);
Mockito.when(a.someLogicMethod()).thenReturn(mockB);

Something something = new Something(mockA);

然后您可以在测试用例中调用 something,这样您就可以通过使用 when/then 或 when/throw 或 doThrow/when 等设置对 mockB 的期望来控制 something 的行为。

【讨论】:

  • 这就是我想要的,但在那种情况下,你用 new 关键字初始化了一些东西,我也想模拟一些东西,所以这就是问题所在,我不能使用 when,然后返回,因为有些东西应该也被嘲笑。
  • 如果 Something 要被嘲笑,那么你就不会关心嘲笑 AB,因为他们可能所做的任何事情都会被设定的期望所覆盖在您的mockSomething 上。在这个阶段,我真的认为最好听从@JBNizet 的建议,并为我们提供一个clear statement 你正在尝试做的事情,否则我们只能猜测。
  • 对不起,T.S.,但这完全没有意义。如果你想测试Something,那么你不能模拟Something,因为那时你只会测试Something的模拟,这没什么用——我们通常同意Mockito工作得很好,谢谢。如果您想测试另一个具有Something 依赖项的类,您只需要模拟Something。但如果是这种情况,那么您没有向我们展示要测试的实际代码,也没有向我们展示真正的问题。一般来说,模拟 Something 应该没有问题,因为 Mockito 应该能够很好地处理该构造函数。
  • @FlorianSchaetz 对不起,我编辑了我的问题并试图更好地解释问题,无论如何,我认为我的问题太复杂了。
  • @T.S 我怀疑这是可以解决的,但您的问题仍然不够清楚。与其尝试用文字解释它,为什么不发布一些代码呢?也许您可以提供您的实际测试用例?
【解决方案2】:

这里有两个方面:

  • 你的构造函数是测试友好的,因为你传递一个A的实例给它。因此,正如另一个答案很好地概述的那样,您应该能够将 mocked 实例传递给该构造函数 - 从而 you 可以完全控制以下方法调用所发生的事情.

  • 关于@autowired:这里的答案是转而使用特殊的spring JUnit runner(有关所有荣耀的详细信息,请参见here

【讨论】:

  • 我尝试了 MockBean 注释,问题是这使我的上下文变脏了,所以我的测试在特定类中通过但其他测试失败,我尝试使用 DirtyContext 注释,但这似乎没有工作。
猜你喜欢
  • 1970-01-01
  • 2011-03-12
  • 2019-11-03
  • 2023-03-31
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多