Skip to content
TaDev Logo TaDev
Go back

TDD vs SDD: Khác nhau thế nào và nên dùng gì trong dự án thực tế?

Bài viết học nhanh cho team product và engineering: hiểu đúng bản chất, thấy rõ ưu nhược điểm, và biết cách kết hợp để ra sản phẩm đúng yêu cầu, ít lỗi.

1) Tóm tắt siêu nhanh (đọc 60 giây)

Nếu nói ngắn gọn:

Trong phần lớn dự án thực tế, cách hiệu quả nhất là: SDD ở mức feature + TDD ở mức implementation.


2) Định nghĩa rõ ràng

TDD là gì?

TDD là vòng lặp phát triển Red -> Green -> Refactor:

  1. Red: Viết test mới và để nó fail.
  2. Green: Viết lượng code nhỏ nhất để test pass.
  3. Refactor: Tối ưu thiết kế code, test vẫn phải pass.

Mục tiêu chính: chất lượng kỹ thuật ổn định, giảm regression, tăng khả năng refactor an toàn.

SDD là gì?

SDD là cách phát triển dựa trên đặc tả (specification) đã thống nhất:

  1. Xác định mục tiêu, phạm vi, rule, acceptance criteria.
  2. Thiết kế và triển khai bám theo spec.
  3. Kiểm chứng kết quả có khớp spec không.

Mục tiêu chính: đồng bộ giữa business và engineering, hạn chế làm sai nhu cầu.

Lưu ý: nhiều đội có thể gọi gần nghĩa bằng BDD/ATDD ở một số ngữ cảnh. Cốt lõi vẫn là “spec dẫn đường”.


3) So sánh tổng quan

Tiêu chíTDDSDD
Điểm bắt đầuTest case kỹ thuậtTài liệu đặc tả nghiệp vụ/sản phẩm
Đơn vị làm việc chínhHàm, class, moduleFeature, use case, luồng nghiệp vụ
Người tham gia chínhDev (chính)PO/BA/QA/Dev (liên phòng ban)
Mục tiêu gầnĐúng hành vi codeĐúng yêu cầu sản phẩm
Mục tiêu xaDễ bảo trì, refactor an toànGiảm lệch kỳ vọng, dễ kiểm soát scope
Artefact sốngUnit/Integration testSpec + Acceptance criteria + test
Rủi ro nếu dùng riêngĐúng code nhưng sai nhu cầuĐúng tài liệu nhưng lỗi kỹ thuật
Tốc độ phản hồiRất nhanh ở mức codeNhanh ở mức nghiệp vụ nếu spec rõ

4) Sơ đồ tư duy nhanh

flowchart LR
    A[Ý tưởng tính năng] --> B{Bắt đầu từ đâu?}
    B -->|Spec trước| C[SDD]
    B -->|Test trước| D[TDD]

    C --> E[Define rules + AC]
    E --> F[Implement theo spec]
    F --> G[Validate đúng nhu cầu]

    D --> H[Red: test fail]
    H --> I[Green: code pass test]
    I --> J[Refactor an toàn]

    G --> K[Đúng cái cần làm]
    J --> L[Làm đúng cách]

    K --> M[Kết hợp để tối ưu]
    L --> M

5) Ưu điểm chi tiết

Ưu điểm của TDD

Nhóm lợi íchMô tả
Giảm lỗi hồi quyTest trở thành lưới an toàn, thay đổi dễ phát hiện lỗi sớm
Thiết kế tốt hơnBuộc tách phụ thuộc, tăng tính module, dễ test và dễ maintain
Refactor tự tinCó cảnh báo tức thì khi đổi code làm sai hành vi
Vòng phản hồi nhanhDev nhận tín hiệu đúng/sai sau vài giây/phút
Tài liệu kỹ thuật sốngTên test và test case phản ánh hành vi mong đợi

Ưu điểm của SDD

Nhóm lợi íchMô tả
Đồng thuận liên phòng banBusiness, QA, Dev cùng nhìn một nguồn sự thật
Giảm hiểu sai yêu cầuQuy tắc và tiêu chí chấp nhận được làm rõ sớm
Quản trị phạm vi tốtDễ phát hiện scope creep, quản lý thay đổi rõ ràng
Hữu ích cho domain nhạy cảmThuận lợi cho audit/compliance/truy vết quyết định
Xác định Done rõ hơnDựa trên acceptance criteria thay vì cảm tính

6) Nhược điểm chi tiết

Nhược điểm của TDD

