Một thí nghiệm kiểm thử tải gần đây xem xét một máy đơn lẻ có thể xử lý bao nhiêu yêu cầu HTTP mỗi giây đã khơi dậy cuộc thảo luận trong cộng đồng về các lựa chọn lưu trữ cơ sở dữ liệu, connection pooling, và giới hạn thực sự của phần cứng hiện đại. Bài kiểm thử sử dụng thiết lập cơ bản với PostgreSQL chứa hơn một triệu bản ghi và đo lường hiệu suất trên các profile tải khác nhau.
Cấu hình Cơ sở dữ liệu:
- PostgreSQL với hơn 1 triệu bản ghi
- Hikari Connection Pool : 10 kết nối ban đầu, có thể mở rộng lên 20
- Bộ nhớ khối bên ngoài DigitalOcean (không phải hệ thống tập tin cục bộ)
- Giới hạn kết nối mặc định của PostgreSQL : ~100 kết nối
Cấu Hình Lưu Trữ Cơ Sở Dữ Liệu Gây Ra Nhiều Câu Hỏi
Thiết lập kiểm thử sử dụng external block storage cho cơ sở dữ liệu thay vì lưu trữ filesystem cục bộ, điều này đã thu hút sự chú ý của nhiều developer. Lựa chọn này ảnh hưởng đáng kể đến hiệu suất vì block storage tạo ra độ trễ mạng cho mọi thao tác cơ sở dữ liệu. Các thành viên cộng đồng chỉ ra rằng việc sử dụng bất cứ thứ gì ngoài filesystem cục bộ cho cơ sở dữ liệu thường được khuyến cáo tránh đối với các ứng dụng quan trọng về hiệu suất.
Tuy nhiên, môi trường cloud thường yêu cầu sự đánh đổi này. Block storage cung cấp độ tin cậy và tính bền vững dữ liệu khi các instance có thể bị lỗi bất cứ lúc nào, trong khi lưu trữ cục bộ mang lại hiệu suất tốt hơn nhưng có nguy cơ mất dữ liệu. Sự căng thẳng cơ bản này giữa hiệu suất và độ tin cậy định hình nhiều quyết định kiến trúc trong các ứng dụng hiện đại.
Các Hạn Chế Connection Pool Trở Nên Rõ Ràng
Bài kiểm thử tiết lộ các nút thắt trong việc xử lý kết nối cơ sở dữ liệu, với thiết lập sử dụng Hikari Connection Pool được cấu hình cho 10 kết nối ban đầu có thể mở rộng lên 20. Phân tích của cộng đồng cho thấy kích thước connection pool tương đối nhỏ này có thể đã hạn chế hiệu suất trước khi đạt đến giới hạn phần cứng thực tế.
Giới hạn kết nối mặc định của PostgreSQL khoảng 100 kết nối đồng thời sẽ cung cấp đủ không gian dự phòng khi được pool hợp lý. Cuộc thảo luận nhấn mạnh rằng với hàng nghìn yêu cầu tiềm năng mỗi giây, việc định kích thước connection pool trở nên quan trọng để tránh các nút thắt nhân tạo.
Góc Nhìn Phần Cứng Thách Thức Các Giả Định
Bài kiểm thử mô tả một máy 8-CPU, 16GB RAM là khổng lồ, điều này đã thu hút sự chỉ trích từ các developer quen thuộc với khả năng phần cứng hiện đại. Các máy tiêu dùng cao cấp ngày nay có thể hỗ trợ 512GB RAM, trong khi các hệ thống doanh nghiệp mở rộng lên 20+ terabyte bộ nhớ và hàng trăm core.
Các máy khổng lồ ngày nay có 20+ TB RAM và hàng trăm core. Ngay cả các máy tiêu dùng cao cấp cũng có thể có 512GB RAM!
Khoảng cách quan điểm này cho thấy rằng nhiều ứng dụng có thể mở rộng quy mô vượt xa các giả định hiện tại bằng cách đơn giản nâng cấp lên các máy đơn lẻ mạnh mẽ hơn thay vì áp dụng các kiến trúc phân tán phức tạp.
Cấu hình máy kiểm thử:
- Máy nhỏ: 4 lõi CPU, bộ nhớ 4 GiB
- Máy trung bình: 4 vCPU, bộ nhớ 4 GiB
- Máy lớn: 8 vCPU, bộ nhớ 4 GiB
- Máy "khổng lồ": 8 CPU, bộ nhớ 16 GB
Hạn Chế Phương Pháp Kiểm Thử
Phương pháp kiểm thử tải sử dụng rate limiting nhân tạo trong mã client, điều mà một số thành viên cộng đồng xác định có thể làm lệch kết quả. Bài kiểm thử cố ý giới hạn số yêu cầu mỗi giây thay vì đo lường thông lượng bền vững tối đa, khiến việc xác định giới hạn hiệu suất thực sự trở nên khó khăn.
Ngoài ra, việc chạy cả ứng dụng và cơ sở dữ liệu trên cùng một máy tạo ra sự cạnh tranh tài nguyên mà sẽ không tồn tại trong các triển khai production điển hình. Mặc dù điều này kiểm thử toàn bộ hệ thống dưới các hạn chế tài nguyên, nhưng nó không tách biệt hiệu suất application server khỏi hiệu suất cơ sở dữ liệu.
Thí nghiệm chứng minh rằng các máy đơn lẻ có thể xử lý tải đáng kể, nhưng các con số cụ thể có thể không phản ánh các cấu hình được tối ưu hóa. Đối với nhiều ứng dụng hiện đang sử dụng các kiến trúc microservices phức tạp để xử lý chỉ vài yêu cầu mỗi giây, ngay cả những kết quả thận trọng này cũng cho thấy các giải pháp đơn giản hơn có thể đủ.
Tham khảo: Load Testing: how many HTTP requests/second can a Single Machine handle?