Ekstensibilitas bidang data dengan EnvoyFilter

Anda dapat menggunakan EnvoyFilter API untuk memperluas kemampuan bidang data di Cloud Service Mesh yang tidak dapat dicapai dengan menggunakan API Istio lainnya. Dengan API EnvoyFilter, Anda dapat menyesuaikan konfigurasi Envoy yang dihasilkan dari kebijakan lain yang diterapkan ke beban kerja, seperti menambahkan filter ke rantai filter HTTP.

Pertimbangan penting

  • Perhatikan bahwa permukaan API terkait dengan detail implementasi internal, sehingga perhatian khusus harus diberikan saat menggunakan fitur ini karena konfigurasi yang salah dapat mengganggu stabilitas mesh. Gunakan EnvoyFilter API hanya jika API Istio lainnya tidak sesuai dengan kebutuhan Anda.
  • EnvoyFilter API didukung dengan batasan tertentu pada kolom dan ekstensi yang dapat digunakan untuk tujuan keandalan dan dukungan. Untuk mengetahui daftar lengkap fitur yang didukung di EnvoyFilter API, lihat Fitur yang didukung menggunakan Istio API (bidang kontrol terkelola).
  • Cakupan dukungan yang ditawarkan Google terbatas pada penyebaran konfigurasi yang disediakan pengguna ke workload dengan sidecar Envoy dan tidak mencakup kebenaran konfigurasi yang ditentukan menggunakan API per-ekstensi.

Kolom API yang Didukung

EnvoyFilter API didukung dengan penerapan bidang kontrol TRAFFIC_DIRECTOR hanya dengan dukungan terbatas sebagai berikut:

  • targetRefs: Tidak didukung
  • configPatches[].applyTo : hanya HTTP_FILTER yang didukung
  • configPatches[].patch.operation: hanya INSERT_FIRST dan INSERT_BEFORE yang didukung saat digunakan dengan filter rute.
  • configPatches[].patch.value.type_url: lihat Ekstensi yang Didukung
  • configPatches[].patch.filterClass: Tidak didukung
  • configPatches[].match.proxy: Tidak didukung
  • configPatches[].match.routeConfiguration: Tidak didukung
  • configPatches[].match.cluster: Tidak didukung
  • Kolom berikut hanya didukung untuk operasi INSERT_BEFORE:
    • configPatches[].match.listener: hanya filter yang didukung.
    • configPatches[].match.listener.filter.name: hanya envoy.filters.network.http_connection_manager yang didukung.
    • configPatches[].match.listener.filter.subFilter.name: hanya envoy.filters.http.router yang didukung.

Ekstensi yang Didukung

Berikut adalah daftar ekstensi yang didukung beserta kolom API yang didukung di berbagai saluran rilis. Definisi API dan semantiknya dapat ditemukan di dokumentasi resmi Envoy.

type.googleapis.com/envoy.extensions.filters.http.local_ratelimit.v3.LocalRateLimit

Kolom Cepat Reguler Stabil
stat_prefix
status
token_bucket
filter_enabled
filter_enforced
response_headers_to_add
request_headers_to_add_when_not_enforced
local_rate_limit_per_downstream_connection
enable_x_ratelimit_headers

type.googleapis.com/envoy.extensions.filters.http.grpc_web.v3.GrpcWeb

Kolom Cepat Reguler Stabil
(Tidak ada kolom)

Contoh Penggunaan

Dalam tutorial ini, Anda akan mempelajari cara menggunakan pembatasan frekuensi lokal bawaan Envoy untuk membatasi traffic ke layanan secara dinamis menggunakan EnvoyFilter API.

Biaya

Tutorial ini menggunakan komponen Google Cloudyang dapat ditagih berikut:

Setelah menyelesaikan tutorial ini, Anda dapat menghindari biaya berkelanjutan dengan menghapus resource yang Anda buat. Untuk informasi selengkapnya, lihat Pembersihan.

Sebelum memulai

  • Pastikan penagihan diaktifkan untuk project Anda.
  • Sediakan Cloud Service Mesh di cluster GKE.
  • Buat clone repositori:

      git clone https://github.com/GoogleCloudPlatform/anthos-service-mesh-samples
      cd anthos-service-mesh-samples
    

Men-deploy gateway traffic masuk

  1. Tetapkan konteks saat ini untuk kubectl ke cluster:

    gcloud container clusters get-credentials CLUSTER_NAME  \
        --project=PROJECT_ID \
        --zone=CLUSTER_LOCATION 
    
  2. Buat namespace untuk gateway masuk Anda:

    kubectl create namespace asm-ingress
    
  3. Aktifkan namespace untuk injeksi. Langkah-langkahnya bergantung pada implementasi bidang kontrol Anda.

    Terapkan label injeksi default ke namespace:

    kubectl label namespace asm-ingress \
        istio.io/rev- istio-injection=enabled --overwrite
    
  4. Deploy gateway contoh di repositori anthos-service-mesh-samples:

    kubectl apply -n asm-ingress \
        -f docs/shared/asm-ingress-gateway
    

    Output yang diharapkan:

    serviceaccount/asm-ingressgateway configured
    service/asm-ingressgateway configured
    deployment.apps/asm-ingressgateway configured
    gateway.networking.istio.io/asm-ingressgateway configured
    

Men-deploy contoh aplikasi Butik Online

  1. Jika belum, tetapkan konteks saat ini untuk kubectl ke cluster:

    gcloud container clusters get-credentials CLUSTER_NAME  \
      --project=PROJECT_ID \
      --zone=CLUSTER_LOCATION 
    
  2. Buat namespace untuk aplikasi contoh:

    kubectl create namespace onlineboutique
    
  3. Beri label pada namespace onlineboutique untuk otomatis memasukkan proxy Envoy:

    kubectl label namespace onlineboutique \
       istio.io/rev- istio-injection=enabled --overwrite
    
  4. Deploy aplikasi contoh, VirtualService untuk frontend, dan akun layanan untuk workload. Untuk tutorial ini, Anda akan men-deploy Online Boutique, aplikasi demo microservice.

    kubectl apply \
      -n onlineboutique \
      -f docs/shared/online-boutique/virtual-service.yaml
    
    kubectl apply \
      -n onlineboutique \
      -f docs/shared/online-boutique/service-accounts
    

Melihat layanan Anda

  1. Lihat pod di namespace onlineboutique:

    kubectl get pods -n onlineboutique
    

    Output yang diharapkan:

    NAME                                     READY   STATUS    RESTARTS   AGE
    adservice-85598d856b-m84m6               2/2     Running   0          2m7s
    cartservice-c77f6b866-m67vd              2/2     Running   0          2m8s
    checkoutservice-654c47f4b6-hqtqr         2/2     Running   0          2m10s
    currencyservice-59bc889674-jhk8z         2/2     Running   0          2m8s
    emailservice-5b9fff7cb8-8nqwz            2/2     Running   0          2m10s
    frontend-77b88cc7cb-mr4rp                2/2     Running   0          2m9s
    loadgenerator-6958f5bc8b-55q7w           2/2     Running   0          2m8s
    paymentservice-68dd9755bb-2jmb7          2/2     Running   0          2m9s
    productcatalogservice-84f95c95ff-c5kl6   2/2     Running   0          114s
    recommendationservice-64dc9dfbc8-xfs2t   2/2     Running   0          2m9s
    redis-cart-5b569cd47-cc2qd               2/2     Running   0          2m7s
    shippingservice-5488d5b6cb-lfhtt         2/2     Running   0          2m7s
    

    Semua pod untuk aplikasi Anda harus aktif dan berjalan, dengan 2/2 di kolom READY. Hal ini menunjukkan bahwa proxy file bantuan Envoy di pod telah berhasil disuntikkan. Jika 2/2 tidak muncul setelah beberapa menit, buka Panduan pemecahan masalah.

  2. Dapatkan IP eksternal, lalu tetapkan ke variabel:

    kubectl get services -n asm-ingress
    export FRONTEND_IP=$(kubectl --namespace asm-ingress \
    get service --output jsonpath='{.items[0].status.loadBalancer.ingress[0].ip}' \
    )
    

    Anda akan melihat output yang mirip dengan berikut ini:

    NAME                   TYPE           CLUSTER-IP      EXTERNAL-IP   PORT(S)                                      AGE
    asm-ingressgateway   LoadBalancer   10.19.247.233   35.239.7.64   80:31380/TCP,443:31390/TCP,31400:31400/TCP   27m
    
    
  3. Buka alamat EXTERNAL-IP di browser web Anda. Anda akan melihat toko Online Boutique di browser Anda.

    frontend butik online

