无法使用 mockito 测试继承方法

Unable to test with mockito for inheritance method

提问人:Mohd Abdul Azeem 提问时间:11/17/2023 更新时间:11/18/2023 访问量:37

问:

我有以下代码

class A {
    public int someMethod(int someParameters....) {
        ........// some implementation 
    }
}

class B extends A {
    public int someMethodFromB(int someParameters....) {
        ........// some implementation 
        return someMethod(someParameters....);
    }
}

我正在为 someMethodFromB 的类 B 编写测试,我想模拟我们返回值的 someMethod。当 B 扩展 A 时,我如何测试代码。

我尝试了以下 2 种方法,但没有成功

@Test
public void testSomeMethodFromB() throws Exception {
      ContextData contextData = mock(ContextData.class);

      SomeObject obj = mock(SomeObject.class);

      B b = spy(new B());

      doReturn(obj).when(b).someMethod(obj, contextData, false);

      Assert.assertNotNull(b.someMethodFromB(someAnotherObj, contextData, Optional.of("someString")));

    }

还有这个

@Mock
private A a;

@InjectMock
private B b;

@Before
public void setUp() {
   MockitoAnnotations.initMocks(this);
}

@Test
public void testSomeMethodFromB() throws Exception {
     ContextData contextData = mock(ContextData.class);

     SomeObject obj = mock(SomeObject.class);

     when(a.someMethod(obj, contextData, false)).thenReturn(obj);

     b.someMethodFromB(someAnotherObj, contextData, Optional.of("someString"));

    }
java spring mocking mockito jmockit

评论

1赞 Andrew S 11/17/2023
did not work out 是什么意思?基于方法参数类型的不匹配,这甚至会编译吗?
0赞 scigs 11/17/2023
或者 B 需要扩展 A 吗?B 可以使用组合并拥有 A 的成员吗?
0赞 knittl 11/17/2023
所以你在嘲笑你正在测试的对象?这种测试的期望是什么?
0赞 Dyjah 11/18/2023
B 类IS_A A 类,所以 B 类是 B 类的方法,它是继承的,所以你试图模拟被测试类的方法,这很奇怪。就像@scigs建议的那样,也许你应该换成构图。someMethod

答:

0赞 NapoleonDynamite 11/17/2023 #1

可能是我,但这个:

@Test
public void testSomeMethodFromB() throws Exception {
     ContextData contextData = mock(ContextData.class);

     SomeObject obj = mock(SomeObject.class);

     when(a.someMethod(obj, contextData, false)).thenReturn(obj);

     b.someMethodFromB(someAnotherObj, contextData, Optional.of("someString"));

    }

对我来说没有意义,什么是 SomeObject.class 和 SomeAnotherObj?SomeAnotherObj 作为参数传递,但从未定义? 你嘲笑SomeObject.class,但从不提及它,它只是你需要测试的东西,与问题无关吗? 我认为你可以做这样的事情:

public class BTest {

    @Mock
    private A a;
    @InjectMocks
    private B b; 

    @Test
    public void testSomeMethodFromB() {

        when(a.someMethod(something)).thenReturn(something);


        int result = b.someMethodFromB(something);

        Assert.assertEquals(expected, result);
    }

再说一次,也许我弄错了,这是漫长的一天工作,但我不太明白这些例子 无论如何,祝你好运!

0赞 Dyjah 11/18/2023 #2

我尝试了您正在尝试执行的操作的简化版本,并且它起作用了:

public class A {

    public int someMethod(int value) {
        return 2 * value;
    }
}
class B extends A {
  public int someMethodFromB(int value) {
    return someMethod(value);
  }
}
class BTest {

  @Test
   void myTest() {
     B spyB = spy(new B());
    
     doReturn(5).when(spyB).someMethod(8);

     assertEquals(5, spyB.someMethodFromB(8));
  }
}

所以我的猜测是,您在测试中传递到的参数与代码在调用它时接收的参数并不完全相同。someMethod

例如,如果我将参数更改为 ,则测试将失败,因为当代码运行时,它接收的值而不是 ,因此间谍不适用:someMethod686

  @Test
   void myTest() {
    B spyB = Mockito.spy(new B());

    Mockito.doReturn(5).when(spyB).someMethod(6);

    assertEquals(5, spyB.someMethodFromB(8));
  }

调试测试并检查何时调用哪些参数,以确保它们是您在调用时在测试中传递的参数。someMethoddoReturn...