我可以模拟方法内部的file.mkdirs()吗

mae*_*mae 0 java junit file mocking

这是我下面的旧代码。我不想创建一个实际的文件夹。相反,我想创建一个临时文件夹,测试执行结束后必须将其删除。

Public class MainClass() {
  public void m1() {
        m2();
  }

  private void m2() {
    File f=new File();
    f.mkrdirs()
  }
}
Run Code Online (Sandbox Code Playgroud)

这是我的TestClass

public class TestClass{
       @Rule
       public TemporaryFolder folder= new TemporaryFolder();

       public void testM1(){
            File fileSpy = mock(File.class);
            Mockito.doNothing().when(fileSpy.mkdir());

       }
}
Run Code Online (Sandbox Code Playgroud)

但不起作用。有任何线索吗?

Gho*_*ica 5

您的问题从这里开始:

File f=new File();
Run Code Online (Sandbox Code Playgroud)

您的生产代码对文件类调用new。在测试代​​码中,您可以执行以下操作:

File fileSpy = mock(File.class);
Run Code Online (Sandbox Code Playgroud)

那间谍与您的f实例有什么关系?答:一点也不。

在测试中声明间谍不会神奇地使您的生产代码使用它!因此,您必须确保当您的生产代码使用该f对象时... f应该是您的fileSpy

现在,您有以下选择:

  • 看看是否可以更改生产代码,以便以某种方式传递文件实例。通过将其作为参数,您实际上可以将某些东西传递给它,或者通过转到f类的某个字段,然后使用Mockito的@InjectMock批注
  • 如果您坚持使用生产代码,则Mockito不会这样做。然后,您需要PowerMock(ito)或JMockit。

通常,我建议人们坚持使用普通的Mockito,避免像瘟疫一样通过PowerMock(ito)嘲笑new()(甚至嘲笑静态调用)。

但是,测试遗留代码是您必须在“根本不测试”或“使用PowerMock(ito)测试”之间进行选择的一种情况。因此,如果您无法更改生产代码,那么唯一的选择就是模拟对new()的调用。请参阅此处以了解如何执行此操作。