Cách viết test case cho người mới: Template, ví dụ và checklist cơ bản

4 tháng trước · 9 phút đọc
Test case là gì và tại sao cần viết đúng ngay từ đầu
Mình nhớ lần đầu được giao viết test case cho tính năng đăng nhập. Nghĩ đơn giản: nhập đúng thì vào, nhập sai thì báo lỗi. Viết xong 3 dòng, tự tin submit.
Kết quả? Dev hỏi ngược lại: "Test case của bạn bước 2 là gì? Expected result viết 'hệ thống hoạt động đúng' nghĩa là sao?"
Mình ngồi nhìn màn hình, không biết trả lời gì.
Test case (kịch bản kiểm thử) là tài liệu mô tả một tình huống cụ thể cần kiểm tra, bao gồm: làm gì, với dữ liệu gì, và kết quả mong đợi là gì. Không phải ghi chú cá nhân, không phải to-do list. Là tài liệu người khác đọc vào phải làm theo được và reproduce đúng kết quả.
Test case tốt giúp bất kỳ ai cũng reproduce được lỗi
Tại sao cần viết đúng? Vì test case viết ẩu dẫn đến 3 hệ quả:
- Dev không reproduce được bug → không fix được
- Bạn test lần sau không nhớ mình đã test cái gì
- Team mới vào không biết hệ thống đã được test đến đâu
Viết test case kỹ lần đầu nghe mất thời gian, nhưng tiết kiệm rất nhiều lần sau. Bài này mình hướng dẫn từ cấu trúc, cách đặt tên, đến template copy được luôn.
Cấu trúc chuẩn của một test case
Một test case đầy đủ gồm 8 trường. Nghe nhiều nhưng mỗi trường có lý do tồn tại.
| Trường | Ý nghĩa | Ví dụ |
|---|---|---|
| Test Case ID | Mã định danh duy nhất | TC_LOGIN_001 |
| Test Case Name | Tên ngắn gọn mô tả tình huống | Đăng nhập thành công với email hợp lệ |
| Module/Feature | Tính năng đang test | Đăng nhập |
| Preconditions | Điều kiện cần có trước khi test | Người dùng đã có tài khoản, chưa đăng nhập |
| Test Steps | Các bước thực hiện theo thứ tự | 1. Mở trang login... |
| Test Data | Dữ liệu cụ thể dùng để test | Email: [email protected], Pass: Test@1234 |
| Expected Result | Kết quả mong đợi chi tiết | Chuyển hướng đến trang dashboard, hiển thị tên user |
| Status | Kết quả sau khi test | Pass / Fail / Blocked |
8 trường này là xương sống - thiếu trường nào là test case không dùng được
Trường hay bị bỏ qua nhất: Preconditions và Test Data.
Preconditions (điều kiện tiên quyết) là thứ phải có trước khi bắt đầu test. Ví dụ test giỏ hàng mà không ghi "sản phẩm đã được thêm vào giỏ", người test sau sẽ bị stuck ngay bước đầu.
Test Data là dữ liệu cụ thể, không phải chung chung. "Nhập email hợp lệ" là không đủ. Phải ghi rõ: [email protected]. Dev và tester khác cần biết chính xác bạn dùng gì để reproduce.
Cách đặt tên test case chuẩn
Tên test case là thứ đầu tiên người khác đọc. Đặt tên tốt giúp nhìn vào biết ngay test gì, không cần đọc hết các bước.
Công thức mình hay dùng:
[Hành động] + [Đối tượng/Input] + [Kết quả mong đợi ngắn]
Ví dụ đặt tên - so sánh:
| ❌ Tên chung chung | ✅ Tên cụ thể |
|---|---|
| Test đăng nhập | Đăng nhập thành công với email và mật khẩu hợp lệ |
| Kiểm tra lỗi | Đăng nhập thất bại khi mật khẩu sai |
| Test password | Đăng nhập thất bại khi bỏ trống trường mật khẩu |
| Kiểm tra form | Đăng nhập thất bại khi email không có ký tự @ |
Tên cụ thể = nhìn vào biết test gì, không cần đọc thêm
Quy tắc đặt Test Case ID:
Format phổ biến: [Viết tắt module]_[Số thứ tự 3 chữ số]
- Đăng nhập:
TC_LOGIN_001,TC_LOGIN_002 - Đăng ký:
TC_REGISTER_001 - Giỏ hàng:
TC_CART_001 - Thanh toán:
TC_PAYMENT_001
Số thứ tự 3 chữ số (001 thay vì 1) để sau này sort đúng thứ tự khi có hàng trăm test case. Mình từng đặt TC_LOGIN_1, TC_LOGIN_2... đến TC_LOGIN_10 thì sort ra thứ tự: 1, 10, 2, 3... Phải rename lại hết, mất cả buổi chiều.
Cách viết test steps và expected result
Hai trường này quyết định test case có dùng được hay không.
Test Steps - 3 nguyên tắc bắt buộc
1. Mỗi bước = 1 hành động
Không viết: "Mở trang, nhập email và password, nhấn đăng nhập"
Viết đúng:
1. Mở trình duyệt, truy cập https://demo-app.com/login
2. Nhập email: [email protected] vào trường "Email"
3. Nhập mật khẩu: Test@1234 vào trường "Mật khẩu"
4. Click nút "Đăng nhập"
2. Ghi rõ URL, tên field, tên nút
Không viết "nhấn nút xác nhận" - trên trang có thể có 3 nút. Phải ghi đúng tên hiển thị: "Click nút 'Đăng nhập'"
3. Không bỏ qua bước "mở trang"
Nghe thừa nhưng không phải. Môi trường khác nhau, URL khác nhau. Người test không biết bạn đang test trên staging hay production.
Mỗi bước chỉ 1 hành động - không gộp, không tắt
Expected Result - phần hay viết sai nhất
Expected result (kết quả mong đợi) mô tả chính xác hệ thống làm gì sau khi thực hiện xong các bước.
❌ Viết sai:
- "Hệ thống hoạt động đúng"
- "Đăng nhập thành công"
- "Hiển thị thông báo lỗi"
✅ Viết đúng:
- "Trang chuyển hướng đến /dashboard, hiển thị tên người dùng 'Nguyễn Văn A' ở góc trên phải"
- "Hiển thị thông báo màu đỏ: 'Mật khẩu không đúng. Vui lòng thử lại'"
- "Nút 'Đăng nhập' bị disabled, không thể click"
Quy tắc đơn giản: expected result phải kiểm tra được bằng mắt mà không cần phán đoán. Nếu phải đoán "đăng nhập thành công" có nghĩa là gì thì bạn viết chưa đủ.
Template test case chuẩn - copy và dùng ngay
Mình tổng hợp template dạng bảng Markdown và file Excel để bạn dùng được ngay, không cần tạo từ đầu.
Dưới đây là template 1 test case hoàn chỉnh:
Test Case ID : TC_[MODULE]_001
Test Case Name : [Hành động] + [Input/Điều kiện] + [Kết quả mong đợi ngắn]
Module : [Tên tính năng]
Priority : High / Medium / Low
Preconditions :
- [Điều kiện 1]
- [Điều kiện 2]
Test Data :
- [Tên field 1]: [Giá trị cụ thể]
- [Tên field 2]: [Giá trị cụ thể]
Test Steps :
1. [Hành động cụ thể]
2. [Hành động cụ thể]
3. [Hành động cụ thể]
Expected Result : [Mô tả chính xác hệ thống làm gì, kiểm tra được bằng mắt]
Actual Result : [Điền sau khi test]
Status : Pass / Fail / Blocked / Not Tested
Notes : [Ghi chú thêm nếu có]
Template này dùng được cho manual test, Jira, hoặc Google Sheets
Bạn có thể tải file Excel đầy đủ với ví dụ sẵn tại đây: Tải template test case Excel
File gồm 3 sheet:
- Sheet 1: Template trống để điền
- Sheet 2: Ví dụ đăng nhập (10 test cases)
- Sheet 3: Ví dụ đăng ký (8 test cases)
Mình recommend dùng Google Sheets thay vì Excel nếu team nhiều người, vì nhiều người sửa cùng lúc không bị conflict file.
Ví dụ thực tế: Test case cho luồng đăng nhập
Mình lấy trang đăng nhập làm ví dụ vì đây là tính năng có ở hầu hết app, và cũng là nơi fresher hay bỏ sót nhiều nhất.
Một tính năng đăng nhập "đơn giản" cần ít nhất 8-10 test case. Không phải 2-3.
TC_LOGIN_001 - Happy path (luồng thành công)
Test Case Name : Đăng nhập thành công với email và mật khẩu hợp lệ
Preconditions : Tài khoản [email protected]/Test@1234 đã tồn tại, chưa đăng nhập
Test Data : Email: [email protected] | Mật khẩu: Test@1234
Test Steps :
1. Mở trình duyệt, truy cập https://demo-app.com/login
2. Nhập "[email protected]" vào trường Email
3. Nhập "Test@1234" vào trường Mật khẩu
4. Click nút "Đăng nhập"
Expected Result : Trang chuyển hướng đến /dashboard
Hiển thị tên "Người Dùng Test" ở header góc trên phải
Không còn thấy trang login
TC_LOGIN_003 - Negative case (luồng thất bại)
Test Case Name : Đăng nhập thất bại khi bỏ trống trường Mật khẩu
Preconditions : Đang ở trang /login, chưa điền gì
Test Data : Email: [email protected] | Mật khẩu: (để trống)
Test Steps :
1. Mở trình duyệt, truy cập https://demo-app.com/login
2. Nhập "[email protected]" vào trường Email
3. Bỏ trống trường Mật khẩu
4. Click nút "Đăng nhập"
Expected Result : Không chuyển trang
Hiển thị thông báo đỏ bên dưới trường Mật khẩu:
"Mật khẩu không được để trống"
Con trỏ focus vào trường Mật khẩu
Happy path và negative case đều cần thiết - chỉ test happy path là không đủ
Các test case còn lại cho đăng nhập bạn nên có:
- Sai mật khẩu (mật khẩu đúng format nhưng không khớp)
- Email không tồn tại trong hệ thống
- Email không có ký tự @ (invalid format)
- Mật khẩu có ký tự đặc biệt như
!@#$% - Tài khoản bị khóa/vô hiệu hóa
- Nhấn Enter thay vì click nút
- Đăng nhập thành công rồi nhấn Back trình duyệt
Bạn không cần nhớ hết danh sách này ngay. Cách mình hay làm là tự hỏi: "Nếu mình cố tình phá tính năng này, mình làm gì?" - câu trả lời chính là các negative test case.
