如何对BufferedReader的IOException异常处理逻辑进行单元测试?
测试BufferedReader抛出IOException的可行方案
要触发readCSV方法里的IOException处理逻辑,核心是让传入的InputStreamReader在读取操作时抛出异常,以下是几种实用方案:
方案1:自定义抛出异常的InputStreamReader子类
手动实现一个继承自InputStreamReader的类,重写读取方法并抛出异常:
public class ExceptionThrowingInputStreamReader extends InputStreamReader { public ExceptionThrowingInputStreamReader() { // 传入空流作为父类构造参数 super(new ByteArrayInputStream(new byte[0])); } @Override public int read(char[] cbuf, int off, int len) throws IOException { // 读取时直接抛出IOException throw new IOException("模拟文件读取失败"); } }
在测试用例中传入这个自定义类的实例:
@Test void testReadCSVHandlesIOException() { YourClass yourClass = new YourClass(); List<String> result = yourClass.readCSV(new ExceptionThrowingInputStreamReader()); // 验证返回列表为空(异常发生时未读取到任何行) assertTrue(result.isEmpty()); // 验证错误日志是否输出(可通过日志测试工具,如SLF4J的TestLogger或Logback的TestAppender) // 示例:假设日志对象已通过Mockito注入 verify(yourClass.getLog()).error("Something went wrong while reading file"); }
方案2:用Mockito模拟InputStreamReader
借助Mockito框架模拟InputStreamReader,指定其读取方法抛出异常:
import org.junit.jupiter.api.Test; import org.mockito.Mockito; import java.io.IOException; import java.io.InputStreamReader; import java.util.List; import static org.junit.jupiter.api.Assertions.assertTrue; import static org.mockito.ArgumentMatchers.*; import static org.mockito.Mockito.doThrow; import static org.mockito.Mockito.mock; @Test void testReadCSVWithMockedIOException() throws IOException { // 模拟InputStreamReader实例 InputStreamReader mockedReader = mock(InputStreamReader.class); // 设定调用read方法时抛出IOException doThrow(new IOException("模拟读取异常")).when(mockedReader) .read(any(char[].class), anyInt(), anyInt()); YourClass yourClass = new YourClass(); List<String> result = yourClass.readCSV(mockedReader); // 验证结果 assertTrue(result.isEmpty()); // 验证日志输出 verify(yourClass.getLog()).error("Something went wrong while reading file"); }
注意:若日志对象是依赖注入的,需确保测试时正确注入Mock对象,以便验证日志调用逻辑。
补充说明
原代码使用了try-with-resources语法,无论是否抛出异常,BufferedReader都会被自动关闭,测试时无需额外处理资源释放逻辑。
内容的提问来源于stack exchange,提问作者LuXoR
相关产品推荐
相关产品推荐

