当文件存在且无法删除时,如何测试方法异常?
How test an method exception when the file exists and cannot be deleted?
我想测试这段代码抛出的异常:
private void delete(final File file, final String fileName) {
boolean deleted = file.delete();
if (deleted) {
log.info("File {} was deleted", fileName);
} else {
throw new RuntimeException("The file exists but could not be deleted");
}
}
我的第一个想法是创建一个在我的单元测试中无法删除的临时文件。当然,我想控制这种行为以在测试后删除该文件。但我认为这是不可能的,这是矛盾的。将文件设置为 "read only" 不适用于这种情况。
那么,有什么想法吗?
我可以创建一个新的 class 并传递删除文件和 return 布尔值的责任,这样我就可以模拟它并测试我的异常。但我想在执行此操作之前使用 Junit 和 Java 探索另一种可能性。
使用不同的文件并测试删除该文件。第二个文件的扩展名可以相同,但内容和位置可能不需要。
我认为创建临时文件或锁定文件是多余的,不需要。
文件无法删除的事实取决于托管该文件的文件系统的运行时条件。您不需要在单元测试中重现这些条件,并且除了在单元测试中重现这些条件外,并不能保证运行时使用的文件不可删除。所以我觉得单元测试不应该考虑这一点。
您可以简单地 mock/stub File.delete()
使其成为 return false
并断言 RuntimeException
被抛出:要断言的实际行为。
以 Mockito 为例:
@RunWith(MockitoJUnitRunner.class)
public class FileServiceTest {
@Test(expected = RuntimeException.class)
public void myMethodToTest() throws Exception {
File file = Mockito.mock(File.class);
Mockito.when(file.delete()).thenReturn(false);
FileService.delete(file, "test");
}
}
编写单元测试时使用模拟对象。
获取 Mockito 并创建文件输入参数的模拟。
然后根据所需的测试结果将 delete
方法的 return 值设置为 return true 或 false。
一般来说我会做以下事情:
@RunWith(MockitoJUnitRunner.class)
public class FileServiceTest {
@Mock
private File file;
@Test
public void myMethodToTest() {
doReturn(false).when(file).delete();
try{
FileService.delete(file, "test");
fail("this test should throws an exception.")
} catch (RuntimeException e) {
assertEquals("The file exists but could not be deleted", e.getMessage());
}
}
}
在此示例中,如果未抛出任何异常,则测试失败;如果遇到 RuntimeException,则验证该异常是否是您抛出的异常。
我想测试这段代码抛出的异常:
private void delete(final File file, final String fileName) {
boolean deleted = file.delete();
if (deleted) {
log.info("File {} was deleted", fileName);
} else {
throw new RuntimeException("The file exists but could not be deleted");
}
}
我的第一个想法是创建一个在我的单元测试中无法删除的临时文件。当然,我想控制这种行为以在测试后删除该文件。但我认为这是不可能的,这是矛盾的。将文件设置为 "read only" 不适用于这种情况。
那么,有什么想法吗?
我可以创建一个新的 class 并传递删除文件和 return 布尔值的责任,这样我就可以模拟它并测试我的异常。但我想在执行此操作之前使用 Junit 和 Java 探索另一种可能性。
使用不同的文件并测试删除该文件。第二个文件的扩展名可以相同,但内容和位置可能不需要。
我认为创建临时文件或锁定文件是多余的,不需要。
文件无法删除的事实取决于托管该文件的文件系统的运行时条件。您不需要在单元测试中重现这些条件,并且除了在单元测试中重现这些条件外,并不能保证运行时使用的文件不可删除。所以我觉得单元测试不应该考虑这一点。
您可以简单地 mock/stub File.delete()
使其成为 return false
并断言 RuntimeException
被抛出:要断言的实际行为。
以 Mockito 为例:
@RunWith(MockitoJUnitRunner.class)
public class FileServiceTest {
@Test(expected = RuntimeException.class)
public void myMethodToTest() throws Exception {
File file = Mockito.mock(File.class);
Mockito.when(file.delete()).thenReturn(false);
FileService.delete(file, "test");
}
}
编写单元测试时使用模拟对象。
获取 Mockito 并创建文件输入参数的模拟。
然后根据所需的测试结果将 delete
方法的 return 值设置为 return true 或 false。
一般来说我会做以下事情:
@RunWith(MockitoJUnitRunner.class)
public class FileServiceTest {
@Mock
private File file;
@Test
public void myMethodToTest() {
doReturn(false).when(file).delete();
try{
FileService.delete(file, "test");
fail("this test should throws an exception.")
} catch (RuntimeException e) {
assertEquals("The file exists but could not be deleted", e.getMessage());
}
}
}
在此示例中,如果未抛出任何异常,则测试失败;如果遇到 RuntimeException,则验证该异常是否是您抛出的异常。