Mockito间谍 - 当调用内部类方法而不是间谍对象中的间谍方法时

时间:2016-09-21 12:46:51

标签: java android mockito

我有内部类的课程如下:

public class ClassWithInnerObject {

  private final InnerObject innerObject;

  public ClassWithInnerObject() {
    innerObject = new InnerObject();
  }

  public void callInnerObjectMethod() {
    innerObject.outerFunc();
  }

  public void outerFunc() {
    innerFunc();
  }

  public void innerFunc() {
    Log.d("XXX", "innerFunc: called");
  }

  public class InnerObject {
    public void outerFunc() {
      innerFunc();
    }
  }
}

模拟测试看起来如下: 的build.gradle:

  androidTestCompile 'junit:junit:4.12'
  androidTestCompile 'org.mockito:mockito-core:1.10.19'

  androidTestCompile 'com.crittercism.dexmaker:dexmaker:1.4'
  androidTestCompile 'com.crittercism.dexmaker:dexmaker-mockito:1.4'
  androidTestCompile 'com.crittercism.dexmaker:dexmaker-dx:1.4'

测试:

@RunWith(AndroidJUnit4.class) public class SpyVerifyTest {

  @Test public void myInnerTestWorking() {
    ClassWithInnerObject p = new ClassWithInnerObject();
    ClassWithInnerObject spy = Mockito.spy(p);
    spy.outerFunc();
    verify(spy, times(1)).innerFunc();
  }


  @Test public void myInnerTestNotWorking() {
    ClassWithInnerObject p = new ClassWithInnerObject();
    ClassWithInnerObject spy = Mockito.spy(p);
    spy.callInnerObjectMethod();
    verify(spy, times(1)).innerFunc();
  }

}

第一项测试按预期工作。 第二个innerFunc永远不会被检测为“被调用”,虽然在日志中我看到它是。出了什么问题? :)

谢谢!

2 个答案:

答案 0 :(得分:7)

  

有什么问题?

嗯,这里的问题非常微妙,当你致电Mockito.spy(p)时,mockito在你的ClassWithInnerObject实例上创建了一些装饰器,允许监视所有方法调用你的实例。多亏了这一点,您可以检查给定方法被调用的次数但仅在装饰器上而不在您的实例上。在这里,当您使用内部类时,它会在innerFunc()的实例上调用ClassWithInnerObject而不是装饰器,因此Mockito innerFunc() 尚未被调用< /强>

答案 1 :(得分:0)

您可以使用“ClassWithInnerObject.this”来解决这个问题。在内部类。

public class InnerObject {
  public void outerFunc() {
    ClassWithInnerObject.this.innerFunc();
  }
}