如何从Junit模拟内部方法的调用

时间:2016-05-08 00:46:34

标签: java junit mocking mockito

我有MyClass,我正在为每个方法(Method1Test)做一个测试类

public class MyClass {
    public int method1(){
        int a = method2();
        return a;
    }
    public int method2(){
        return 0;
    }
}

@RunWith(MockitoJUnitRunner.class)
public class Method1Test {
    @InjectMocks
    private MyClass myClass = new MyClass();
    @Before
    public void setup(){}
    @Test
    public void test01(){
        Mockito.when(myClass.method2()).thenReturn(25);
        int a = myClass.method1();
        assertTrue("We did it!!!",a==25);
    }
}

问题是我无法模拟对method2的调用以使其返回不同的值。 Mockito的句子不起作用。

非常感谢^ _ ^

4 个答案:

答案 0 :(得分:1)

您必须通过重新定义间谍的method2()

的行为来在被测试类上创建一个间谍并部分模仿它
import static org.junit.Assert.assertEquals;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.when;


public class Method1Test {

  private MyClass myClass = new MyClass();

  @Test
  public void test01(){
    //given
    MyClass spy = spy(myClass); //create a spy for class-under-test
    when(spy.method2()).thenReturn(25); //partially override behavior of the spy
    //when
    int a = spy.method1(); //make the call to method1 of the _spy_!
    //then
    assertEquals(25, a);
  }
}

除此之外,你不需要Mockito Runner和@InjectMocks进行测试,因为你没有在课堂上注入@Mock注释的模拟-test。

此外,只有当断言条件 NOT 满足时,才会显示assertTrue语句中的消息。所以它应该至少"我们失败了!!!" ;)

答案 1 :(得分:0)

最后,我找到了一个横向解决方案而没有创建一个新类(我还没能做到,因为它在实际项目中是禁止的)。我已经在测试中覆盖了这个方法。

解决方案是

public class MyClass {
    public int method1(){
        int a=0;
        a=method2();
        return a;
    }
    public int method2(){
        return 1;
    }
}

@RunWith(MockitoJUnitRunner.class)
public class Method1Test {
    @InjectMocks
    private MyClass myClass = new MyClass(){
        public int method2(){
            return 25;
        }
    };
    @Before
    public void setup(){}
    @Test
    public void test001(){
        Mockito.when(myClass.method2()).thenReturn(25);
        int a = myClass.method1();
        assertTrue("We did it!!!",a==25);
    }
}

答案 2 :(得分:0)

我使用下面的代码尝试了该解决方案,但没有通过。

Mockito.when(myClass.method2()).thenReturn(25);

然后,我尝试了不同的方法,而不是上面的代码段,并且测试成功通过。看看:

Mockito.doReturn(25).when(myClass).method2();

为了模拟测试(可能是内部方法),必须使用doReturn()方法。

对于任何方法,都可以使用when()代替doThrow(),doAnswer(),doNothing(),doReturn()和doCallRealMethod()。当你

  • 无效的方法
  • 间谍对象的存根方法(见下文)
  • 多次重复使用同一方法,以在测试过程中更改模拟的行为。

,但是您可能更喜欢使用这些方法来代替 使用when(),用于您的所有存根调用。

更多信息,请点击此处https://javadoc.io/doc/org.mockito/mockito-core/latest/org/mockito/Mockito.html#12

答案 3 :(得分:0)

这里,我们需要使用Mockito.spy()来模拟我们正在测试的同一类,而不是使用模拟(class)。然后,我们可以模拟所需的方法,如下所示。

@Test

  public void method1Test() { 

  MyClass myClass = new MyClass();

  MyClass myClass1 = Mockito.spy(myClass);

  Mockito.doReturn(1).when(myClass1).method2();

  Assert.assertEquals(1, myClass1.method1());

     }
 }