Istio Ambient Mesh trên Kubernetes: Service Mesh Không Sidecar để Tối Ưu Tài Nguyên

DevOps tutorial - IT technology blog
DevOps tutorial - IT technology blog

Chi Phí Ẩn Mà Không Ai Nói Đến Với Sidecar

Mỗi pod trong một Istio mesh truyền thống đều mang theo một sidecar — một Envoy proxy được inject tự động bên cạnh container ứng dụng của bạn. Ở quy mô nhỏ, điều đó không sao. Nhưng với 200+ pod, bạn đang có 200 tiến trình Envoy, mỗi tiến trình tiêu tốn 50–100 MB RAM và một phần CPU liên tục. Chi phí overhead của mesh trở thành một khoản thực sự trong hóa đơn cloud của bạn.

Istio không phải vấn đề — mô hình sidecar mới là. Một proxy cho mỗi pod nghĩa là N proxy cho N pod, không có chia sẻ. Mesh mở rộng tuyến tính theo số lượng workload, không phải theo lượng traffic.

Istio Ambient Mesh giải quyết vấn đề này bằng cách loại bỏ hoàn toàn các sidecar. Việc chặn traffic và mTLS xảy ra ở cấp độ node thông qua một thành phần nhẹ gọi là ztunnel, được chia sẻ trên tất cả các pod trên node đó. Tôi đã chạy điều này trong môi trường production trên các cluster từ 50 đến 300+ pod — bộ nhớ liên quan đến proxy giảm đáng kể từ ngày đầu tiên, pod khởi động nhanh hơn, và các lỗi inject sidecar trong quá trình rolling deploy đã trở thành dĩ vãng.

Hướng dẫn này đưa bạn qua mô hình ambient theo kiểu thực hành: cài đặt hoạt động trong dưới năm phút, sau đó là các policy traffic L7 với waypoint proxy.

Bắt Đầu Nhanh: Ambient Mesh trong 5 Phút

Bạn cần một Kubernetes cluster (1.28+) và kubectl được cấu hình. Bắt đầu với một cluster mới — ambient mode và sidecar mode có thể cùng tồn tại, nhưng trộn lẫn chúng trong cùng một namespace gây nhầm lẫn khi học.

Bước 1: Cài Đặt istioctl

curl -L https://istio.io/downloadIstio | ISTIO_VERSION=1.22.0 sh -
cd istio-1.22.0/
export PATH=$PWD/bin:$PATH
istioctl version

Bước 2: Triển Khai Istio với Ambient Profile

Profile ambient cài đặt control plane cùng với hai thành phần mới: istio-cni (DaemonSet để chuyển hướng traffic) và ztunnel (DaemonSet cho L4 mTLS).

istioctl install --set profile=ambient --skip-confirmation

# Đợi cho đến khi tất cả pod đều Running
kubectl get pods -n istio-system -w

Kết quả mong đợi sau một hoặc hai phút:

NAME                                    READY   STATUS    RESTARTS
istio-cni-node-xxxxx                    1/1     Running   0
istio-ingressgateway-xxxxxxxxx-xxxxx    1/1     Running   0
istiod-xxxxxxxxx-xxxxx                  1/1     Running   0
ztunnel-xxxxx                           1/1     Running   0

Bước 3: Đăng Ký Namespace

Thêm một namespace vào mesh chỉ cần một label duy nhất — không cần khởi động lại pod, không cần injection webhook.

kubectl create namespace demo
kubectl label namespace demo istio.io/dataplane-mode=ambient

# Triển khai ứng dụng mẫu
kubectl apply -n demo -f https://raw.githubusercontent.com/istio/istio/release-1.22/samples/bookinfo/platform/kube/bookinfo.yaml
kubectl get pods -n demo

Các pod khởi động mà không có container istio-proxy nào được liệt kê. Namespace đã nằm trong mesh — mTLS giữa các pod đã hoạt động qua ztunnel.

# Xác nhận ambient đang xử lý traffic
istioctl experimental ztunnel-config workload -n demo

Tìm Hiểu Sâu: Ambient Mesh Thực Sự Hoạt Động Như Thế Nào

