0
0
Lập trình
Sơn Tùng Lê
Sơn Tùng Lê103931498422911686980

Hệ Thống Của Bạn Có Chịu Được Pha Ghi Nhớ Cao Nhất Không?

Đăng vào 4 ngày trước

• 10 phút đọc

Giới thiệu

Khi các cây cầu lớn được xây dựng, các kỹ sư không bao giờ tiết kiệm trong việc thử nghiệm. Họ bắt đầu bằng cách mô phỏng tải trọng cực đại trên các dự án số và mô hình. Sau đó, khi cấu trúc đã hoàn thành, họ thực hiện các bài kiểm tra thực tế với các xe tải nặng và cảm biến được phân bố khắp công trình. Tất cả những điều này không chỉ để đảm bảo cầu có thể đứng vững, mà còn để nó có thể chịu đựng được những tình huống tắc nghẽn tồi tệ nhất.

Hãy nghĩ về máy bay, thang máy, lốp xe… Hầu hết mọi thứ chúng ta sử dụng hàng ngày đều trải qua các bài kiểm tra nghiêm ngặt. Vậy tại sao trong phát triển phần mềm, nhiều người vẫn đặt niềm tin mù quáng vào việc "mọi thứ sẽ ổn"?

Cảnh báo: Không phải lúc nào cũng như vậy và thực tế sẽ trả giá nhanh chóng.


🔥 Khi Mọi Thứ Đổ Vỡ (Ng ngay cả ở Các Doanh Nghiệp Lớn)

Gần đây, trong thời điểm phát hành trước của Nintendo Switch 2, ngay cả những trang web lớn cũng sụp đổ, không thể xử lý được lưu lượng truy cập khổng lồ. Đây không phải là một trường hợp đơn lẻ. Bạn có nhớ lần bạn cố gắng mua vé cho buổi hòa nhạc gần đây không?

Vấn đề thường phát sinh từ sự lạc quan gần như trẻ con: niềm tin rằng tài nguyên máy tính là vô hạn hoặc rằng "các vấn đề về khả năng" là điều của quá khứ. Những người khác lại đổ lỗi cho đội ngũ hạ tầng, bỏ qua thực tế rằng việc đảm bảo khả năng mở rộng và sự phục hồi là trách nhiệm của tất cả mọi người trong nhóm: từ phát triển, kiểm thử, kiến trúc đến sản phẩm.


🧪 Lập Kế Hoạch, Kiểm Tra và Xác Thực: Bộ Ba Quy Tắc Của Sự Ổn Định

Nếu bạn làm trong lĩnh vực công nghệ, bạn cần phải đối mặt với thực tế: lập kế hoạch, kiểm tra và xác thực ứng dụng của bạn cho những thời điểm căng thẳng là điều cần thiết như việc kiểm tra một cây cầu trước khi khánh thành.

Đừng để sản phẩm của bạn sụp đổ đúng lúc nó cần thiết nhất. Đó là lý do tại sao các bài kiểm tra tải là rất quan trọng.


🧱 Kiểm Tra Tải Là Gì?

Kiểm tra tải mô phỏng hành vi của nhiều người dùng truy cập ứng dụng của bạn cùng một lúc, giống như bạn có thể điều khiển, một cách có kiểm soát, tình trạng tắc nghẽn tồi tệ nhất trên "cây cầu số" của mình. Những bài kiểm tra này rất cần thiết để xác định:

  • Các nút thắt về hiệu suất;
  • Các điểm yếu trong kiến trúc;
  • Giới hạn khả năng hoạt động.

Nếu không có chúng, bạn đang phát hành hệ thống của mình mà không có sự chuẩn bị, đánh cược rằng nó sẽ chịu đựng được bất kỳ khối lượng truy cập nào và đánh cược không phải là một chiến lược.

Đầu tư vào kiểm tra tải là đầu tư vào sự tin cậy, ổn định và, cuối cùng, vào trải nghiệm của người dùng, người sẽ không tha thứ cho bạn nếu ứng dụng gặp sự cố chính xác khi họ cần nhất.


