public class FakeExcelSheet implements Sheet
{
private final Map<Integer, FakeExcelRow> fakeSheet = new HashMap<Integer, FakeExcelRow>();
@Override
public Row createRow(int rowNum)
{
Row row = new FakeExcelRow(rowNum, fakeSheet);
fakeSheet.put(rowNum, (FakeExcelRow)row);
return row;
}
@Override
public Row getRow(int rowNum)
{
if (fakeSheet.get(rowNum) != null)
{
return fakeSheet.get(rowNum);
}
else
{
return createRow(rowNum);
}
}
/**Other unimplemented methods of Apache POI class Sheet**/
}
public class FakeExcelRow implements Row
{
private int rowNum;
private Map<Integer, FakeExcelRow> sheet;
private List<Object> cellList = new LinkedList<Object>();
public FakeExcelRow(int rowNum , Map<Integer,FakeExcelRow> sheet)
{
this.rowNum = rowNum;
this.sheet = sheet;
}
@Override
public Cell createCell(int colNum)
{
return new FakeExcelCell(colNum, rowNum, sheet);
}
/**Other unimplemented methods of Apache POI class Row**/
}
public class FakeExcelCell implements Cell
{
private int colNum;
private int rowNum;
private Map<Integer, FakeExcelRow> sheet;
public FakeExcelCell(int colNum, int rowNum, Map<Integer, FakeExcelRow> sheet)
{
this.colNum = colNum;
this.rowNum = rowNum;
this.sheet = sheet;
}
public void setCellValue(String value)
{
if(sheet != null)
{
FakeExcelRow fakeExcelRow = sheet.get(rowNum);
List<Object> cellList = fakeExcelRow.getCellList();
cellList.add(value);
}
}
/**Other unimplemented methods of Apache POI class Cell**/
}
我必须测试我的类服务,它使用类ExcelWriter的受保护方法writeToCell,如下所示:
public class ServiceImpl
{
........
.
.
private ExcelWriter excelWriter;
private Sheet sheet;
private void handleRequest()
{
while("Till there are more rows")
{
excelWriter.writeDetailsForCategory(List<String> listOfItems)
}
}
}
ExcelWriter 类的设计是这样的:
public class ExcelWriter()
{
protected Sheet sheet;
public void writeDetailsForCategory(List<String> listOfItems)
{
for(String item : listOfItems)
{
writeToCell(rowNum, columnNum, value, sheet);
columnNum++;
}
}
}
writeToCell(( 方法设计有受保护的访问修饰符:
protected void writeCell(int rowNum, int colNum, String value, Sheet sheet)
{
if (value == null)
{
return;
}
Row row = sheet.getRow(rowNum);
if (row == null)
{
row = sheet.createRow(rowNum);
}
Cell cell = row.createCell(colNum);
cell.setCellValue(value);
}
我必须对使用ExcelWriter的writeDetailsForCategory
的类ServiceImpl
的handleRequest
方法进行单元测试,该方法使用受保护的方法writeToCell
。我已经通过了writeToCell
方法中的FakeExcelSheet
。在此之后,我将断言Map <Object, FakeExcelRow>
的价值。我应该如何在protected
writeToCell
方法中传入假ExcelSheet参数?我的限制是我只能使用Mockito或PowerMockito。
继续我的另一个答案,您可以将特定的ExcelWriter
替换为写入给定StringGrid
的StringGridWriter
。它不知道也不在乎它是excel。
public final class StringGridWriter() {
private final StringGrid grid;
public StringGridWriter(StringGrid grid) {
this.grid = grid;
}
public void writeDetailsForCategory(List<String> listOfItems) {
for(String item : listOfItems) {
grid.writeToCell(rowNum, columnNum, value);
columnNum++;
}
}
}
服务用法:
public class ServiceImpl {
........
.
.
private final StringGridWriter gridWriter;
public ServiceImpl(StringGridWriter gridWriter) {
this.gridWriter = gridWriter;
}
private void handleRequest() {
while("Till there are more rows"){
gridWriter.writeDetailsForCategory(List<String> listOfItems)
}
}
}
这就是您分配给它以使用它的方式:
Sheet theApacheSheet = ...;
StringGrid grid = new ApacheSheetStringGrid(theApacheSheet);
StringGridWriter writer = new StringGridWriter(grid);
ServiceImpl service = new ServiceImpl(writer);
根据我的另一个答案,ApacheSheetStringGrid
在哪里。所以现在,即使是ServiceImpl
也不知道这是在使用 excel。这种依赖关系的注入在实践中就是依赖反转原则。
看看我如何快速摆脱复杂的 excel 接口并将其归结为一个抽象,一个功能的子集,这只是我的客户想要的接口(接口隔离原则(,这使得它既易于测试,又易于替换为其他实现。通过不抽象,您将代码与 apache excel 实现紧密耦合。