Menerapkan Konfigurasi Pembatasan Kapasitas

Bagian ini menerapkan resource EnvoyFilter untuk membatasi semua traffic ke layanan frontend hingga 5 req/mnt.

  1. Terapkan CR ke layanan frontend:

    kubectl apply -f - <<EOF
    apiVersion: networking.istio.io/v1alpha3
    kind: EnvoyFilter
    metadata:
      name: frontend-local-ratelimit
      namespace: onlineboutique
    spec:
      workloadSelector:
        labels:
          app: frontend
      configPatches:
        - applyTo: HTTP_FILTER
          match:
            context: SIDECAR_INBOUND
            listener:
              filterChain:
                filter:
                  name: "envoy.filters.network.http_connection_manager"
                  subFilter:
                    name: "envoy.filters.http.router"
          patch:
            operation: INSERT_BEFORE
            value:
              name: envoy.filters.http.local_ratelimit
              typed_config:
                "@type": type.googleapis.com/udpa.type.v1.TypedStruct
                type_url: type.googleapis.com/envoy.extensions.filters.http.local_ratelimit.v3.LocalRateLimit
                value:
                  stat_prefix: http_local_rate_limiter
                  token_bucket:
                    max_tokens: 5
                    tokens_per_fill: 5
                    fill_interval: 60s
                  filter_enabled:
                    runtime_key: local_rate_limit_enabled
                    default_value:
                      numerator: 100
                      denominator: HUNDRED
                  filter_enforced:
                    runtime_key: local_rate_limit_enforced
                    default_value:
                      numerator: 100
                      denominator: HUNDRED
    EOF
    

    Output yang diharapkan:

    envoyfilter.networking.istio.io/frontend-local-ratelimit created
    
  2. Pastikan status CR tidak melaporkan error:

    kubectl get envoyfilter -n onlineboutique frontend-local-ratelimit -o yaml
    

    Output yang diharapkan:

    ...
    status:
      conditions:
      - lastTransitionTime: "2025-06-30T14:29:25.467017594Z"
        message: This resource has been accepted. This does not mean it has been propagated
          to all proxies yet
        reason: Accepted
        status: "True"
        type: Accepted
    
  3. Hapus deployment loadgenerator karena memanggil layanan beberapa kali yang menghabiskan token:

    kubectl delete -n onlineboutique deployment loadgenerator
    

    Output yang diharapkan:

    deployment.apps/loadgenerator deleted
    
  4. Dengan menggunakan curl, verifikasi bahwa tidak lebih dari 5 permintaan diizinkan dalam 60 detik. Kode 429 menunjukkan bahwa pembatasan kecepatan sedang diterapkan.

    for i in {1..10}; do curl -s http://${FRONTEND_IP} -o /dev/null -w "%{http_code}\n"; sleep 1; done
    

    Output yang diharapkan:

    200
    200
    200
    200
    200
    429
    429
    429
    429
    429
    

Pembersihan

Agar tidak menimbulkan biaya berkelanjutan pada akun Google Cloud Anda untuk resource yang digunakan dalam tutorial ini, Anda dapat menghapus project atau menghapus setiap resource.

Menghapus project

Di Cloud Shell, hapus project:

  gcloud projects delete PROJECT_ID

Menghapus resource

  • Jika Anda ingin mempertahankan cluster dan menghapus contoh Butik Online:

    1. Hapus namespace aplikasi:

      kubectl delete namespace onlineboutique
      

      Output yang diharapkan:

      namespace "onlineboutique" deleted
      
    2. Hapus namespace Ingress Gateway:

      kubectl delete namespace asm-ingress
      

      Output yang diharapkan:

      namespace "asm-ingress" deleted
      
  • Jika Anda ingin mencegah tagihan tambahan, hapus cluster:

    gcloud container clusters delete CLUSTER_NAME  \
      --project=PROJECT_ID \
      --zone=CLUSTER_LOCATION 
    

Pemecahan masalah

Lihat Menyelesaikan masalah ekstensibilitas bidang data.