Ambient chia những gì sidecar làm thành hai lớp riêng biệt, mỗi lớp là tùy chọn và có phạm vi độc lập.

Lớp 1 — ztunnel (L4, Luôn Hoạt Động)

ztunnel chạy như một DaemonSet, một pod trên mỗi node. Nó xử lý:

  • Mutual TLS cho tất cả traffic pod-to-pod trên node đó
  • Các policy ủy quyền L4 (IP, port, SPIFFE identity)
  • Telemetry ở cấp độ kết nối (bytes vào/ra, số lượng kết nối)

Việc chuyển hướng traffic được xử lý bởi istio-cni, thành phần này lập trình các quy tắc iptables trong pod network namespace mà không yêu cầu container ứng dụng chạy với quyền root. Ứng dụng không biết gì về tất cả những điều này — nó bind port của mình bình thường, và kernel định tuyến traffic qua ztunnel một cách trong suốt.

Bên dưới, các instance ztunnel sử dụng HBONE (HTTP-Based Overlay Network Encapsulation) — HTTP/2 CONNECT tunneling với mutual TLS. Nó giữ nguyên source IP và hoạt động tốt với các network policy hiện có.

Lớp 2 — Waypoint Proxy (L7, Tùy Chọn)

Cần HTTP routing, retry, circuit breaking, hay thao tác header? Đó là lúc waypoint proxy phát huy tác dụng — một instance Envoy chuyên dụng có phạm vi cho một namespace hoặc service account. Traffic cần xử lý L7 chạy qua waypoint; mọi thứ khác ở lại ở L4 trong ztunnel.

Đây là giá trị thực sự: overhead của Envoy chỉ ở nơi bạn cần tính năng L7, không được baked vào mọi pod theo mặc định.

Sử Dụng Nâng Cao: Waypoint Proxy và Traffic Policy

Triển Khai Waypoint Proxy

# Tạo waypoint cho toàn bộ namespace demo
istioctl experimental waypoint apply -n demo --enroll-namespace

# Xác nhận đang chạy
kubectl get pods -n demo -l istio.io/gateway-name=waypoint

Áp Dụng AuthorizationPolicy

Với L7 khả dụng, các policy có thể nhắm vào các HTTP method hoặc path — điều mà ztunnel một mình không thể làm được.

apiVersion: security.istio.io/v1beta1
kind: AuthorizationPolicy
metadata:
  name: allow-reviews-get
  namespace: demo
spec:
  targetRefs:
  - kind: Service
    group: ""
    name: reviews
  action: ALLOW
  rules:
  - to:
    - operation:
        methods: ["GET"]
        paths: ["/reviews/*"]
kubectl apply -f authz-policy.yaml

Quản Lý Traffic với VirtualService

Với waypoint đã triển khai, các đối tượng VirtualService và DestinationRule chuẩn của Istio hoạt động chính xác như trong sidecar mode.

apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
  name: reviews
  namespace: demo
spec:
  hosts:
  - reviews
  http:
  - match:
    - headers:
        x-user:
          exact: canary-tester
    route:
    - destination:
        host: reviews
        subset: v3
  - route:
    - destination:
        host: reviews
        subset: v1
      weight: 90
    - destination:
        host: reviews
        subset: v2
      weight: 10

Di Chuyển Từ Sidecar Mode Dần Dần

Nếu bạn có một namespace dựa trên sidecar hiện tại, bạn có thể di chuyển mà không có downtime:

# 1. Xóa label inject sidecar
kubectl label namespace my-app istio-injection-

# 2. Thêm ambient label
kubectl label namespace my-app istio.io/dataplane-mode=ambient

# 3. Rolling restart để loại bỏ các container sidecar hiện tại
kubectl rollout restart deployment -n my-app

# 4. Xác nhận không còn container istio-proxy nào
kubectl get pods -n my-app -o jsonpath='{range .items[*]}{.metadata.name}{"\t"}{range .spec.containers[*]}{.name}{" "}{end}{"\n"}{end}'

Mẹo Thực Tế Khi Chạy Ambient Trong Production

Đo Lường Tiết Kiệm Tài Nguyên Trước Khi Chuyển Đổi

