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

Giải pháp tối ưu hóa Load Balancing cho GRPC Communication trong Kubernetes - Phần 2

Đăng vào 2 tháng trước

• 3 phút đọc

Giới thiệu

Trong phần 1 của bài viết, mình đã đề cập đến những hạn chế của Kubernetes service khi thực hiện Load Balancing cho GRPC. Ở phần 2 này, chúng ta sẽ cùng khám phá các giải pháp hiệu quả giúp khắc phục tình trạng này.

Kho lưu trữ mã nguồn: https://github.com/phamsyhung2110/test-grpc-lb

Giải pháp 1: Sử dụng Client-side Load Balancing

Client-side Load Balancing là phương pháp mà client có thể tự quản lý việc phân phối các yêu cầu tới các instance backend mà không cần phải dựa vào một load balancer bên ngoài. Thay vào đó, client sẽ sử dụng danh sách các endpoint để tự quyết định nơi để gửi yêu cầu.

Cách hoạt động

  1. Service Discovery: Client cần phải biết danh sách các endpoint của backend. Việc này thường được thực hiện thông qua DNS hoặc API của Kubernetes.
  2. Chọn Endpoint: Client sẽ dùng các thuật toán như Round Robin, Least Connections, hoặc Random để chọn endpoint từ danh sách.
  3. Gửi Request: Client sẽ gửi yêu cầu trực tiếp tới pod backend.

Điều kiện cần thiết

  • Headless Service: Cần cấu hình Kubernetes headless service để DNS trả về danh sách các IP của các pod backend thay vì chỉ trả về ClusterIP.
  • Thư viện hỗ trợ: Sử dụng các thư viện hoặc framework hỗ trợ client-side Load Balancing, ví dụ như gRPC balancer trong các SDK chính thức của gRPC.

Ví dụ triển khai

1. Cập nhật mã nguồn của Service A (HTTP proxy)

Tạo file service-A-lb.js trong folder grpc-app/ với cấu hình sử dụng DNS cho Service Discovery:

javascript Copy
const grpcServiceAddress = process.env.GRPC_SERVICE_ADDRESS || 'dns:///service-b-grpc.default.svc.cluster.local:50051';

2. Thêm logic Load Balancing

  • Mục đích: Cho phép gRPC client tự động phát hiện các pod của Service B trong môi trường Kubernetes.
  • Chi tiết cấu hình:
    • dns:///: là prefix cần thiết khi sử dụng DNS để định tuyến trong gRPC.
    • service-b-grpc.default.svc.cluster.local: tên DNS đầy đủ của Service B trong Kubernetes.
    • Dùng cấu hình load balancing:
    javascript Copy
    const client = new echoService(grpcServiceAddress, grpc.credentials.createInsecure(), {
      'grpc.service_config': JSON.stringify({
        loadBalancingConfig: [{ round_robin: {} }]
      })
    });

Như vậy, phần sửa mã nguồn đã hoàn tất. Bạn cần tự build và deploy lại Service A:

Copy
cd grpc-app/
docker build . -f dockerfile -t <repo>/testgrpc:v1
docker push <repo>/testgrpc:v1

3. Chuyển đổi Kubernetes service của Service B thành Headless service

yaml Copy
apiVersion: v1
kind: Service
metadata:
  name: service-b-grpc
spec:
  clusterIP: None
  selector:
    app: service-b-grpc
  ports:
    - protocol: TCP
      port: 50051
      targetPort: 50051

Áp dụng manifest:

Copy
kubectl apply -f deploy/grpc-deploy.yaml -n grpc

Kiểm tra: Gửi yêu cầu tới Service A bằng K6

Trước tiên, bạn cần thực hiện port-forwarding:

Copy
kubectl port-forward svc/service-a-grpc 5000:5000 -n grpc

Chạy kiểm tra với K6:

Copy
cd k6/
k6 run grpc-loadtest.js

Kết quả: Các yêu cầu đã được phân phối qua lại đến các pod của Service B thành công.

Giải pháp 2: Sử dụng Service Mesh

Giải pháp này không yêu cầu thay đổi mã nguồn nhưng yêu cầu bạn sử dụng công cụ service mesh, ở đây mình sẽ sử dụng Istio.

Lưu ý: Hướng dẫn này không bao gồm cách cài đặt Istio, bạn cần đã có kiến thức hoặc đã cài đặt Istio trong cluster của mình.

Kích hoạt sidecar injection

Copy
kubectl label namespace dev-hung istio-injection=enabled

Khởi động lại service

Copy
kubectl delete -f deploy/grpc-deploy.yaml && kubectl apply -f deploy/grpc-deploy.yaml

Sau khi các service đã được chạy với Istio sidecar, bạn có thể thực hiện lại bài kiểm tra như đã hướng dẫn ở phần trước. Theo tài liệu của Istio, cơ chế Load Balancing mặc định của Envoy proxy là Least Connection. Bạn có thể tùy chỉnh cấu hình load balancing theo nhu cầu cụ thể của mình.

Theo mặc định, các proxy Envoy phân phối traffic giữa các service dựa trên mô hình least requests, trong đó mỗi yêu cầu được điều hướng tới host có ít yêu cầu hơn từ việc chọn ngẫu nhiên hai host từ nhóm load balancing.

Đọc thêm tại: https://istio.io/latest/docs/concepts/traffic-management/#introducing-istio-traffic-management

Kết luận

Qua bài viết này, mình đã trình bày lý thuyết cũng như thực tế triển khai các giải pháp khắc phục vấn đề Load Balancing cho gRPC trong Kubernetes. Hy vọng những thông tin này sẽ giúp bạn có thêm kiến thức về Networking và cách triển khai gRPC hiệu quả trong môi trường Kubernetes.
source: viblo

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