使用Mockito模拟java.nio.file.Files静态方法

使用Mockito模拟java.nio.file.Files静态方法,java,unit-testing,mockito,Java,Unit Testing,Mockito,我试图理解如何模拟静态方法,特别是从static Files.class 基本上,只要这一行执行: Files.newInputStream(this.getPathObj(), StandardOpenOption.READ); 我希望它只返回一个作为InputStream实例的对象 这是我试图模仿的静态方法的类 public class JavaFileInput{ private Path path; public JavaFileInput(Path path){ thi

我试图理解如何模拟静态方法,特别是从static Files.class

基本上,只要这一行执行:

 Files.newInputStream(this.getPathObj(), StandardOpenOption.READ);
我希望它只返回一个作为InputStream实例的对象

这是我试图模仿的静态方法的类

public class JavaFileInput{

private Path path;

public JavaFileInput(Path path){
    this.path = path;
}

public InputStream getInputStream() throws IOException {
    return Files.newInputStream(this.getPathObj(), StandardOpenOption.READ);
}

public Path getPathObj() {
    return this.path;
}

}
这是一些“psuedo-ish”单元测试代码,显然不起作用,但我希望它描述了我试图实现的想法

@Mock(name="path")
private Path mockedPath = Mockito.mock(Path.class);

@InjectMocks
private JavaFileInput javaFile_MockedPath;

@Before
public void testSetup(){
  javaFile_MockedPath = new JavaFileInput(mockedPath);
  MockitoAnnotations.initMocks(this);
}

@Test
public void getNewInputStreamTest(){
    //Setup
    Mockito.when(Files.newInputStream(mockedPathObj, StandardOpenOption.Read)).thenReturn(new InputStream());

    //Test
    InputStream outputValue = javaFile_MockedPath.getInputStream();

    //Validate
    assertTrue(outputValue instanceof InputStream);

}
这有什么意义吗?有人做过类似的事情吗?任何帮助都将不胜感激


谢谢你的时间

使用标准Mockito,您无法模拟静态方法——我想问问您这样做的原因

通过模拟
newInputStream
方法,您想要测试什么?您只是在创建一个重言式——您的方法返回您告诉它要返回的内容。InputStream的实例也是一种重言式


模拟
JavaFileInput
来测试依赖于它的另一个类会更有意义(可能通过使用带有样本数据的
ByteArrayInputStream

我不清楚
JavaFileInput
提供了什么值。但是,要测试静态方法,您可以查看。

我遇到了相同的问题:我有(自己的)代码,可以使用nio.file修改符号链接

为了在不必准备和访问文件系统的情况下测试代码,我必须围绕这些函数编写自己的可模仿包装器类


不太好,但是NiO JSR没有通过定义官方接口和提供非静态(=可注射)的方式来访问<代码>文件< /代码>来考虑这个用例。Mockito早在这之前就已经知道了。

您也可以使用在内存中工作的NIO2实现,而不是使用Mockito或PowerMock:

虽然这不能解决所有问题(或者说,它不能回答您模拟静态方法的尝试),也不能允许您创建有缺陷的
InputStream
(例如,读取N字节时会返回错误的输入流),但这可能适合您的用例

你也会问你的案例是否有意义:

//Setup
Mockito.when(Files.newInputStream(mockedPathObj, StandardOpenOption.Read)).thenReturn(new InputStream());

//Test
InputStream outputValue = javaFile_MockedPath.getInputStream();

//Validate
assertTrue(outputValue instanceof InputStream);
您正在测试
outputValue
确实是
InputStream
的一个实例,编译器已经为您完成了这项工作:
outputValue
已经是
InputStream
的一个实例,因此,断言它是
InputStream
的实例将永远不会失败,并且您的测试不会检查您想要检查的内容

您最好使用模拟而不是新的InputStream来测试
outputValue
是否与返回的实例完全相同,例如:

InputStream is = mock(InputStream.class);
Mockito.when(Files.newInputStream(mockedPathObj, StandardOpenOption.Read)).thenReturn(is);
InputStream outputValue = javaFile_MockedPath.getInputStream();
assertTrue(outputValue == is);

汤姆G-感谢您的及时回复!我想我只是想测试以确保getInputStream()返回一个InputStream实例,仅此而已。我应该测试其他东西吗?实际上,我想模拟Files.class中的一些静态方法,例如Files.exists()和Files.isDirectory()等。我只是希望在尝试其他方法之前弄清楚如何处理此测试。您可能想看看PowerMock.Romski-感谢您的回复。我会考虑尝试一下PowerMock。我在网上看到很多其他东西也推荐这个工具。