---
name: GenerateUnitTest
description: Hướng dẫn tạo Unit Test cô lập (tốc độ cao) sử dụng Mocking (Moq hoặc NSubstitute).
---

# GenerateUnitTest Skill

Khi user yêu cầu tạo **Unit Test** cho một class/method, bạn cần tuân thủ các nguyên tắc sau để sinh ra code test:

## Mục đích
- Chỉ test duy nhất 1 class/method.
- Bỏ qua hoàn toàn Database thật, Redis hay HTTP.
- Tốc độ chạy cực nhanh.

## 1. Với CQRS Handlers hoặc Services
- **Nhận diện Dependencies:** Tự động nhận diện các Interface (ví dụ: `IRepository`, `IUnitOfWork`, `ILogger`, `IMediator`) được inject vào constructor.
- **Tạo Mock Object:** Sử dụng thư viện Mocking (như `Moq` hoặc `NSubstitute`) để tạo instance giả của các Interface này.
- **Kịch bản Test (Arrange - Act - Assert):**
  - **Arrange:** Cấp data giả (Mock data) cho các hàm của Interface.
  - **Act:** Gọi hàm thực thi (ví dụ `Handle()` của CQRS hoặc các method của Service).
  - **Assert:** Kiểm tra kết quả trả về, HOẶC verify xem một method của Mock object có được gọi đúng số lần không (ví dụ kiểm tra xem `_repository.AddAsync()` có được gọi không), HOẶC kiểm tra xem nó có ném ra `ValidationException` khi input sai không.

## 2. Với Domain Entities
- **Mục tiêu:** Kiểm tra các logic kinh doanh, tính toán nội bộ của Entity.
- **Kịch bản:**
  - Khởi tạo Entity với các trạng thái cụ thể.
  - Gọi method thay đổi trạng thái hoặc tính toán (ví dụ: `Order.CalculateTotal()`).
  - Kiểm tra xem giá trị biến đổi có đúng với quy tắc nghiệp vụ không (ví dụ: `Total` phải bằng `Price * Quantity`).

## Định dạng file đầu ra
- **Đường dẫn:** Đặt trong project `tests/MyNewProjectName.UnitTests/...` (tương ứng với thư mục gốc của class bị test).
- **Tên file:** `[ClassName]Tests.cs` (ví dụ: `CreateOrderCommandHandlerTests.cs`).