📏 Trước Khi Kiểm Tra: Đưa Ra Dự Đoán Đúng

Nhưng hãy chú ý: trước khi kiểm tra, việc ước lượng chính xác khối lượng truy cập bạn muốn mô phỏng là rất quan trọng.

Quá trình này bắt đầu bằng việc phân tích:

  • Các đỉnh sử dụng lịch sử của ứng dụng;
  • Các dự đoán cho các sự kiện đặc biệt (ra mắt lớn, chiến dịch tiếp thị, phản ứng bất ngờ).

Và còn hơn thế nữa: bạn cũng cần xem xét các kịch bản thất bại của hạ tầng, cho dù trong trung tâm dữ liệu của bạn hay trên đám mây.

☁️ Đám mây không phải là bất khả chiến bại: các khu vực có thể bị sập, toàn bộ khu vực có thể không khả dụng trong nhiều giờ. Ứng dụng của bạn cần được chuẩn bị để phân phối lại tải và tiếp tục hoạt động.


🧠 Ví Dụ Thực Tế: Lập Kế Hoạch Tải

Hãy tưởng tượng rằng trang web của bạn, trong một ngày bình thường, có thể chịu đựng 2000 người dùng đồng thời ở đỉnh điểm.
Bây giờ, hãy xem xét một sự kiện đặc biệt (như Black Friday hoặc ra mắt viral) có thể nhân đôi con số này.
Ngoài ra, hãy nghĩ về khả năng xảy ra một sự cố trong một khu vực của đám mây, buộc ứng dụng của bạn phải phân phối lại tải trong chỉ một nửa hạ tầng hiện có.

Trong kịch bản này, bài kiểm tra tải cần mô phỏng:

10.000 người dùng đồng thời, chạy trên 50% cấu trúc hiện tại của bạn.


🛠️ Công Cụ Để Kiểm Tra Tải

Hiện tại, có nhiều công cụ, miễn phí và doanh nghiệp, giúp mô phỏng truy cập đồng thời, đo lường hiệu suất và xác định các điểm yếu.
Trong số những công cụ nổi tiếng, có:

  • Apache JMeter
  • K6
  • Locust
  • Artillery
  • Gatling

Chúng ta sẽ tập trung vào K6, công cụ nhẹ, đơn giản và mạnh mẽ.


🧪 Tạo Một Endpoint Để Kiểm Tra Với Node.js

Để kiểm tra với K6, trước tiên chúng ta cần khởi động một dịch vụ đơn giản với Node.js trả về mã trạng thái 200.
Tạo file server.js với nội dung sau:

javascript Copy
const http = require('http');

const server = http.createServer((req, res) => {
  res.writeHead(200, { 'Content-Type': 'text/plain' });
  res.end('OK');
});

const port = 3000;
server.listen(port, () => {
  console.log(`Server running at http://localhost:${port}`);
});

Chạy bằng:

bash Copy
node server.js

Bây giờ chúng ta có một endpoint địa phương trên cổng 3000 (hoặc cổng mà terminal hiển thị).


⚙️ Cài Đặt K6

Để sử dụng K6, chúng ta cần cài đặt như sau.

Linux (Ubuntu):

bash Copy
sudo apt update
sudo apt install gnupg ca-certificates
sudo mkdir -m0755 -p /etc/apt/keyrings
curl -fsSL https://dl.k6.io/key.gpg | sudo gpg --dearmor -o /etc/apt/keyrings/k6-archive-keyring.gpg
echo "deb [signed-by=/etc/apt/keyrings/k6-archive-keyring.gpg] https://dl.k6.io/deb stable main" | sudo tee /etc/apt/sources.list.d/k6.list
sudo apt update
sudo apt install k6

Mac:

bash Copy
brew install k6

Windows (với Chocolatey):

bash Copy
choco install k6

🚀 Bài Kiểm Tra Tải Đầu Tiên Với 50 Người Dùng

Tạo file load-test.js:

