为了了解Mockito注释的工作原理,我浏览了一些博客。

但是我面临着一个疑问,何时去手动实例化带有@InjectMocks注释的字段,即

@InjectMocks
A a = new A();

什么时候需要依靠MockitoAnnotations.initMocks()功能来执行相同的操作:
@InjectMocks
A a;

这是否取决于我们用来运行测试用例的JunitTestRunner还是取决于Mockito框架版本?

最佳答案

这取决于您是否使用(声明)跑步者。

如果使用跑步者,则无需自己调用MockitoAnnotations.initMocks()-跑步者会为您调用。

通常我们去跑步。但是,当您想使用其他跑步者时(例如Spring的),您可以自己调用.initMocks()

为了清楚起见,MockitoAnnotations.initMocks(this)将:

  • 实例化带有@InjectMocks的字段
  • 为每个用@Mock注释的字段创建一个模拟版本
  • @Mock变量的字段中注入@InjectMocks(或调用其构造函数或使用其setter-取决于您使用的依赖注入类型)

  • Mockito运行器,initMocks和规则代码示例

    下面的三个代码示例应等效。

    与亚军:

    第一个代码段使用了运行器,从而无需调用initMocks()
    @RunWith(MockitoJUnitRunner.class)
    public class MyClassTest {
    
        @Mock private MyDependency myDependency;
        @InjectMocks private MyClass myClass;
    
        @Test
        public void myClass_should_get_stuff_from_dependency() {
            when(myDependency.getStuff()).thenReturn("stuff!");
    
            assertThat(myClass.getDependencyStuff(), is("stuff!"));
        }
    }
    

    没有跑步者+手动调用.initMocks():

    另一个不使用运行器,因此需要setUp()方法来调用我们的initMocks()朋友。
    // notice there is no runner
    public class MyClassTest {
    
        @Mock private MyDependency myDependency;
        @InjectMocks private MyClass myClass;
    
        // but now you have to call initMocks() yourself
        @Before
        public void setUp() throws Exception {
              MockitoAnnotations.initMocks(this);
        }
    
        @Test
        public void myClass_should_get_stuff_from_dependency() {
            when(myDependency.getStuff()).thenReturn("stuff!");
    
            assertThat(myClass.getDependencyStuff(), is("stuff!"));
        }
    }
    

    没有Runner或人工调用,请使用@Rule:

    最后,正如comments (thanks @StefanBirkner)中指出的那样,从1.10.17版本开始,还可能使用名为JUnit @Rule MockitoRule :
    public class MyClassTest {
    
        @Rule
        public MockitoRule rule = MockitoJUnit.rule();
    
        @Mock private MyDependency myDependency;
        @InjectMocks private MyClass myClass;
    
        @Test
        public void myClass_should_get_stuff_from_dependency() {
            when(myDependency.getStuff()).thenReturn("stuff!");
    
            assertThat(myClass.getDependencyStuff(), is("stuff!"));
        }
    }
    

    07-28 10:18