最近我一直在督促自己学习越来越多的单元测试技术,但遇到了一些我无法弄清楚的事情——即如何开始。我正在尝试使用非常非常简单的单一方法对工厂进行单元测试。我已经使用示例名称简化了它,为您提供帮助。
public class HandlerFactory extends SecondHandlerFactory
{
//To hold singleton of this class.
private static SecondHandler factoryInstance = null;
private HandlerFactory() throws HandlerCreationException
{
super();
}
protected InterfaceExample createSomethingByThisKey(String key) throws HandlerCreationException
{
InterfaceExample myNewHandler = null;
if (StringFunctions.isEqualIgnoreCase(key, "Phone"))
{
myNewHandler = new PhoneHandler();
}
}
}
我在弄清楚如何设置此测试甚至落入 createSomethingByKey() 时遇到了很大的麻烦。即使这样,我什至不知道如何正确执行我的assertEquals()方法。
现在,我已经设置了一些东西来执行 createInstance();但对我来说,如何陷入这种困境似乎没有任何意义。添加的变量和接口(interface)让我很困惑。它看起来测试起来很简单,而且是一个非常非常短的类(class) - 但不接触这个(Java 甚至不是我的第一语言)对我来说是一堵难以逾越的墙)。
关于如何设置标准 JUnit 或 Mockito (实际上并不重要)有什么帮助吗?此外, protected 事实让我更加无能为力,因为正确的标准是在另一个包中进行单元测试。
最佳答案
老实说,我不确定你的困难是什么。我只能猜2:
- 您不知道要在这样的工厂测试什么。
- 您在测试 protected 方法时遇到问题
对于1,其实并不难,只要假设你正在测试的方法是公开的:
public class HandlerFactory extends SecondHandlerFactory
{
public InterfaceExample createSomethingByThisKey(String key) throws HandlerCreationException
{
InterfaceExample myNewHandler = null;
if (StringFunctions.isEqualIgnoreCase(key, "Phone"))
{
myNewHandler = new PhoneHandler();
}
}
}
此方法中的逻辑只是根据键创建一个处理程序实例。因此,您的测试应该旨在查看是否根据您的 key 创建了正确类型的处理程序。因此测试应该类似于:
@Test
testCreateSomethingByThisKeyGivenKeyForPhoneKey {
InterfaceExample result = handelerFactory.createSomethingByThisKey("Phone");
assertTrue("result is a PhoneHandler", result instanceof PhoneHandler);
}
@Test
testCreateSomethingByThisKeyGivenKeyForUnknownKey {
InterfaceExample result = handelerFactory.createSomethingByThisKey("NONEXIST");
assertNull("result", result);
}
对于问题 2(限制访问 protected 方法),您通常有 2 个选择: 我们通常将测试与被测系统 (SUT) 放在同一个包中,因此您应该能够调用 protected 方法。
您还可以选择创建一个特定于测试的子类 (TSS),它公开直接委托(delegate)给 SUT 中 protected 方法的方法(或覆盖以放松该方法的可见性),并针对 TSS 执行测试。当然,您应该确保您的 SUT 可以扩展。它可能看起来像这样
public class Sut {
protected Foo methodToTest(Param param) {
//....
}
}
创建一个这样的 TSS:
public class SutTss extends Sut {
@Override
public Foo methodToTest(Param param) { // visibility loosen
return super.methodToTest(param);
}
}
然后你可以自由地测试该 protected 方法(我相信在Java中很少使用它,因为我们总是可以通过将测试放在与SUT相同的包下来调用 protected 方法)
关于java - 使用接口(interface)对工厂进行单元测试很困难,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12311082/