2024-10-26 016_學寫API_建一個新的測試項目的步驟

2024-10-26 016_學寫API_建一個新的測試項目的步驟

當你剛創建一個新的測試項目時,你的測試類 PackageControllerTests.cs 可能只是一個「空殼」模板,因為這是 Visual Studio 或其他 IDE 給你的基本樣式,它們並不知道具體你要測試什麼內容。而我給你的例子則是我一步步寫出來的具體測試代碼,目的是讓你理解整個測試流程。

下面我會一步步帶你從這個「空殼」開始,把它變成一個完整的測試類:

1. 修改測試類的訪問修飾符

你的測試類目前是 internal,這意味著這個類只能在相同的程式集中被訪問。為了讓它能夠被測試框架(如 xUnit)正常調用,你需要把它改為 public

1
2
3
4
5
6
namespace LogisticsAPI.Tests
{
public class PackageControllerTests
{
}
}

2. 引入必要的命名空間

要測試你的控制器,必須引用和測試內容相關的命名空間,這些包括:

  • LogisticsAPI.Controllers:用來訪問你要測試的 PackageController
  • LogisticsAPI.Models:用來訪問你的模型,例如 Package
  • Microsoft.Extensions.Logging:用來創建 Logger。
  • Microsoft.AspNetCore.Mvc:用來處理控制器返回的 Action 結果。
  • System.Collections.Generic:用來操作泛型集合,例如 List<Package>
  • xUnit:xUnit 是一個單元測試框架,它提供了測試方法的屬性標記(如 [Fact])和斷言(如 Assert)。

所以在 PackageControllerTests.cs 文件的頂部,加入以下引用:

1
2
3
4
5
6
using Xunit;
using LogisticsAPI.Controllers;
using LogisticsAPI.Models;
using Microsoft.Extensions.Logging;
using Microsoft.AspNetCore.Mvc;
using System.Collections.Generic;

3. 添加測試類的成員變數和構造函數

你需要有一個控制器實例 _controller 和一個 Logger 實例 _logger 來支持測試。所以在測試類中,先定義這些變數並用構造函數來初始化它們。

添加變數和構造函數:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
namespace LogisticsAPI.Tests
{
public class PackageControllerTests
{
private readonly PackageController _controller;
private readonly ILogger<PackageController> _logger;

public PackageControllerTests()
{
// 創建一個 Logger 的實例
_logger = new LoggerFactory().CreateLogger<PackageController>();

// 初始化 PackageController,並把 Logger 傳給它
_controller = new PackageController(_logger);
}
}
}

4. 添加測試方法

測試方法一般遵循以下結構:

  1. [Fact] 屬性:這是 xUnit 用來標記測試方法的屬性,代表這是一個測試用例。
  2. 測試方法的名稱最好具有描述性,例如 GetAllPackages_WhenCalled_ReturnsOkResult,這樣能清楚地表達測試的目標。

你可以參考以下測試方法來測試 GetAllPackages()

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
namespace LogisticsAPI.Tests
{
public class PackageControllerTests
{
private readonly PackageController _controller;
private readonly ILogger<PackageController> _logger;

public PackageControllerTests()
{
_logger = new LoggerFactory().CreateLogger<PackageController>();
_controller = new PackageController(_logger);
}

[Fact]
public void GetAllPackages_WhenCalled_ReturnsOkResult()
{
// Act: 調用 GetAllPackages 方法
var okResult = _controller.GetAllPackages();

// Assert: 確認返回的結果是 OkObjectResult
Assert.IsType<OkObjectResult>(okResult.Result);
}
}
}

5. 一步步解釋如何知道要寫什麼

你可能會有疑問:如何知道要寫什麼?

  1. 理解你要測試的目標:你首先需要知道你的 PackageController 裡有什麼方法,例如 GetAllPackages(),它的目標是返回所有包裹。你測試的目標就是確保這個方法在被調用時返回正確的結果。

  2. 考慮測試場景:不同的方法有不同的行為,例如對於 GetAllPackages(),你需要測試它返回的包裹列表是否正確。對於 CreatePackage(),你需要測試新包裹是否正確地被添加到列表中。

  3. 使用 Arrange-Act-Assert 模式

    • Arrange(準備):創建控制器並準備好需要的輸入數據。
    • Act(執行):調用你要測試的方法。
    • Assert(斷言):檢查結果是否符合你的預期。

6. 總結

  • 從「空殼」開始:當你看到一個空的測試類,不用緊張,逐步添加你需要的部分即可。
  • 逐步添加需要的代碼:先引入命名空間,添加成員變數和構造函數,再開始編寫具體的測試方法。
  • 遵循 Arrange-Act-Assert 模式:每個測試都應該明確地包含準備、執行和斷言三個步驟。

希望這些步驟能幫助你更好地理解如何從頭開始編寫測試代碼。如果你有具體問題或不確定某些部分應該怎麼做,隨時告訴我,我會一步步引導你完成測試的撰寫。