問題背景
我有幾個JUnit測試,例如從目錄中獲取每個文件並對其執行測試。如果我在TestCase中實現了一個test方法,在一個循環裏讀取文件做測試,則只會顯示一個可能失敗或成功的測試。這樣的缺點是一旦中間有個測試用例不通過,後面的測試都不會進行了。如何編寫TestCase/TestSuite,以便每個文件都顯示爲單獨的測試,即使中間有一個測試失敗也不會影響其他測試用例。
解決方法
使用Junit 4的Parameterized/參數化測試。例子:
package yuth.junit.fromFile;
import static org.junit.Assert.assertTrue;
import java.io.File;
import java.util.ArrayList;
import java.util.Collection;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
import org.junit.runners.Parameterized.Parameters;
/**
* 從文件讀入測試數據,動態構造測試用例。基於jUnit 4,Junit 3下不可用。
* @author yuth
* <p>
* @version 1.0 2018年8月25日
*
*/
@RunWith(Parameterized.class)
public class TestDemo
{
private File file;
@Parameters
public static Collection<Object[]> getFiles()
{
Collection<Object[]> params = new ArrayList<Object[]>();
// 讀取測試文件
for (File f : new File(".").listFiles())
{
Object[] arr = new Object[] { f };
params.add(arr);
}
return params;
}
public TestDemo(File file)
{
this.file = file;
}
@Test
public void test()
{
// 實現自己的測試邏輯
assertTrue(!"testFromFile.txt".equals(file.getName()));
}
}
要點:
1.runwith中使用value = Parameterized.class。
2.必須提供@Parameters方法,方法簽名必須是public static Collection,不能有參數,並且collection元素必須是相同長度的數組。同時數組元素必須與唯一的公共構造函數的參數數量和類型相匹配。在本例中,我們數組的長度是1,構造方法的參數數量也是1,並且類型都是File。
3.執行test方法,調用了我們提供的參數。
與Spring boot整合時的例子
package yuth.junit.fromFile;
import static org.junit.Assert.assertTrue;
import java.io.File;
import java.util.ArrayList;
import java.util.Collection;
import javax.annotation.Resource;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
import org.junit.runners.Parameterized.Parameters;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.TestContextManager;
import com.kingdee.ai.thirdpart.TestLocalIntention;
import com.kingdee.ai.web.Application;
/**
* 簡述:從文件讀入測試數據,動態構造測試用例。JUNT 4。整合Spring boot
* <p>
* 詳細描述:
*
* @author yuth
* <p>
* @version 1.0 2018年8月25日
*
*/
@RunWith(Parameterized.class)
@SpringBootTest(classes = Application.class, webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@EnableAutoConfiguration
public class TestDemoWithSpringBoot
{
private File file;
private TestContextManager testContextManager;
@Before
public void setUpContext() throws Exception {
this.testContextManager = new TestContextManager(getClass());
this.testContextManager.prepareTestInstance(this);
}
@Parameters
public static Collection<Object[]> getFiles()
{
Collection<Object[]> params = new ArrayList<Object[]>();
// 讀取測試文件
for (File f : new File(".").listFiles())
{
Object[] arr = new Object[] { f };
params.add(arr);
}
return params;
}
public TestDemoWithSpringBoot(File file)
{
this.file = file;
}
@Test
public void test()
{
// 實現自己的測試邏輯
assertTrue(!"testFromFile.txt".equals(file.getName()));
}
}