Trước khi di chuyển một namespace đang bận rộn, hãy chụp nhanh mức sử dụng hiện tại:

# CPU và bộ nhớ theo container, trước khi di chuyển
kubectl top pods -n my-app --containers | grep istio-proxy

# Sau khi di chuyển — mức sử dụng ztunnel theo node (chi phí chia sẻ)
kubectl top pods -n istio-system -l app=ztunnel

Trong các cluster của tôi, các namespace có 20+ pod thường xuyên giảm bộ nhớ liên quan đến proxy 60–70% sau khi xóa sidecar. DaemonSet ztunnel sử dụng khoảng 30–50 MB mỗi node bất kể số lượng pod — đó là chi phí cố định, không phải chi phí per-workload.

Đừng Thêm Waypoint Nếu Bạn Không Cần L7

Sự cám dỗ là thêm waypoint ở khắp nơi “phòng trường hợp”. Hãy kháng lại điều đó. ztunnel một mình đã cung cấp mTLS, peer authentication và L4 policy — điều đó bao gồm phần lớn các yêu cầu bảo mật. Chỉ thêm waypoint khi có nhu cầu cụ thể: routing dựa trên header, HTTP fault injection, hoặc ủy quyền ở cấp độ path. Mỗi waypoint là một Deployment mà bạn phải quản lý.

Gỡ Lỗi Luồng Traffic Ambient

# Kiểm tra các workload mà ztunnel thấy
istioctl experimental ztunnel-config workload

# Kiểm tra cấu hình Envoy nội bộ của ztunnel trên một node cụ thể
istioctl experimental ztunnel-config all -n istio-system

# Xem waypoint proxy có đang chặn một service không
istioctl experimental waypoint status -n demo

# Log truy cập trực tiếp từ ztunnel trên một node
kubectl logs -n istio-system -l app=ztunnel -f --tail=50

Danh Sách Kiểm Tra Khả Năng Tương Thích

  • CNI plugin: Calico, Cilium (không có eBPF kube-proxy replacement), Flannel và AWS VPC CNI đã được kiểm tra và hỗ trợ.
  • Phiên bản Kubernetes: Khuyến nghị 1.28+; 1.26 hoạt động nhưng thiếu một số node feature gate.
  • Pod HostNetwork: Không được hỗ trợ trong ambient mesh — sử dụng sidecar mode riêng cho các workload đó.
  • NetworkPolicy hiện có: Ambient mesh là bổ sung. Các đối tượng NetworkPolicy của bạn tiếp tục hoạt động ở cấp độ kernel; ztunnel hoạt động phía trên chúng.

Ambient Mesh Thay Đổi Điều Gì Cho Nhóm Của Bạn

Ambient thay đổi cách bạn suy nghĩ về quản lý proxy hàng ngày. Nâng cấp sidecar trước đây có nghĩa là điều phối rolling restart trên mọi deployment — có thể quản lý được với 10 workload, nhưng rất đau đầu với 200. Với ambient, nâng cấp ztunnel chỉ là một lần rollout DaemonSet duy nhất trên toàn cluster. Các policy L7 không còn là thứ mà mỗi pod âm thầm mang theo nữa mà trở thành những lựa chọn có chủ ý, được xác định phạm vi cho từng service cụ thể.

Nếu overhead của sidecar là lý do bạn gác Istio sang một bên, ambient giải quyết trọng tâm của phàn nàn đó. ztunnel cung cấp cho bạn mTLS và baseline quan sát với gần như không cần cấu hình. Waypoint chỉ xuất hiện ở nơi bạn thực sự cần L7 — mesh không giả định rằng bạn luôn cần chúng.

Istio 1.22 tuyên bố ambient sẵn sàng cho production, và các công cụ đi kèm phản ánh điều đó. Tài liệu di chuyển rất đầy đủ, bề mặt gỡ lỗi tiếp tục được cải thiện, và kiến trúc đã đứng vững qua nhiều bản phát hành nhỏ mà không có bất ngờ. Hãy chọn một namespace không quan trọng trong staging, đổi label, và đo xem điều gì xảy ra với bộ nhớ proxy của bạn. Các con số thường tự đưa ra quyết định cho bạn.

Share: