Lab 9.5 - Xây dựng hệ thống Centralized Logging với Fluent Bit, Loki và Grafana
Phần 5 - Điều tra sự cố thực tế với Metrics, Alerts và Logs
Đến thời điểm này, chúng ta đã xây dựng được một hệ thống Observability gần như hoàn chỉnh:
- Prometheus thu thập Metrics.
- Grafana hiển thị Dashboard.
- Alertmanager gửi cảnh báo.
- Fluent Bit thu thập log.
- Loki lưu trữ log.
Nhưng một câu hỏi quan trọng vẫn còn bỏ ngỏ:
Làm thế nào để sử dụng tất cả những công cụ này để điều tra một sự cố thực tế?
Trong phần này, chúng ta sẽ mô phỏng một sự cố Production trên hệ thống Todo và đi qua toàn bộ quy trình mà một DevOps Engineer thường thực hiện.
Mục tiêu của phần này
Sau khi hoàn thành phần này, bạn sẽ:
- Hiểu quy trình xử lý sự cố trong Production.
- Kết hợp Alert, Metrics và Logs.
- Sử dụng LogQL để tìm nguyên nhân gốc (Root Cause).
- Debug ứng dụng thay vì chỉ quan sát Dashboard.
Tình huống thực tế
Một buổi sáng thứ Hai, Product Owner gửi tin nhắn:
"Người dùng phản ánh API tạo Todo rất chậm, thỉnh thoảng còn báo lỗi."
Đồng thời, DevOps nhận được Email từ Alertmanager:
🚨 ALERT
Alert Name:
HighHTTP5xxRate
Severity:
Critical
Service:
todo-api
Namespace:
todo-app
Đây là lúc quy trình điều tra bắt đầu.
Bước 1. Kiểm tra Dashboard
Mở Grafana Dashboard đã tạo ở Lab 7.
Quan sát các Metrics:
CPU
↓
32%
Memory
↓
55%
Request Rate
↓
120 req/s
Request Latency
↓
4.8 s
HTTP 500
↓
Tăng liên tục
Từ Dashboard chúng ta nhận thấy:
- CPU không cao.
- Memory còn nhiều.
- Request Rate bình thường.
- Nhưng Latency và HTTP 500 tăng mạnh.
Điều này cho thấy:
Ứng dụng vẫn hoạt động nhưng đang gặp lỗi bên trong.
Dashboard giúp xác định điều gì đang xảy ra, nhưng chưa thể cho biết nguyên nhân.
Bước 2. Kiểm tra Alert
Mở:
Alerting
↓
Alert Rules
Hoặc:
Alertmanager
Quan sát:
HighHTTP5xxRate
Status
FIRING
Thông tin Alert:
Started
08:15
Severity
Critical
Namespace
todo-app
Service
todo-api
Nhờ Alert, DevOps biết:
- Lỗi vẫn đang tiếp diễn.
- Không phải sự cố đã xảy ra rồi tự biến mất.
- Cần điều tra ngay.
Bước 3. Chuyển sang Logs
Mở:
Grafana
↓
Explore
↓
Loki
Chúng ta chỉ muốn xem log của Backend:
{namespace="todo-app"}
Kết quả:
INFO Application started
GET /api/todos
POST /api/todos
ERROR Database timeout
Ngay lập tức chúng ta đã thấy nhiều log ERROR.
Bước 4. Chỉ lấy log lỗi
Thay vì xem tất cả log, lọc riêng log chứa từ khóa ERROR.
{namespace="todo-app"} |= "ERROR"
Ví dụ:
ERROR Database connection timeout
ERROR Cannot get JDBC Connection
ERROR Transaction rollback
ERROR Failed to execute SQL
Lượng log đã giảm rất nhiều.
DevOps chỉ cần tập trung vào những dòng thực sự quan trọng.
Bước 5. Xác định nguyên nhân
Quan sát kỹ hơn:
ERROR
org.postgresql.util.PSQLException
Connection timed out
Hoặc:
ERROR
HikariPool
Connection is not available
Đến đây chúng ta đã có manh mối.
Ứng dụng không bị lỗi vì:
- CPU.
- Memory.
- Kubernetes.
Mà vì:
Backend không lấy được kết nối tới PostgreSQL.
Đây chính là Root Cause.
Bước 6. Kiểm tra PostgreSQL
Quay lại Kubernetes:
kubectl get pods -n todo-app
Ví dụ:
NAME
todo-postgres
Running
Pod vẫn chạy.
Kiểm tra tiếp:
kubectl logs \
todo-postgres \
-n todo-app
Ví dụ:
FATAL
remaining connection slots are reserved
Hoặc:
too many connections
Lúc này nguyên nhân đã rõ ràng:
Ứng dụng tạo quá nhiều kết nối tới Database khiến PostgreSQL từ chối kết nối mới.
Bước 7. Đối chiếu Metrics
Quay lại Dashboard.
Quan sát:
CPU
30%
Memory
50%
Không có gì bất thường.
Điều này chứng minh:
Không phải mọi sự cố đều thể hiện qua CPU hoặc Memory.
Nếu chỉ nhìn Dashboard Infrastructure, rất khó phát hiện vấn đề.
Bước 8. Khắc phục sự cố
Sau khi xác định nguyên nhân, DevOps có thể:
- Tăng kích thước Connection Pool.
- Kiểm tra Connection Leak.
- Tối ưu Transaction.
- Khởi động lại Database nếu cần.
Sau khi khắc phục:
Dashboard:
Latency
4.8 s
↓
120 ms
HTTP 500:
85/min
↓
0/min
Alert:
Resolved
Hệ thống hoạt động bình thường trở lại.
Mô phỏng một sự cố khác
Chúng ta sẽ thử tạo lỗi để quan sát toàn bộ quy trình.
Tắt PostgreSQL
kubectl scale deployment todo-postgres \
--replicas=0 \
-n todo-app
Kiểm tra:
kubectl get pods -n todo-app
Bạn sẽ thấy Pod PostgreSQL biến mất.
Gửi Request
curl http://localhost:8080/api/todos
Ứng dụng sẽ trả về lỗi.
Ví dụ:
HTTP/1.1 500
Quan sát Dashboard
Request Latency tăng.
HTTP 500 tăng.
Request Rate giảm.
Quan sát Alert
Sau khoảng thời gian cấu hình (for: 2m hoặc for: 5m), Alert chuyển sang:
Pending
↓
Firing
Alertmanager gửi Email hoặc Slack.
Quan sát Logs
Mở Grafana.
Query:
{namespace="todo-app"} |= "ERROR"
Ví dụ:
ERROR
Connection refused
postgres:5432
Hoặc:
ERROR
Failed to connect to PostgreSQL
Chỉ trong vài phút, DevOps đã xác định được nguyên nhân.
Khôi phục PostgreSQL
kubectl scale deployment todo-postgres \
--replicas=1 \
-n todo-app
Đợi Pod Running:
kubectl get pods -n todo-app
Sau vài phút:
- HTTP 500 giảm.
- Alert chuyển sang Resolved.
- Logs không còn xuất hiện lỗi mới.
Quy trình điều tra sự cố hoàn chỉnh
Đây là quy trình mà nhiều đội ngũ DevOps áp dụng trong môi trường Production.
Người dùng báo lỗi
│
▼
Alertmanager gửi cảnh báo
│
▼
Kiểm tra Grafana Dashboard
│
▼
Xác định Metrics bất thường
│
▼
Mở Grafana Explore
│
▼
Truy vấn Log bằng Loki
│
▼
Tìm Root Cause
│
▼
Khắc phục sự cố
│
▼
Alert chuyển Resolved
Metrics, Alerts và Logs bổ sung cho nhau như thế nào?
| Thành phần | Trả lời câu hỏi |
|---|---|
| Metrics | Hệ thống đang hoạt động như thế nào? |
| Alerts | Khi nào cần hành động? |
| Logs | Nguyên nhân của sự cố là gì? |
Không có thành phần nào có thể thay thế hoàn toàn thành phần còn lại.
Chỉ khi kết hợp cả ba, chúng ta mới có thể điều tra và xử lý sự cố một cách hiệu quả.
Kết quả đạt được
Sau phần này, bạn đã biết cách:
- Điều tra một sự cố Production từ đầu đến cuối.
- Kết hợp Dashboard, Alert và Logs.
- Sử dụng LogQL để tìm Root Cause.
- Phân biệt vai trò của Metrics, Alerts và Logs.
- Áp dụng quy trình xử lý sự cố giống các đội ngũ DevOps trong thực tế.
Đến đây, chúng ta không chỉ có một hệ thống Monitoring hay Logging riêng lẻ, mà đã xây dựng được một nền tảng Observability hoàn chỉnh, nơi Metrics giúp phát hiện dấu hiệu bất thường, Alerts chủ động thông báo sự cố và Logs cung cấp bằng chứng để xác định nguyên nhân gốc của vấn đề. Đây cũng chính là mục tiêu cuối cùng của chuỗi Kubernetes từ Zero đến Production.
All Rights Reserved