使用xUnit.net 对 .net core 进行单元测试
文章目錄
- 1.自動化測試綜述
- 1.為什么要進行自動化測試
- 2.自動化測試的分類
- 2.測試的三個階段 AAA
- 代碼部分:
- 3.Assert
- 具體代碼:
- 4.測試的優化
- 1.分組 [ Trait ("Name",“Value”) ]
- 1.代碼:
- 2.輸出測試的信息
- 3.可以跳過去某個測試
- 4.為了防止代碼重復,new 的實例,在構造函數里實現
- 5.數據驅動測試
- 題外話
1.自動化測試綜述
1.為什么要進行自動化測試
1.可以在任何時間進行測試。
2.測試速度要比人快。
3.非常可靠。
2.自動化測試的分類
- 單元測試:測試某個類或者類下的某個方法
- 集成測試
- 皮下測試
- UI 測試
測試的是 public ,private不太好測試,需要修改代碼
2.測試的三個階段 AAA
- Arrange:(序列,安排),這里做一些先決的設定,例如創建對象實例,數據,輸入等等。
- Act ,在這里執行生產代碼并返回結果,例如調用方法和設置屬性。
- Assert:(主張)在這里檢測結果,測試通過或者失敗。
xUnit 是一個測試框架,可以針對 .net /core 進行測試。
代碼部分:
1.先看目錄結構
- 命名規則:在類的名字后邊加 test 。
- 命名規則:測試方法的方法名用 ShouldAdd 。
- 測試的項目,添加 xUnit.net 測試項目。
Cakulator 類
public class Cakulator{public int Add(int a, int b){return a + b;}}CakulatroTest 類
public class CakulatroTest{[Fact] //根據這個特性判斷出來是個測試方法。public void ShouldAdd(){// Arrangevar sut = new Cakulator();// system Under Test// Actvar result = sut.Add(1, 2);// AssertAssert.Equal(3, result);//結果等于3}}進行測試:
在要準備測試的類和方法上直接右鍵運行。
3.Assert
- Assert基于代碼的返回值,對象的最終狀態,事件是否發生等情況來評估測試結果。
- Assert的結果可能是 pass 也有可能是 Fail,如果所有的 Assert 都是 Pass ,那么整個測試就 pass 了。如果有任何的 assert fail 了,那么測試就 fail 了。
xUnit 可以進行以下的判斷:
一個test里面應該有多少個 assert
- 一個 test 方法里,只能有一個 assert 。
- 一個 test 方法里,可以有多個 Asserts,只要這多個 assert 這對一個 Action 就行。
具體代碼:
1.先建一個 Person 類
public class Person{public string FirstName { get; set; }public string LastName { get; set; }}2.再建一個 patient 類
public class patient:Person{public patient(){IsNew = true; //剛 new 出來的時候,這個 isnew 是 true 。BloodSugar = 4.9f;History = new List<string>();//把這個要 new 出來.}public string FullName => $"{LastName}{FirstName}";public bool IsNew { get; set; } //是否是剛出生的。public float BloodSugar { get; set; }public int HeartBeatRate { get; set; }public void IncressHeartBeatRate() //計算心跳{//執行完以后的方法 + 2HeartBeatRate = CalulateHeartBeatRate() + 2;}public List<string> History { get; set; }private int CalulateHeartBeatRate() //心跳{var random = new Random();return random.Next(1,100);}}3.使用 xUnit 進行測試:
public class PatientShould{// 對 bool 類型進行判斷.[Fact]public void BeNewWhenCreated(){// arrangepatient patient = new patient();//Actbool result = patient.IsNew;//AssertAssert.True(result);// Assert.False(result);}//對字符串進行判斷[Fact] //表明這個是個測試方法public void HaveCorrctFullName(){// Arrange (實例化一個你要檢查的類)patient patient = new patient{FirstName = "小明",LastName = "張"};// Act 。把需要檢查的屬性弄出來var fullName = patient.FullName;//Assert 。進行判斷.Assert.Equal("張小明", fullName);Assert.StartsWith("張", fullName);Assert.EndsWith("明", fullName);Assert.Contains("小", fullName);//是小寫但不是大寫;Assert.NotEqual("李", fullName);}//對 浮點型 進行判斷[Fact]public void HaveDefaultBloodSugarWhenCreate(){patient patient = new patient();float blooddar = patient.BloodSugar;Assert.Equal(4.9f, blooddar, 5);//在哪個范圍內Assert.InRange(blooddar, 3.9f, 6.1f);}//剛開始創建的時候,名字應該是空;[Fact]public void HaveNameWhenCreated(){patient p = new patient();var a = p.FirstName;Assert.Null(a);Assert.NotNull(p);}//對集合進行測試[Fact]public void HaveHadColid(){var p = new patient();p.History.Add("感冒");p.History.Add("發燒");p.History.Add("水痘");p.History.Add("腹瀉");Assert.Contains("感冒", p.History);Assert.DoesNotContain("心臟病", p.History);//Predicate//對集合中的元素判斷是否包含Assert.Contains(p.History, x => x.StartsWith("水"));//對集合內的所有元素都進行判斷Assert.All(p.History, x => Assert.True(x.Length >= 2));// 判斷兩個集合是否相等var diseases = new List<string>{"感冒","發燒","水痘","腹瀉"};Assert.Equal(p.History, diseases);}// 對 object 進行測試[Fact]public void BeAPerson(){var p1 = new patient();var p2 = new patient();Assert.IsType<patient>(p1);//p是否是 patient 類型.Assert.IsNotType<Person>(p1);//這個就會判斷處所。盡管是他的子類.Assert.IsAssignableFrom<Person>(p1);//判斷是否繼承于某個類//判斷是否是一個實例//same 是同一個實例Assert.NotSame(p1,p2);// Assert.Same(p1,p2);}// 判斷異常// 判斷拋出的異常是否和我們所期待的相等.// 對委托和事件的測試.// 寫起來有點麻煩,用到再說吧。}在使用 測試資源管理器的時候,如果加斷點,要使用 debug 模式,不能進行直接測試
4.測試的優化
- 測試分組
- 忽略測試
- 自定義測試輸出的內容
- 減少重復代碼
- 共享上下文
注意,在每次測試的時候,都要重新生成一下
1.分組 [ Trait (“Name”,“Value”) ]
- 方法級
- Class級
1.代碼:
public class PatientShould{private readonly ITestOutputHelper output;private readonly patient _patient;private readonly LongTimeTask _task;public PatientShould(ITestOutputHelper output){this.output = output;_patient=new patient();_task=new LongTimeTask();}// 對 bool 類型進行判斷.[Fact][Trait("Category","New")]public void BeNewWhenCreated(){output.WriteLine("這是第一個測試");//在這里用 Console.WriteLine()是無效的;bool result = _patient.IsNew;Assert.True(result);}[Fact] //表明這個是個測試方法[Trait("Category", "Name")]public void HaveCorrctFullName(){patient patient = new patient{FirstName = "小明",LastName = "張"};var fullName = patient.FullName;Assert.Equal("張小明", fullName);Assert.StartsWith("張", fullName);Assert.EndsWith("明", fullName);Assert.Contains("小", fullName);//是小寫但不是大寫;Assert.NotEqual("李", fullName);}在測試任務管理器里面,選擇分組依據為特征:
2.輸出測試的信息
在測試的時候,console.writeLine( ) 不管用,要使用 outputhelp.WriteLine 進行測試,構造函數引用方法如下。
3.可以跳過去某個測試
[Fact(Skip =“不需要跑這個測試”)]
4.為了防止代碼重復,new 的實例,在構造函數里實現
要養成這種習慣:
具體代碼如下:
public class PatientShould{private readonly ITestOutputHelper output;private readonly patient _patient;private readonly LongTimeTask _task;public PatientShould(ITestOutputHelper output){this.output = output;// 為減少重復代碼,使用構造函數重構// 下邊都使用同一個構造函數_patient=new patient();_task=new LongTimeTask();}// 對 bool 類型進行判斷.[Fact][Trait("Category","New")]public void BeNewWhenCreated(){output.WriteLine("這是第一個測試");//在這里用 Console.WriteLine()是無效的;//Actbool result = _patient.IsNew;//AssertAssert.True(result);// Assert.False(result);}//對字符串進行判斷[Fact] //表明這個是個測試方法[Trait("Category", "Name")]public void HaveCorrctFullName(){// Arrange (實例化一個你要檢查的類)patient patient = new patient{FirstName = "小明",LastName = "張"};// Act 。把需要檢查的屬性弄出來var fullName = patient.FullName;//Assert 。進行判斷.Assert.Equal("張小明", fullName);Assert.StartsWith("張", fullName);Assert.EndsWith("明", fullName);Assert.Contains("小", fullName);//是小寫但不是大寫;Assert.NotEqual("李", fullName);}//對 浮點型 進行判斷[Fact][Trait("Category","New")]public void HaveDefaultBloodSugarWhenCreate(){patient patient = new patient();float blooddar = patient.BloodSugar;Assert.Equal(4.9f, blooddar, 5);//在哪個范圍內Assert.InRange(blooddar, 3.9f, 6.1f);}//剛開始創建的時候,名字應該是空;[Fact(Skip ="不需要跑這個測試")]public void HaveNameWhenCreated(){patient p = new patient();var a = p.FirstName;Assert.Null(a);Assert.NotNull(p);}//對集合進行測試[Fact]public void HaveHadColid(){var p = new patient();p.History.Add("感冒");p.History.Add("發燒");p.History.Add("水痘");p.History.Add("腹瀉");Assert.Contains("感冒", p.History);Assert.DoesNotContain("心臟病", p.History);//Predicate//對集合中的元素判斷是否包含Assert.Contains(p.History, x => x.StartsWith("水"));//對集合內的所有元素都進行判斷Assert.All(p.History, x => Assert.True(x.Length >= 2));// 判斷兩個集合是否相等var diseases = new List<string>{"感冒","發燒","水痘","腹瀉"};Assert.Equal(p.History, diseases);}// 對 object 進行測試[Fact]public void BeAPerson(){var p1 = new patient();var p2 = new patient();Assert.IsType<patient>(p1);//p是否是 patient 類型.Assert.IsNotType<Person>(p1);//這個就會判斷處所。盡管是他的子類.Assert.IsAssignableFrom<Person>(p1);//判斷是否繼承于某個類//判斷是否是一個實例//same 是同一個實例Assert.NotSame(p1,p2);// Assert.Same(p1,p2);}// 判斷異常// 判斷拋出的異常是否和我們所期待的相等.// 對委托和事件的測試.// 寫起來有點麻煩,用到再說吧。}5.數據驅動測試
舉例前邊的,加法的測試,可以寫多個 fact,但是比較麻煩,使用【Theory】+ 【InlineData】有簡單的方法。
public class Theory_CaculatorTest{[Theory][InlineData(1,2,3)][InlineData(1, 3, 4)][InlineData(2, 2, 4)][InlineData(1, 9, 10)][InlineData(9, 2, 11)]public void ShouldAddEquls(int x, int y, int expected){var sut = new Cakulator();var reslut = sut.Add(x,y);Assert.Equal(expected,reslut);}}除此之外,還可以直接用 從數據庫或者 CSV等文件中讀取后進行測試,這里沒看,用到的時候再學吧
題外話
最大的是解決方案名,下邊是類名
參考文獻:
xUnit.Net單元測試
gitee代碼
總結
以上是生活随笔為你收集整理的使用xUnit.net 对 .net core 进行单元测试的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: uip架构和局限
- 下一篇: c语言程序运行结果怎么看,c语言程序的运