繁体   English   中英

不能模拟FileInputStream

[英]Can`t mock FileInputStream

我有

@Component
public class CodesConverterService {    
private final FileInputStreamFactory fileInputStreamFactory;

public CodesConverterService(FileInputStreamFactory fileInputStreamFactory, YamlFactory yamlFactory) {
    this.fileInputStreamFactory = fileInputStreamFactory;

}
@EventListener(ApplicationReadyEvent.class)
    public void loadMappingsFromSource() {
        try {
            FileInputStream f = fileInputStreamFactory.getStream("mappingFile");
        } catch (Exception e) {
            throw new CodesConverterException("Can`t load mappings from source");
        }
    }

我的FileInputStreamFactory:

@Component
public class FileInputStreamFactory {

    public FileInputStream getStream(final String file) throws FileNotFoundException {
        return new FileInputStream(file);
    }
}

我的测试

@RunWith(SpringRunner.class)
public class CodesConverterServiceTest {

    @InjectMocks
    private CodesConverterService codesConverterService;

    @Mock
    private FileInputStreamFactory fileInputStreamFactory;

    @Mock
    private FileInputStream fileInputStream;
    @Test
    public void whenLoadMappingsFromSource_GoodPath() throws FileNotFoundException {
        when(fileInputStreamFactory.getStream("mappingFile")).thenReturn(fileInputStream);

        this.codesConverterService.loadMappingsFromSource();
    }

为什么我的f总是为null? 我试过分配变化。 但它始终为空。 我已经为FileInputStream创建了工厂,因为我不想在测试中使用PowerMock模拟新FileInputStream上的创建。

我在下面的示例中重现了您的测试,该测试对我有用。
(已通过JUnit 4Mockito 3.0.02.28.2

我唯一更改的是Runner ,但根据您的评论,您已经这样做了。

我删除该示例中的注释作为当测试与执行他们应该是不相关的MockitoJUnitRunner和改变的返回类型loadMappingsFromSource容易地添加Assert.assertNotNull 我还用RuntimeException替换了CodesConverterException

这些更改均不会影响测试本身。

即使仅存在带有参数的构造函数,也可以正确创建FileInputStreammock

@RunWith(MockitoJUnitRunner.class)
public class CodesConverterServiceTest {

    class YamlFactory {
    }

    class FileInputStreamFactory {
        public FileInputStream getStream(final String file) throws FileNotFoundException {
            return new FileInputStream(file);
        }
    }

    static class CodesConverterService {    

        private final FileInputStreamFactory fileInputStreamFactory;

        public CodesConverterService(FileInputStreamFactory fileInputStreamFactory, YamlFactory yamlFactory) {
            this.fileInputStreamFactory = fileInputStreamFactory;
        }

        public FileInputStream loadMappingsFromSource() {
            try {
                return fileInputStreamFactory.getStream("mappingFile");
            } catch (Exception e) {
                throw new RuntimeException("Can`t load mappings from source");
            }
        }
    }

    @InjectMocks
    private CodesConverterService codesConverterService;

    @Mock
    private FileInputStreamFactory fileInputStreamFactory;

    @Mock
    private FileInputStream fileInputStream;

    @Test
    public void whenLoadMappingsFromSource_GoodPath() throws FileNotFoundException {

        Mockito.when(fileInputStreamFactory.getStream("mappingFile")).thenReturn(fileInputStream);
        Assert.assertNotNull(codesConverterService.loadMappingsFromSource());
    }
}

1)尝试以下代码:

        @Test
        public void itShouldReturnFileInputStream() {
            FileInputStreamFactory mockFileInputStreamFactory = mock(FileInputStreamFactory.class);
            FileInputStream  mockFileInputStream = mock(FileInputStream.class);
            Mockito.doReturn(mockFileInputStream).when(mockFileInputStreamFactory).getStream("fileName");
            CodesConverterService  codeConverterService = new CodesConverterService(mockFileInputStreamFactory);
            assertThatCode(() -> codeConverterService.codeConverterService()).doesNotThrowAnyException();
        }

我弄清楚我在使用@RunWith(SpringRunner.class)MockitoAnnotations.initMocks(this);是什么错误MockitoAnnotations.initMocks(this); 同时。 如果同时使用这两种方法,则将创建怪人,但工作方式不正确。 所以我只是删除了MockitoAnnotations.initMocks(this);

FileInputStream没有no-arg构造函数。 这就是Mockito无法实例化模拟的原因。

您可以尝试使其成为间谍,并相应地模拟所需的方法:

@Spy
private FileInputStream fileInputStreamSpy = new FileInputStream("dummy");

编辑

另外,您可以通过以下方式在测试方法中创建模拟:

FileInputStream fileInputStreamMock = 
   Mockito.mock(FileInputStream.class, withSetting().useConstructor("dummy"));

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM