C# NUnit 同時(並行)執行測試

並行測試主要就是依靠 Parallelizable 這個屬性(Attribute), Parallelizable 可以傳入 ParallelScope 列舉(enum),此列舉內容如下:
  • None:預設值,不並行處理,每個測試都會按順序逐一執行。
  • Self:本測試類別可以和不同的測試類別並行執行
  • Children:在同一父級測試類別中的測試並行執行
  • All:Self + Children,本測試類別會和其他可並行測試的類別同時執行,且同一父級測試類別中的測試並行執行

並行執行測試範例

測試範例如下:
    
public class UnitTestA{
	public void Test1([Values(1, 2, 3)] int option1){}
    public void Test2([Values(1, 2, 3)] int option1){}
}

public class UnitTestB{
	public void Test3([Values(1, 2, 3)] int option1){}
    public void Test4([Values(1, 2, 3)] int option1){}
}
    

UnitTestA 測試類別中有 Test1 和 Test2 兩個測試案例
UnitTestB 測試類別中有 Test3 和 Test4 兩個測試案例
且上面所有測試案例都使用 Values ,每個測試案例都會執行 3 次
(不直接使用 Repeat 是因為比較難直觀看到測試進度)

執行順序:
    
Test1-1,Test1-2,Test1-3,Test2-1,Test2-2,Test2-3,Test3-1,Test3-2,Test3-3,Test4-1,Test4-2,Test4-3
    

多個類別同時依序執行測試

UnitTestA.Test1 和 UnitTestB.Test3 會同時測試,接下來換 UnitTestA.Test2 和 UnitTestB.Test4 同時測試。
    
[Parallelizable(ParallelScope.Self)]
public class UnitTestA{
	public void Test1([Values(1, 2, 3)] int option1){}
    public void Test2([Values(1, 2, 3)] int option1){}
}

[Parallelizable(ParallelScope.Self)]
public class UnitTestB{
	public void Test3([Values(1, 2, 3)] int option1){}
    public void Test4([Values(1, 2, 3)] int option1){}
}
    

執行順序:(兩條同時執行)
    
Test1-1,Test1-2,Test1-3,Test2-1,Test2-2,Test2-3
Test3-1,Test3-2,Test3-3,Test4-1,Test4-2,Test4-3
    

單測試案例同時測試

UnitTestA.Test1 和 UnitTestB.Test3 會同時測試,接下來換 UnitTestA.Test2 和 UnitTestB.Test4 同時測試,但 Test2 是逐一測試,Test4 的所有測試案例則是同時測試
    
[Parallelizable(ParallelScope.Self)]
public class UnitTestA{
	public void Test1([Values(1, 2, 3)] int option1){}
    public void Test2([Values(1, 2, 3)] int option1){}
}

[Parallelizable(ParallelScope.Self)]
public class UnitTestB{
	public void Test3([Values(1, 2, 3)] int option1){}
    [Parallelizable(ParallelScope.Children)]
    public void Test4([Values(1, 2, 3)] int option1){}
}
    

執行順序:
    
Test1-1,Test1-2,Test1-3,Test2-1,Test2-2,Test2-3
Test3-1,Test3-2,Test3-3,Test4-1
						Test4-2
                        Test4-3
    

單測試類別同時測試

UnitTestA.Test1 逐個測試, UnitTestB 下的所有測試案例同時測試(Test3 * 3 + Test4 * 3)
    
[Parallelizable(ParallelScope.Self)]
public class UnitTestA{
	public void Test1([Values(1, 2, 3)] int option1){}
    public void Test2([Values(1, 2, 3)] int option1){}
}

[Parallelizable(ParallelScope.All)]
public class UnitTestB{
	public void Test3([Values(1, 2, 3)] int option1){}
    public void Test4([Values(1, 2, 3)] int option1){}
}
    

執行順序:
    
Test1-1,Test1-2,Test1-3,Test2-1,Test2-2,Test2-3
Test3-1
Test3-2
Test3-3
Test4-1
Test4-2
Test4-3
    

所有測試類別同時測試

UnitTestA.Test1 和 UnitTestB 下的所有測試案例同時測試
    
[Parallelizable(ParallelScope.All)]
public class UnitTestA{
	public void Test1([Values(1, 2, 3)] int option1){}
    public void Test2([Values(1, 2, 3)] int option1){}
}

[Parallelizable(ParallelScope.All)]
public class UnitTestB{
	public void Test3([Values(1, 2, 3)] int option1){}
    public void Test4([Values(1, 2, 3)] int option1){}
}
    

執行順序:
    
就是全部同時執行
    

限制同時執行數量

可以在 namespace 上方使用 LevelOfParallelism 來限制最大數量,不過在未加上限制前,筆者最多只能同時執行 24 個測試,應該是和 CPU 處理器數量有關
    
[assembly: LevelOfParallelism(4)]

namespace RuyutTestProject;

[Parallelizable(ParallelScope.All)]
public class UnitTestA
{
}
    

就算有多個 cs 檔案也只能使用一個,不然會出現編譯時錯誤:
    
UnitTestB.cs(1, 12): [CS0579] 'LevelOfParallelism' 屬性重複
    



參考資料:
NUnit - Parallelizable
NUnit - LevelOfParallelism

留言