我有一个类如下的课程;
class ClassA {
private static File myDir;
// myDir is created at some stage
private static String findFile(final String fileName) {
for (final String actualBackupFileName : myDir.list()) {
if (actualBackupFileName.startsWith(removeExtensionFrom(backupFile))) {
return actualBackupFileName;
}
}
}
}
所以,基本上,我想通过模拟File类来测试这个类,这样当调用list()时,它会返回我在我的测试类中定义的字符串列表。
我已经得到了以下内容,但它现在没有工作,可能有一些明显我做错了 - 我是JMockit的新手 - 非常感谢任何帮助!
@Mocked("list") File myDir;
@Test
public void testClassA() {
final String[] files = {"file1-bla.txt"};
new NonStrictExpectations() {{
new File(anyString).list();
returns(files);
}};
String returnedFileName = Deencapsulation.invoke(ClassA.class, "findFile","file1.txt");
// assert returnedFileName is equal to "file1-bla.txt"
}
运行上面的测试时,我得到了ClassA中myDir字段的NullPointerException - 所以看起来它没有被正确模拟?
答案 0 :(得分:11)
您可以使用Deencapsulation类中的setField方法。请注意以下示例:
Deencapsulation.setField(ClassA, "File", your_desired_value);
答案 1 :(得分:10)
JMockit(或任何其他模拟工具)不会模拟字段或变量,它会模拟类型(类,接口等),其中这些类型的实例存储在被测试的代码中不相关。
ClassA
的示例测试:
@Test
public void testClassA(@Mocked File myDir)
{
new Expectations() {{ myDir.list(); result = "file1-bla.txt"; }};
String returnedFileName = new ClassA().publicMethodThatCallsFindFile("file1.txt");
assertEquals("file1-bla.txt", returnedFileName);
}
以上应该有效。请注意,直接测试private
方法(或访问private
字段)被认为是不好的做法,所以我在这里避免使用它。此外,最好避免模仿File
类。相反,只测试您的public
方法,并使用实际文件而不是模拟文件系统。
答案 2 :(得分:0)
试试这个:
new Expectations {{
invoke(File.class, "list", null, null);
returns(files);
}}