2016-04-15 110 views
1

我正在使用Apache POI方法写入Excel中的工作表。我必须为我写的方法进行单元测试。我使用了很多Apache POI的方法。我应该存储Apache POI的不同对象类的所有方法吗?Java中Jar方法的单元测试

示例:我创建了用于写入使用Apache POI方法的单元格的包装方法。

protected void writeCell(int rowNum, int colNum, String value, Sheet sheet) 
{ 
    if(value == null) 
    { 
     return; 
    } 
    Row row = sheet.getRow(rowNum); 
    Cell cell = row.createCell(colNum); 
    cell.setCellValue(); 
    } 

} 

我应该嘲笑甚至像的the Sheet.classgetRow和Row类的createCell的方法呢?

+1

你不必为Apache POI方法进行单元测试,你只需要模拟它们。也只模拟你使用的方法不是全部 –

+0

@KP我没有编写Apache POI的测试用例。我正在写我自己的方法。 – Ashley

回答

3

测试结果,未执行。

I.e.如果我写一个单元格,我现在可以从该单元格中读取该值吗?

另外,您向我们展示了protected方法,您只需要测试类的公共接口。如果通过公共接口看不到结果,那么你的课程可能会做得太多(单一责任原则)。

但是,其他考虑因素是速度和脆弱性,因为Apache POI正在读取和写入实际文件,所以编写这些测试会比较困难,而且速度会变慢。可以进行一些测试,但是如果整个套件正在读取和写入文件,那么速度会变慢,并且整个测试套件在理想情况下应该在几秒钟内运行。

因此,我将创建一个封装了一个Excel工作表,你想用它做什么的接口,这可能是:

public interface StringGrid { 
    String readCell(int rowNum, int colNum); 
    void writeCell(int rowNum, int colNum, String value); 
} 

现在,我可能会做一个快速的实现没有自动测试,或者只是少数围绕Apache POI进行简单的测试,但随后我的套件的其余部分将针对StringGridFake实现进行测试,并且我可以创建大量的快速运行测试,其中包含我的代码。

所以这些可能看起来像:

真正实现,只有在它的测试和直播节目中使用。

public final class ApacheSheetStringGrid implements StringGrid { 

    private final Sheet theApacheSheet; 

    public ApacheSheetStringGrid(Sheet theApacheSheet) { 
     this.theApacheSheet = theApacheSheet; 
    } 

    public String readCell(int rowNum, int colNum){ 
     ... 
    } 

    public void writeCell(int rowNum, int colNum, String value) { 
     Row row = theApacheSheet.getRow(rowNum); 
     Cell cell = row.createCell(colNum); 
     cell.setCellValue(); 
    } 
} 

的假(一个工作,速度快,内存只有实现StringGrid),对于所有其他测试:

public final class FakeStringGrid implements StringGrid { 

    private final Map<String, String> contents = new HashMap<String, String>(); 

    private static String getKey(int rowNum, int colNum) { 
     return rowNum + ", " + colNum; 
    } 

    public String readCell(int rowNum, int colNum){ 
     return contents.get(getKey(rowNum, colNum)); 
    } 

    public void writeCell(int rowNum, int colNum, String value) { 
     contents.put(getKey(rowNum, colNum), value); 
    } 
} 

这有额外的好处,你可以在以后换出现场实施另外,也许使用其他POI方法之一,甚至谷歌表实现,你只需要添加一些测试和一个新的实现,并不需要修改任何代码(开放封闭原则)。

+0

这是一个非常有效的解决方案。谢谢。我是否应该将所有方法(如writeCell(int rowNum,int colNum,String value))公诸于众以用于测试它们?因为那样我就无法测试受保护的方法。 – Ashley

+0

那么,如果你遵循这个方法,那些方法就会变成另一个类的“公共”。我*只*写'公共'方法,我只*写他们解决失败的测试,在我的代码'私人'和'保护'方法*只*通过[重构](http://blog.cleancoder。 COM /叔叔,鲍勃/ 2014/12/17/TheCyclesOfTDD.html)。 – weston

+0

“解决失败的测试”是什么意思?你是说你把所有的方法都写成公共第一,然后再把更大的方法分解成更小的方法,而不是把它们变成私有/保护? – Ashley