是否可以重用模拟?

时间:2018-08-07 12:07:01

标签: java mocking mockito

我有一个服务ISOLanguageService,其方法为getDefaultLanguage();

我想以此方式在一个类ISOLanguageServiceMock中模拟此服务:

public class ISOLanguageServiceMock {

    @Mock
    private ISOLanguageService isoLanguageService;

    public ISOLanguageServiceMock() {

        MockitoAnnotations.initMocks(this);

        ISOLanguage isoLanguage = new ISOLanguage();
        isoLanguage.setLanguageCode("EN");
        when(isoLanguageService.getDefaultLanguage()).thenReturn(isoLanguage);
    }

然后我还有另一个服务UserService,它在其中一个方法中使用了此服务isoLanguageService。

public void doSomtthing() {
   return isoLanguageService.getDefaultLanguage()
}

我想测试UserService,但是我想以某种方式重用模拟ISOLanguageServiceMock,因为它将在许多其他服务中使用。

我想要这样的东西

@RunWith(PowerMockRunner.class)
public class UserServiceTest {

    private ISOLanguageServiceMock languageMock = new ISOLanguageServiceMock();

    @InjectMocks
    private UserService userService;

    public void setUp() {
       MockitoAnnotations.init(this) 

    }

    public void testDoSomething() {

        userService.doDomething();
    }

}

我想将isoLanguageService的模拟注入到userService中,但这不是...

反正有重用模拟吗??我是否必须在每个测试类中编写isoLanguageService的模型??

1 个答案:

答案 0 :(得分:0)

您不能以这种方式重复使用模拟。您需要将@Mock实例放入测试用例,并在其中使用它们。

含义:

@Mock
private ISOLanguageService isoLanguageService;

和用于您的UserServiceTest类的规范。

Mockito无法理解(或关心)您的ISOLanguageServiceMock类包含可以注入被测类的内容。 Mockito会寻找您在测试课程中拥有的模拟,然后注入这些模拟,别无其他!

关于重复使用方面:

  • 您可以通过子类化(具有具有该@Mock字段的基类)来做到这一点
  • 但是,在某种程度上,这是一种不好的做法。单元测试应尽可能独立。单元测试重复代码时,可以,因为您希望能够查看一个文件(您的测试用例)以了解发生了什么事情。

含义:(通常),单元测试中的代码复制不是那么关键。单元测试的目的是实现快速调试。

好吧,一些替代方法:

  • 您当然可以不使用@InjectMocks。在这种情况下,您的生产代码需要另一种方式让您自己注入模拟对象(setter或仅测试构造函数)。
  • 当您手动注入时,您当然可以注入想要的任何模拟对象,甚至包括来自另一个类的对象
  • 但是然后:不需要额外的类,只需在某个地方放一个static方法即可返回(预先配置的)模拟。