将Mock用于作为一类实例的字段

时间:2019-01-24 10:35:56

标签: java mocking mockito

我有一个课程:

public class Sender {
    private final SomeClass firstField;
    private final SomeClass secondField;
    private Sender(SomeClass firtsField, SomeClass secondField){
        this.firstField = firstField;
        this.secondField = secondField;
    }
}

@RunWith(MockitoJUnitRunner.class)
public class SenderTest{
    @Mock
    private firstField;
    @Mock
    private secondField;
}

一切看起来都不错,但是看起来它在两个字段或类似的字段中注入了相同的对象。当我试图在一个字段中使用when(...)。thenReturn()时,它会另外设置两个数据并进行比较。最奇怪的是,它可以在调试模式下正常工作。你能说什么?

2 个答案:

答案 0 :(得分:1)

在构造函数注入两个或多个相同类型的字段时,Mockito存在一些问题。但是,如果使用setter注入,它会完美地工作。

因此您可以像这样重构“ Sender”类:

public class SenderTest {

    private SomeClass firstField;
    private SomeClass secondField;

    private Sender sender;

    @Before
    public void setUp() {
        firstField = Mockito.mock(SomeClass.class);
        secondField = Mockito.mock(SomeClass.class);

        sender = new Sender(firstField, secondField);
    }

    @Test
    public void smokeTest() {

    }
}

请记住,如果class同时具有构造函数和设置方法,则Mockito将选择注入的构造方法,而完全忽略设置方法。

编辑:如果您出于某些原因确实需要使用构造函数,则始终可以手动模拟字段,而不必使用Mockito批注。 因此,在您的情况下,发件人将保持不变,而SenderTest将如下所示:

{{1}}

答案 1 :(得分:0)

这取决于SomeClass本身是什么。它是一个数据(POJO)对象,值得在测试中创建它们(也就是填充随机生成的值)。

如果是服务。它可能是体系结构问题的标志。为什么需要同一服务的两个副本?进行一些重构也许很有意义。