Nội dung

DaiPhan

DaiPhan

Full-Stack Developer

Full-stack developer passionate about modern web technologies, best practices, and sharing knowledge with the community.

Skills & Expertise

JavaScript TypeScript React Node.js DevOps
150+
Articles
50k+
Readers
4.9
Rating

Kiểm thử đơn vị trong JavaScript: Best Practices và Công Cụ

Hướng dẫn chi tiết về kiểm thử đơn vị trong JavaScript với Jest, Testing Library và best practices

Kiểm thử đơn vị trong JavaScript: Best Practices và Công Cụ

Kiểm thử đơn vị (Unit Testing) là một phần không thể thiếu trong quy trình phát triển phần mềm hiện đại. Trong bài viết này, chúng ta sẽ tìm hiểu cách viết kiểm thử đơn vị hiệu quả cho JavaScript.

1. Tại sao cần kiểm thử đơn vị?

Lợi ích của unit testing:

  • Phát hiện bug sớm: Giúp phát hiện lỗi ngay từ giai đoạn development
  • Tăng độ tin cậy: Code được test kỹ lưỡng trước khi deploy
  • Dễ refactor: Có thể thay đổi code mà không sợ break functionality
  • Documentation sống: Test cases cho thấy cách sử dụng và expected behavior
  • Tiết kiệm thời gian: Giảm thời gian debug và manual testing

2. Setup môi trường testing

Cài đặt Jest

npm install --save-dev jest @types/jest

Cấu hình Jest trong package.json

{
  "scripts": {
    "test": "jest",
    "test:watch": "jest --watch",
    "test:coverage": "jest --coverage"
  },
  "jest": {
    "testEnvironment": "node",
    "collectCoverageFrom": [
      "src/**/*.js",
      "!src/**/*.test.js"
    ]
  }
}

3. Viết test case cơ bản

Ví dụ 1: Test function đơn giản

// math.js
function add(a, b) {
  return a + b;
}

function multiply(a, b) {
  return a * b;
}

module.exports = { add, multiply };
// math.test.js
const { add, multiply } = require('./math');

describe('Math functions', () => {
  test('adds 1 + 2 to equal 3', () => {
    expect(add(1, 2)).toBe(3);
  });

  test('multiplies 3 * 4 to equal 12', () => {
    expect(multiply(3, 4)).toBe(12);
  });

  test('handles negative numbers', () => {
    expect(add(-1, -2)).toBe(-3);
    expect(multiply(-2, 3)).toBe(-6);
  });
});

4. Best Practices cho Unit Testing

1. ARRANGE - ACT - ASSERT Pattern

test('follows AAA pattern', () => {
  // ARRANGE - Setup test data
  const input = [1, 2, 3, 4, 5];
  const expected = 15;
  
  // ACT - Execute the function
  const result = sumArray(input);
  
  // ASSERT - Verify the result
  expect(result).toBe(expected);
});

2. Test naming convention

  • Test name nên mô tả rõ ràng what is being tested
  • Sử dụng format: should [expected behavior] when [condition]
test('should return error when email is invalid', () => {
  // test implementation
});

3. Keep tests independent

  • Mỗi test nên chạy độc lập
  • Không chia sẻ state giữa các test
  • Sử dụng beforeEachafterEach để cleanup

4. Test edge cases

  • Test với input hợp lệ và không hợp lệ
  • Test với boundary values
  • Test error conditions

5. Coverage và Quality Metrics

Chạy test với coverage

npm run test:coverage

Target coverage:

  • Statements: > 80%
  • Branches: > 75%
  • Functions: > 80%
  • Lines: > 80%

💡 Lưu ý: 100% coverage không có nghĩa là code không có bug. Focus vào quality của test cases chứ không chỉ quantity.

6. Kết luận

Unit testing là investment cho quality và maintainability của codebase. Bắt đầu với:

  1. Setup Jest cho project của bạn
  2. Viết test cho critical business logic
  3. Follow best practices và AAA pattern
  4. Monitor coverage nhưng focus vào test quality

🔑 Key Takeaway: Good tests giúp bạn confident khi refactor, thêm features, và deploy code. Đó là foundation cho sustainable development.


Bài viết này là phần đầu tiên trong series về testing. Trong các bài tiếp theo, chúng ta sẽ explore integration testing, e2e testing, và performance testing.