Xử lý sự cố khi node TServer bị mất hoặc treo
Trong môi trường Kubernetes, pod chứa TServer (tserver) có thể bị lỗi, treo hoặc bị OOM Killer giết chết. YugabyteDB tự động phát hiện và chuyển hướng lưu lượng, nhưng admin cần can thiệp để khôi phục trạng thái ổn định.
Đầu tiên, xác định pod TServer đang gặp sự cố bằng cách liệt kê tất cả pod trong namespace.
kubectl get pods -n yugabyte -o wide | grep tserver
Kết quả mong đợi: Danh sách các pod, trong đó pod lỗi có trạng thái CrashLoopBackOff, Error, hoặc Terminating.
Nếu pod ở trạng thái CrashLoopBackOff, cần xem log cuối cùng để biết nguyên nhân.
kubectl logs -n yugabyte --previous
Kết quả mong đợi: Log cuối cùng trước khi crash, thường chứa thông báo về OOM (Out Of Memory), lỗi disk I/O, hoặc lỗi khởi động cấu hình.
Để mô phỏng sự cố mất node (node failure) và kiểm tra khả năng tự phục hồi (self-healing), hãy xóa mạnh tay một pod TServer đang chạy.
kubectl delete pod -n yugabyte --force --grace-period=0
Kết quả mong đợi: Kubernetes sẽ tự động tạo lại pod mới. YugabyteDB sẽ tự động phân phối lại các tablet (tablet redistribution) sang các node còn lại để đảm bảo dữ liệu không bị mất.
Verify quá trình tự phục hồi bằng cách kiểm tra trạng thái của master và tserver.
ycsh -u yugabyte -p yugabyte -c "status"
Kết quả mong đợi: Thông báo "Cluster is healthy" sau vài phút, với số lượng tablet đã được cân bằng lại (tablet count).
Phân tích log YugabyteDB để tìm nguyên nhân lỗi kết nối
Log của YugabyteDB được lưu trữ trong các container. Khi gặp lỗi kết nối từ ứng dụng (Connection refused, Timeout), cần phân tích log của TServer và Master để xác định nguyên nhân.
Định vị file log cụ thể của TServer trên pod đang gặp sự cố.
kubectl exec -it -n yugabyte -- cat /var/lib/ysql/state/tserver/log/yugabyte-tserver.log | tail -n 100
Kết quả mong đợi: 100 dòng log cuối cùng của TServer. Tìm các từ khóa "Error", "Exception", hoặc "Timeout".
Tìm kiếm cụ thể các lỗi liên quan đến kết nối TCP hoặc RPC failure.
kubectl exec -it -n yugabyte -- grep -i "connection refused\|timeout\|rpc error" /var/lib/ysql/state/tserver/log/yugabyte-tserver.log | tail -n 20
Kết quả mong đợi: Các dòng log chỉ rõ lỗi kết nối, ví dụ: "Connection refused from " hoặc "Timeout waiting for response from master".
Nếu lỗi là do mất kết nối với Master, cần kiểm tra log của Master để xem Master có phát hiện node đó là không còn tồn tại (dead) hay không.
kubectl exec -it -n yugabyte -- cat /var/lib/ysql/state/master/log/yugabyte-master.log | grep -i "tserver.*down\|heartbeat.*missed"
Kết quả mong đợi: Log xác nhận Master đã đánh dấu TServer đó là "dead" sau khi không nhận được heartbeat trong khoảng thời gian cấu hình.
Verify lại bằng cách kiểm tra trạng thái của các tablet trên TServer đó trong console của Master.
ycsh -u yugabyte -p yugabyte -c "tserver_status"
Kết quả mong đợi: Danh sách các tserver, node lỗi sẽ có trạng thái "UNREACHABLE" hoặc "DOWN".
Tối ưu hóa cấu hình JVM và thread pool cho TServer
Hiệu năng của YugabyteDB phụ thuộc lớn vào cấu hình JVM (Java Virtual Machine) và số lượng thread xử lý. Mặc định có thể không phù hợp với workload nặng hoặc tài nguyên Kubernetes hạn chế.
Chỉnh sửa giá trị heap memory cho TServer trong file Helm values. Điều này quan trọng để tránh OOM khi xử lý dữ liệu lớn.
helm upgrade yugabyte yugabyte/yugabyte --set tserver.heapSize=4Gi --set tserver.heapNewSize=1Gi -n yugabyte
Kết quả mong đợi: Helm thực hiện upgrade, Kubernetes sẽ restart các pod TServer để áp dụng cấu hình mới.
Tối ưu hóa số lượng thread cho TServer để tăng khả năng xử lý đồng thời (concurrency). Mặc định là 20, có thể tăng lên tùy theo số CPU.
helm upgrade yugabyte yugabyte/yugabyte --set tserver.threadPoolSize=40 -n yugabyte
Kết quả mong đợi: Pod TServer restart và khởi động với 40 thread worker.
Để áp dụng các tham số JVM nâng cao hơn (như GC algorithm), cần chỉnh sửa file config trong container. Tạo file config tùy chỉnh và mount vào container.
Đường dẫn file config: /etc/yugabyte/conf.tserver trong container.
Nội dung file config (tạo file trên local và áp dụng vào deployment):
cat
Kết quả mong đợi: File config được tạo thành công trên local machine.
Áp dụng file config này vào Kubernetes bằng cách tạo ConfigMap và tham chiếu trong Helm values hoặc chỉnh sửa Deployment trực tiếp (ở đây dùng cách patch deployment để minh họa nhanh).
kubectl create configmap tserver-jvm-config -n yugabyte --from-file=/tmp/tserver-jvm-config
Kết quả mong đợi: ConfigMap được tạo trong namespace yugabyte.
Mount config này vào container TServer để override mặc định. Lưu ý: Cần chỉnh sửa Helm values để mount volume này vào đường dẫn /etc/yugabyte/conf.tserver.
helm upgrade yugabyte yugabyte/yugabyte --set-file tserver.configOverride=/tmp/tserver-jvm-config -n yugabyte
Kết quả mong đợi: Helm áp dụng cấu hình, TServer khởi động lại với các tham số JVM tùy chỉnh.
Verify cấu hình JVM đang chạy bằng cách vào container và kiểm tra.
kubectl exec -it -n yugabyte -- jps -l
Kết quả mong đợi: Danh sách tiến trình Java, chứng tỏ JVM đang chạy. Kiểm tra heap size bằng:
kubectl exec -it -n yugabyte -- jstat -gc | head -n 1
Kết quả mong đợi: Các giá trị heap (S0, S1, Ed, O, M, YGC, YGCT, FGCT) phản ánh dung lượng heap đã cấu hình.
Xử lý tình trạng data skew và các vấn đề về phân vùng (sharding)
Data skew xảy ra khi dữ liệu không được phân bổ đều giữa các tablet, dẫn đến một số node quá tải trong khi các node khác nhàn rỗi. YugabyteDB tự động cân bằng (tablet rebalancing), nhưng cần can thiệp nếu skew quá lớn.
Kiểm tra sự phân bổ tablet trên các TServer để phát hiện skew.
ycsh -u yugabyte -p yugabyte -c "tablet_server_status"
Kết quả mong đợi: Bảng hiển thị số lượng tablet trên mỗi tserver. Nếu chênh lệch lớn (ví dụ: node A có 100 tablet, node B có 10 tablet), đó là dấu hiệu của skew.
Kích hoạt thủ tục cân bằng tablet thủ công nếu cơ chế tự động chưa kịp xử lý.
ycsh -u yugabyte -p yugabyte -c "rebalance_tablets"
Kết quả mong đợi: YugabyteDB bắt đầu di chuyển các tablet từ node quá tải sang node nhẹ hơn. Quá trình này diễn ra trong background.
Đối với các bảng có sharding không đồng đều (ví dụ: partition key là timestamp hoặc ID tự tăng), cần xem lại lược đồ (schema) hoặc sử dụng composite key.
Ví dụ: Thay vì dùng chỉ 1 column làm partition key, hãy thêm một column ngẫu nhiên hoặc hash.
ALTER TABLE orders ADD COLUMN shard_key UUID DEFAULT gen_random_uuid();
Kết quả mong đợi: Column mới được thêm vào bảng.
Chuyển đổi bảng sang sử dụng composite key để phân phối đều hơn.
ALTER TABLE orders ALTER PRIMARY KEY USING COLUMNS (shard_key, order_id);
Kết quả mong đợi: YugabyteDB sẽ thực hiện rebuild index và phân phối lại dữ liệu theo key mới.
Verify sự phân bổ đều sau khi thay đổi schema và chờ rebalance.
ycsh -u yugabyte -p yugabyte -c "tablet_server_status"
Kết quả mong đợi: Số lượng tablet trên các node đã cân bằng hơn (chênh lệch nhỏ hơn 10%).
Best practices để vận hành YugabyteDB trong môi trường Production
Vận hành YugabyteDB ở môi trường Production đòi hỏi tuân thủ các nguyên tắc về độ tin cậy, bảo mật và hiệu năng.
Sử dụng Persistent Volumes (PV) với loại storage tốc độ cao (NVMe hoặc SSD) cho dữ liệu. Tránh sử dụng local storage (ephemeral) vì dữ liệu sẽ mất khi node bị xóa.
kubectl describe pvc -n yugabyte | grep StorageClass
Kết quả mong đợi: StorageClass được sử dụng là loại SSD hoặc NVMe, không phải default (thường là HDD hoặc local).
Cấu hình Resource Limits và Requests chính xác để tránh OOM và CPU throttling. Không để Kubernetes tự động guess.
helm upgrade yugabyte yugabyte/yugabyte --set tserver.resources.limits.memory=8Gi --set tserver.resources.limits.cpu=4 --set tserver.resources.requests.memory=6Gi --set tserver.resources.requests.cpu=3 -n yugabyte
Kết quả mong đợi: Pod TServer được restart với giới hạn tài nguyên rõ ràng.
Luôn duy trì số lượng node Master là số lẻ (1, 3, 5) để đảm bảo quorum trong trường hợp mất node.
helm upgrade yugabyte yugabyte/yugabyte --set master.replicaCount=3 -n yugabyte
Kết quả mong đợi: Cụm Master mở rộng lên 3 node, tăng tính sẵn sàng.
Kiểm tra định kỳ các chỉ số cảnh báo (alert) về disk usage, replication lag và connection pool.
ycsh -u yugabyte -p yugabyte -c "cluster_status"
Kết quả mong đợi: Tổng quan về trạng thái cụm, bao gồm số lượng node, tablet, và trạng thái replication.
Thực hiện backup định kỳ và kiểm tra khả năng restore (disaster recovery drill) ít nhất mỗi quý.
yb_backup --dest_dir=/mnt/nfs/backup/yugabyte --keyspace=yugabyte
Kết quả mong đợi: Backup được thực hiện thành công và lưu vào đường dẫn chỉ định.
Giám sát hiệu năng liên tục bằng Prometheus và Grafana, thiết lập cảnh báo khi độ trễ (latency) vượt quá ngưỡng chấp nhận được.
kubectl get svc -n monitoring
Kết quả mong đợi: Dịch vụ Prometheus và Grafana đang chạy và sẵn sàng thu thập metrics.
Điều hướng series:
Mục lục: Series: Xây dựng hệ thống Database phân tán với YugabyteDB và Kubernetes
« Phần 7: Giám sát hiệu năng và cảnh báo với Prometheus và Grafana