这是一个非常常见的测试问题,为此,我遇到的最常见的解决方案是使用依赖注入将数据源与使用数据的代码分开.这不仅支持良好的测试,而且在使用外部数据源时通常是一个好的策略(良好的职责分工,隔离集成点,促进代码重用是其中的一些原因).
您需要进行的更改如下:
>对于每个数据源,创建一个接口来定义如何访问该数据源中的数据,然后分解出将数据返回到实现此目标的单独类中的代码.
>依赖关系将数据源注入到包含“ long”函数的类中.
>对于单元测试,请为每个数据源注入模拟实现.
这是一些显示示例的代码示例-请注意,此代码仅是模式的说明,您将需要一些更合理的名称.值得研究这种模式,并更多地了解依赖注入和应用程序.嘲讽-单元测试军械库中最强大的武器中的两种.
数据源
public interface DataSourceOne {
public Data getData();
}
public class DataSourceOneImpl implements DataSourceOne {
public Data getData() {
...
return data;
}
}
public interface DataSourceTwo {
public Data getData();
}
public class DataSourceTwoImpl implements DataSourceTwo {
public Data getData() {
...
return data;
}
}
长方法类
public class ClassWithLongMethod {
private DataSourceOne dataSourceOne;
private DataSourceTwo dataSourceTwo;
public ClassWithLongMethod(DataSourceOne dataSourceOne,
DataSourceTwo dataSourceTwo) {
this.dataSourceOne = dataSourceOne;
this.dataSourceTwo = dataSourceTwo;
}
public Result longMethod() {
someData = dataSourceOne.getData();
someMoreData = dataSourceTwo.getData();
...
return result;
}
}
单元测试
import org.junit.Test;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;
public class ClassWithLongMethodTest {
@Test
public void testLongMethod() {
// Create mocked data sources which return the data required by your test
DataSourceOne dataSourceOne = mock(DataSourceOne.class);
when(dataSourceOne.getData()).thenReturn(...);
DataSourceTwo dataSourceTwo = mock(DataSourceTwo.class);
when(dataSourceTwo.getData()).thenReturn(...);
// Create the object under test using the mocked data sources
ClassWithLongMethod sut = new ClassWithLongMethod(dataSourceOne,
dataSourceTwo);
// Now you can unit test the long method in isolation from it's dependencies
Result result = sut.longMethod();
// Assertions on result
...
}
}
请原谅(并纠正)任何语法错误,这些天我写的Java很少.