首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 數據庫知識 >  >> SQL Server 資料庫 >> 關於SqlServer

數據庫單元測試實戰指南:TDD 在 SQL Server 專案中的落地、DBPro 工具鏈與持續集成模式

     編輯:關於SqlServer

「數據庫沒有單元測試」是技術債務的溫床。Visual Studio Database Edition (DBPro/Data Dude) 將測試驅動開發 (TDD)引入數據庫專案:Schema 比對、靜態分析、單元測試 (T-SQL/CLR)、數據生成、部署驗證、版本控制一體化。本文構建從需求到生產的 TDD 閉環流程。

數據庫 TDD 核心流程 (紅-綠-重構)

  1. 紅:編寫失敗的單元測試 (定義預期行為);
  2. 綠:編寫最少 T-SQL/CLR 代碼通過測試;
  3. 重構:優化代碼結構、性能、命名,測試保綠;
  4. 提交:測試 + 代碼 入庫,CI 自動驗證。

DBPro 單元測試架構

組件角色關鍵特性
數據庫專案 (.dbproj)Schema 來源 (創建腳本、預部署/後部署)版本控制、Schema 比對、建置驗證
測試專案 (.testproj)單元測試容器 (C# 承載 T-SQL 測試)MSTest 框架、有序/並行執行、數據驅動
測試類/方法對應存儲過程/函數/觸發器/視圖`[TestMethod]`、`[TestInitialize]`、`[TestCleanup]`
測試條件斷言邏輯 (行數、標量值、結果集、執行時間、空結果集)內建 8 種條件,可擴展自定義條件
測試數據生成計劃生成符合約束的測試數據 (發生器、分布、外鍵一致性)預部署腳本、後部署腳本、數據綁定
部署配置目標實例 (本地/共享/隔離)、部署動作 (創建/更新/重建)沙箱隔離、事務回滾、快照還原

標準化測試模板 (存儲過程示例)

-- 1. 定義測試數據 (預部署腳本 / 數據生成計劃)
INSERT INTO dbo.Customers (Id, Name, Email, Status) VALUES
(1, 'Alice', 'alice@test.com', 'Active'),
(2, 'Bob', 'bob@test.com', 'Inactive');

-- 2. 測試方法 (C# 承載 T-SQL)
[TestMethod]
public void GetActiveCustomers_ReturnsOnlyActive()
{
    // Arrange: 測試數據已由部署/生成計劃準備
    // Act
    using (var cmd = new SqlCommand("dbo.GetActiveCustomers", conn) { CommandType = CommandType.StoredProcedure })
    using (var reader = cmd.ExecuteReader())
    {
        // Assert: 測試條件驗證
        Assert.IsTrue(reader.Read());           // 至少一行
        Assert.AreEqual("Alice", reader["Name"]);
        Assert.AreEqual("Active", reader["Status"]);
        Assert.IsFalse(reader.Read());          // 僅一行
    }
}

三大測試隔離策略

進階模式:數據驅動測試 + 邊界覆蓋

[DataSource("Microsoft.VisualStudio.TestTools.DataSource.CSV", "TestCases.csv", "TestCases#csv", DataAccessMethod.Sequential)]
[TestMethod]
public void CalculateDiscount_DataDriven()
{
    var input = Convert.ToDecimal(TestContext.DataRow["InputAmount"]);
    var expected = Convert.ToDecimal(TestContext.DataRow["ExpectedDiscount"]);
    var customerType = TestContext.DataRow["CustomerType"].ToString();

    using (var cmd = new SqlCommand("dbo.CalculateDiscount", conn) { CommandType = CommandType.StoredProcedure })
    {
        cmd.Parameters.AddWithValue("@Amount", input);
        cmd.Parameters.AddWithValue("@CustomerType", customerType);
        var result = (decimal)cmd.ExecuteScalar();
        Assert.AreEqual(expected, result, 0.001m, $"Failed for {customerType} amount {input}");
    }
}
  • CSV/Excel/XML/SQL Server 數據源;
  • 覆蓋:正常值、邊界值 (0、MAX)、異常值 (NULL、負數)、業務規則邊界 (VIP 閾值);
  • 新增測試用例 = 新增 CSV 行,**零代碼變更**。

CI/CD 管道集成

# Azure DevOps / GitHub Actions 片段
- task: VSBuild@1
  inputs:
    solution: 'DatabaseProject.dbproj'
    platform: 'Any CPU'
    configuration: 'Release'

- task: VSTest@2
  inputs:
    testSelector: 'testAssemblies'
    testAssemblyVer2: '**/*Test*.dll'
    searchFolder: '$(Build.BinariesDirectory)'
    runSettingsFile: 'DatabaseTest.runsettings'  # 連接字符串、部署配置
    codeCoverageEnabled: true

- task: PublishTestResults@2
  inputs:
    testResultsFormat: 'VSTest'
    testResultsFiles: '**/*.trx'

避坑指南

  • 測試邏輯洩露生產代碼:測試項目**獨立編譯、獨立部署**,不引用生產專案輸出;
  • 共享開發數據庫導致測試不穩定:強制**本地實例 / 容器 / 專用測試實例**,CI 獨立佈建;
  • 忽視性能基準測試:`ExecutionTime` 條件設置基準 (P95 < 200ms),防止性能回歸;
  • 測試數據不符合約束:生成計劃**必須滿足 FK/CK/UK**,否則測試失效掩蓋真實 Bug;
  • 過度測試內部實現:測試**公共契約 (參數、結果集、副作用)**,不測試私有邏輯/中間表。

總結

數據庫 TDD 非理想主義,而是將 Schema 變更、邏輯重構、性能優化的風險從「上線後發現」前移到「編碼時發現」的工程紀律。DBPro/SSDT 提供了工具鏈,關鍵在於團隊建立:**測試先行文化、隔離環境標準化、數據生成自動化、CI 門禁強制**。從「手工驗證」進化到「自動化契約驗證」,是數據庫工程化的必經之路。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved
策略機制優點缺點適用場景
事務回滾`TransactionScope` / `BEGIN TRAN ... ROLLBACK`極快、無殘留、並行安全不支持測試 `COMMIT` 邏輯、分布式事務、DDL單元測試首選 (90%+)
快照還原數據庫快照 / 備份還原 / 容器重建支持 DDL、完整隔離、狀態重現慢 (秒~分)、資源重、串行集成測試、Schema 遷移測試
數據重建`TRUNCATE` + 重新插入 / `MERGE` 同步中等速度、可控制數據狀態外鍵順序、觸發器、標識列重置複雜無事務支持場景 (MyISAM 等)