Vấn đềTác động
Đường học ban đầu dốcTeam mới có thể thấy chậm trong 1-3 sprint đầu
Dễ viết test sai trọng tâmNếu test bám implementation, test sẽ giòn và tốn công sửa
Có thể thiếu góc nhìn E2ENhiều unit test pass nhưng flow thật vẫn có thể lỗi
Không thay thế phân tích nghiệp vụTest đúng chưa chắc yêu cầu business đúng

Nhược điểm của SDD

Vấn đềTác động
Spec có thể lỗi thờiNếu không cập nhật, tài liệu lệch thực tế triển khai
Nguy cơ nặng quy trìnhQuá nhiều thủ tục làm giảm nhịp delivery
Chất lượng code không tự tăngCó spec tốt nhưng vẫn cần kỹ thuật test tốt
Phụ thuộc chất lượng viết specSpec mơ hồ kéo theo triển khai mơ hồ

7) Ví dụ dễ hình dung: tính năng chuyển tiền

Nếu đi theo SDD trước

Bạn sẽ chốt:

Sau đó dùng TDD cho phần rủi ro cao

Bạn viết test trước cho:

Kết quả:


8) Khi nào nên chọn gì?

Bối cảnhKhuyến nghị
Startup MVP, thay đổi nhanh, team nhỏSDD nhẹ + TDD chọn lọc cho lõi logic
Hệ thống tài chính/nhạy cảm, nhiều stakeholderSDD bắt buộc + TDD mạnh ở core domain
Legacy code nhiều rủi roViết characterization test theo TDD trước khi refactor
Team mới với testingBắt đầu TDD ở module quan trọng, mở rộng dần

9) Công thức kết hợp thực dụng (khuyên dùng)

  1. Spec nhẹ 1 trang/feature: mục tiêu, phạm vi, rule, AC.
  2. Đánh dấu vùng rủi ro cao: tiền, trạng thái, phân quyền, tích hợp ngoài.
  3. Áp dụng TDD bắt buộc cho vùng rủi ro cao.
  4. Dùng integration/e2e cho các luồng chính và lỗi trọng yếu.
  5. Review theo 2 câu hỏi:
    • Có đúng spec chưa?
    • Có đủ test ngăn regression chưa?
flowchart TD
    A[Feature request] --> B[Viết mini-spec]
    B --> C{Có rule rủi ro cao?}
    C -->|Có| D[TDD bắt buộc]
    C -->|Không| E[Test mức phù hợp]
    D --> F[Integration/E2E then chốt]
    E --> F
    F --> G{Pass AC + Pass tests?}
    G -->|Yes| H[Ready to release]
    G -->|No| I[Quay lại refine spec hoặc test]

10) Checklist 15 phút cho team áp dụng ngay

Checklist SDD nhanh

Checklist TDD nhanh


11) Sai lầm phổ biến cần tránh

Sai lầmHậu quảCách tránh
Chỉ TDD, không làm rõ yêu cầuCode chuẩn kỹ thuật nhưng lệch businessLuôn có mini-spec trước khi code
Chỉ SDD, test yếuĐúng tài liệu nhưng sản phẩm dễ vỡBắt buộc test cho rule rủi ro cao
Test viết sau cho cóKhông còn tính “driven”Viết test trước ít nhất ở core logic
Spec dài nhưng không đo đượcTranh cãi đúng/sai khi nghiệm thuAC phải đo được và kiểm thử được

12) Kết luận

Công thức nhớ nhanh:

Khi hai thứ đi cùng nhau, team vừa đi đúng hướng vừa đi nhanh hơn theo thời gian.


13) Phụ lục: Template mini-spec (copy dùng ngay)

# Mini Spec - <Feature Name>

## 1. Goal
- Business goal:
- User value:

## 2. Scope
- In scope:
- Out of scope:

## 3. Business Rules
- Rule 1:
- Rule 2:

## 4. Acceptance Criteria
- AC1 (Given/When/Then):
- AC2 (Given/When/Then):

## 5. Risks
- Main risks:
- Rollback note:

14) Phụ lục: Template test list (TDD starter)

# TDD Test List - <Feature Name>

## Happy Path
- [ ] Case 1
- [ ] Case 2

## Validation
- [ ] Invalid input 1
- [ ] Invalid input 2

## Error Handling
- [ ] Timeout from dependency
- [ ] Retry/rollback behavior

## Edge Cases
- [ ] Boundary value 1
- [ ] Boundary value 2

Share this post on:

Previous Post
Mega Manager - Quản lý dự án trong kỷ nguyên AI
Next Post
Hướng dẫn sử dụng Jules Google để lập trình đa nền tảng kết nối trực tiếp với GitHub