javascript Copy
import http from 'k6/http';
import { check } from 'k6'; 

export const options = {
    vus: 50,
    duration: '30s',
};

export default function () {
    const res = http.get('http://localhost:3000');
    check(res, { 'status là 200': (r) => r.status === 200 });
}

Chạy với:

bash Copy
k6 run load-test.js

📊 Giải Thích Kết Quả Từ K6

Khi thực hiện, bạn sẽ nhận được một kết quả như hình dưới đây:

Trong đó bạn có thể tìm thấy:

  • checks_total / succeeded / failed: Kiểm tra số lượng kiểm tra đã thực hiện, bao nhiêu đã thành công và bao nhiêu đã thất bại. ✅ Trong trường hợp này: 1.675.407 kiểm tra với 100% thành công.
  • http_req_duration: Thời gian tổng thể của các yêu cầu HTTP (từ khi gửi đến khi nhận được phản hồi).
    • avg: trung bình tổng thể (850.51μs, xuất sắc).
    • med: trung vị (618μs).
    • max: thời gian tối đa (90.91ms).
    • p(90)p(95): phần trăm (ví dụ: 95% các yêu cầu mất đến 1.89ms).
  • http_req_failed: Tỷ lệ thất bại trong các yêu cầu. ✅ Ở đây: 0.00%, không có thất bại.
  • iteration_duration: Thời gian của mỗi vòng lặp hoàn chỉnh (yêu cầu + logic script).
  • vus / vus_max: Số lượng người dùng ảo đang hoạt động (ở đây là 50).
  • data_received / data_sent: Khối lượng dữ liệu đã truyền tải trong quá trình kiểm tra (283MB nhận được, 139MB gửi đi).
  • http_reqs: Tổng số yêu cầu thực hiện: 1.675.407 > Tỷ lệ: ~55.843 yêu cầu/giây. ✅ Kết quả cho thấy endpoint đã phản hồi nhanh chóng, không có lỗi, ngay cả dưới tỷ lệ yêu cầu đồng thời cao.

📈 Ramp Load: Tại Sao Không Phải Mọi Tình Huống Đều Đến Đột Ngột

Trong nhiều kịch bản, không chỉ cần thử nghiệm xem ứng dụng có hỗ trợ một khối lượng nhất định ngay lập tức. Để thực sự hiểu cách thức hệ thống phản ứng dưới áp lực khác nhau, việc áp dụng ramp load trong các bài kiểm tra là rất quan trọng.

Loại tiếp cận này cho phép quan sát cách thức ứng dụng phản ứng khi số lượng người dùng tăng dần, đồng thời rất cần thiết để đánh giá hiệu quả của tính đàn hồi (tự động mở rộng) và xác định các nút thắt có thể xảy ra trong suốt đường cong tăng trưởng.

Hãy tạo một mã mới dựa trên ví dụ trước mà chúng ta sẽ thêm một ramp load. Trong bài kiểm tra mới này, chúng ta sẽ:

  • Mô phỏng 50 người dùng ảo trong 30 giây đầu tiên;
  • Tăng lên 100 người dùng trong 30 giây tiếp theo;
  • Giữ 100 người dùng trong thêm 30 giây;
  • Và cuối cùng, giảm tải dần cho đến không trong suốt 30 giây. Trong các bài kiểm tra thực tế, lý tưởng là thời gian này nên lớn hơn và được điều chỉnh theo thực tế của hệ thống bạn, phản ánh đúng các đỉnh mong đợi của việc sử dụng.

Ví dụ với Ramp Load
Tạo file ramp-load-test.js với nội dung sau:

javascript Copy
import http from 'k6/http';
import { check } from 'k6';

export const options = {
    stages: [
        { duration: '30s', target: 50 },
        { duration: '30s', target: 100 },
        { duration: '30s', target: 100 },
        { duration: '30s', target: 0 },
    ],
};

export default function () {
    const res = http.get('http://localhost:3000');
    check(res, { 'status là 200': (r) => r.status === 200 });
}

Chạy với:

bash Copy
k6 run ramp-load-test.js

Những bài kiểm tra này nên được thực hiện với thời gian tương xứng với kịch bản thực tế, tăng dần, duy trì và giảm tải giống như trong các sự kiện thực tế.


🛡️ Sử Dụng Công Cụ Quan Sát

Các báo cáo từ K6 rất tốt, nhưng để chẩn đoán sâu hơn, hãy kết hợp các bài kiểm tra với các công cụ như:

  • New Relic
  • Datadog
  • Dynatrace
  • Elastic Stack
  • Splunk

Chúng cung cấp thông tin về việc sử dụng CPU, bộ nhớ, độ trễ giữa các dịch vụ, Apdex, v.v. Điều này biến dữ liệu thành quyết định thực tế về kiến trúc và kinh doanh.


🚨 Khi Bạn Không Biết Đỉnh Điểm Là Gì?

Trong nhiều trường hợp, đặc biệt trong quá trình phát triển các ứng dụng mới, chúng ta không có số lượng chính xác người dùng để mô phỏng trong các bài kiểm tra tải. Trong những kịch bản này, nên tiến hành một bài kiểm tra stress cho đến khi xác định điểm bão hòa của hệ thống, đúng là sự khác biệt chính giữa kiểm tra tải và kiểm tra stress là kiểm tra đầu tiên được sử dụng để xác nhận ứng dụng có hỗ trợ một tải trọng nhất định hay không, trong khi cái sau xác định đến mức nào ứng dụng có thể xử lý tải tăng lên, xác định thời điểm nó bắt đầu thất bại hoặc giảm hiệu suất.

Loại kiểm tra này cho phép cung cấp cho nhóm kinh doanh một cái nhìn rõ ràng về giới hạn hiện tại của ứng dụng, giúp đưa ra quyết định về hạ tầng, lộ trình cải tiến và giao tiếp với người dùng.

Đúng là sự khác biệt chính giữa kiểm tra tải và kiểm tra stress nằm ở mục tiêu:

  • Kiểm tra tải tìm cách xác nhận liệu ứng dụng có hỗ trợ một tải trọng nhất định trong các tham số chấp nhận được hay không.
  • Trong khi kiểm tra stress tập trung vào việc khám phá giới hạn mà ứng dụng có thể xử lý, xác định thời điểm bắt đầu thất bại hoặc giảm hiệu suất. Để thực hiện một bài kiểm tra tải trong K6, chỉ cần tăng số lượng VUs và nếu cần, tăng số lượng ramp để hiểu hành vi ở mỗi giai đoạn.

💡 Mẹo Cuối: Tính Đàn Hồi Cũng Là Giảm Tải

Các môi trường đàn hồi nên quay trở lại bình thường sau đỉnh điểm. Nếu không giải phóng tài nguyên, bạn có thể gặp phải:

  • Tăng cường tài nguyên;
  • Sử dụng máy không cần thiết;
  • Và, tất nhiên, hóa đơn đám mây đáng sợ hơn cả lỗi trong sản xuất 👻💸

🧩 Kết Luận: Kiểm Tra Là Ngăn Ngừa, Không Là Khắc Phục

Mọi cây cầu, máy bay hay thang máy đều phải trải qua kiểm tra trước khi được sử dụng bởi hàng triệu người. Trong thế giới số, tư duy cần phải tương tự. Đừng đợi đến lúc hỗn loạn để phát hiện ra nơi ứng dụng của bạn thất bại.

Kiểm tra tải không phải là “xa xỉ của các doanh nghiệp lớn”, mà là thực hành cần thiết cho bất kỳ hệ thống nào coi trọng sự ổn định, danh tiếng và trải nghiệm của người dùng. Bỏ qua điều này là chấp nhận rủi ro sụp đổ khi cần thiết nhất.

Gợi ý câu hỏi phỏng vấn
Không có dữ liệu

Không có dữ liệu

Bài viết được đề xuất
Bài viết cùng tác giả

Bình luận

Chưa có bình luận nào

Chưa có bình luận nào