Halaman ini menjelaskan cara menggunakan load balancing berbasis container di Google Kubernetes Engine (GKE). Load balancing berbasis container memungkinkan load balancer langsung menarget Pod Kubernetes dan mendistribusikan traffic ke Pod secara merata.
Untuk mengetahui informasi selengkapnya tentang manfaat, persyaratan, dan batasan load balancing berbasis container, lihat Load balancing berbasis container.
Sebelum memulai
Sebelum memulai, pastikan Anda telah menjalankan tugas berikut:
- Aktifkan Google Kubernetes Engine API. Aktifkan Google Kubernetes Engine API
- Jika ingin menggunakan Google Cloud CLI untuk tugas ini,
instal lalu
lakukan inisialisasi
gcloud CLI. Jika sebelumnya Anda telah menginstal gcloud CLI, dapatkan versi terbaru dengan menjalankan
gcloud components update
.
Menggunakan load balancing berbasis container
Bagian berikut akan memandu Anda melakukan konfigurasi load balancing berbasis container di GKE. Perlu diperhatikan bahwa untuk cluster GKE yang menjalankan versi 1.17 atau yang lebih baru dan dalam kondisi tertentu, load balancing berbasis container bersifat default dan tidak memerlukan anotasi Layanan cloud.google.com/neg: '{"ingress": true}'
yang eksplisit.
Membuat cluster VPC native
Untuk menggunakan load balancing native container, cluster GKE Anda harus mengaktifkan IP alias.
Misalnya, perintah berikut akan membuat cluster GKE, neg-demo-cluster
, dengan subnetwork yang disediakan otomatis:
Untuk mode Autopilot, alamat IP alias diaktifkan secara default:
gcloud container clusters create-auto neg-demo-cluster \ --location=COMPUTE_LOCATION
Ganti
COMPUTE_LOCATION
dengan lokasi Compute Engine untuk cluster.
Untuk mode Standar, aktifkan alamat IP alias saat Anda membuat cluster:
gcloud container clusters create neg-demo-cluster \ --enable-ip-alias \ --create-subnetwork="" \ --network=default \ --zone=us-central1-a
Membuat Deployment
Contoh Deployment berikut, neg-demo-app
, menjalankan satu instance server HTTP dalam container. Sebaiknya
gunakan workload yang menggunakan
masukan
Kesiapan Pod.
Menggunakan masukan kesiapan Pod
apiVersion: apps/v1 kind: Deployment metadata: labels: run: neg-demo-app # Label for the Deployment name: neg-demo-app # Name of Deployment spec: selector: matchLabels: run: neg-demo-app template: # Pod template metadata: labels: run: neg-demo-app # Labels Pods from this Deployment spec: # Pod specification; each Pod created by this Deployment has this specification containers: - image: registry.k8s.io/serve_hostname:v1.4 # Application to run in Deployment's Pods name: hostname # Container name ports: - containerPort: 9376 protocol: TCP
Menggunakan penundaan yang di-harcode
apiVersion: apps/v1 kind: Deployment metadata: labels: run: neg-demo-app # Label for the Deployment name: neg-demo-app # Name of Deployment spec: minReadySeconds: 60 # Number of seconds to wait after a Pod is created and its status is Ready selector: matchLabels: run: neg-demo-app template: # Pod template metadata: labels: run: neg-demo-app # Labels Pods from this Deployment spec: # Pod specification; each Pod created by this Deployment has this specification containers: - image: registry.k8s.io/serve_hostname:v1.4 # Application to run in Deployment's Pods name: hostname # Container name # Note: The following line is necessary only on clusters running GKE v1.11 and lower. # For details, see https://cloud.google.com/kubernetes-engine/docs/how-to/container-native-load-balancing#align_rollouts ports: - containerPort: 9376 protocol: TCP terminationGracePeriodSeconds: 60 # Number of seconds to wait for connections to terminate before shutting down Pods
Dalam Deployment ini, setiap container menjalankan server HTTP. Server HTTP menampilkan nama host server aplikasi (nama Pod tempat server berjalan) sebagai respons.
Simpan manifes ini sebagai neg-demo-app.yaml
, lalu buat Deployment:
kubectl apply -f neg-demo-app.yaml
Membuat Layanan untuk load balancer berbasis container
Setelah membuat Deployment, Anda perlu mengelompokkan Pod-nya ke dalam Layanan.
Contoh Layanan berikut, neg-demo-svc
, menargetkan contoh Deployment yang Anda buat di bagian sebelumnya:
apiVersion: v1
kind: Service
metadata:
name: neg-demo-svc # Name of Service
annotations:
cloud.google.com/neg: '{"ingress": true}' # Creates a NEG after an Ingress is created
spec: # Service's specification
type: ClusterIP
selector:
run: neg-demo-app # Selects Pods labelled run: neg-demo-app
ports:
- name: http
port: 80 # Service's port
protocol: TCP
targetPort: 9376
Anotasi Layanan, cloud.google.com/neg: '{"ingress": true}'
, akan mengaktifkan load balancing berbasis container. Namun, load balancer tidak dibuat sebelum Anda membuat Ingress untuk Layanan.
Simpan manifes ini sebagai neg-demo-svc.yaml
, lalu buat Service:
kubectl apply -f neg-demo-svc.yaml
Membuat Ingress untuk Layanan
Contoh Ingress berikut, neg-demo-ing
, menargetkan Layanan yang Anda buat:
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: neg-demo-ing
spec:
defaultBackend:
service:
name: neg-demo-svc # Name of the Service targeted by the Ingress
port:
number: 80 # Should match the port used by the Service
Simpan manifes ini sebagai neg-demo-ing.yaml
, lalu buat Ingress:
kubectl apply -f neg-demo-ing.yaml
Setelah membuat Ingress, Application Load Balancer akan dibuat di project, dan Grup Endpoint Jaringan(NEG) dibuat di setiap zona tempat cluster berjalan. Endpoint di NEG dan endpoint Layanan terus disinkronkan.
Memverifikasi Ingress
Setelah men-deploy workload, mengelompokkan Pod-nya ke dalam Layanan, dan membuat Ingress untuk Layanan, Anda harus memverifikasi bahwa Ingress telah berhasil menyediakan load balancer berbasis container.
Ambil status Ingress:
kubectl describe ingress neg-demo-ing
Output-nya mencakup peristiwa ADD
dan CREATE
:
Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Normal ADD 16m loadbalancer-controller default/neg-demo-ing
Normal Service 4s loadbalancer-controller default backend set to neg-demo-svc:32524
Normal CREATE 2s loadbalancer-controller ip: 192.0.2.0
Menguji load balancer
Bagian berikut menjelaskan cara menguji fungsi load balancer berbasis container.
Membuka alamat IP Ingress
Tunggu beberapa menit hingga Load Balancer Aplikasi dikonfigurasi.
Anda dapat memverifikasi bahwa load balancer berbasis container berfungsi dengan membuka alamat IP Ingress.
Untuk mendapatkan alamat IP Ingress, jalankan perintah berikut:
kubectl get ingress neg-demo-ing
Dalam output perintah, alamat IP Ingress ditampilkan di kolom ADDRESS
. Buka alamat IP di browser web.
Memeriksa status responsivitas layanan backend
Anda juga bisa mendapatkan status responsivitas layanan backend load balancer.
Dapatkan daftar layanan backend yang berjalan di project Anda:
gcloud compute backend-services list
Catat nama layanan backend yang menyertakan nama Layanan, seperti
neg-demo-svc
.Dapatkan status responsivitas layanan backend:
gcloud compute backend-services get-health BACKEND_SERVICE_NAME --global
Ganti
BACKEND_SERVICE_NAME
dengan nama layanan backend.
Menguji Ingress
Cara lain untuk menguji apakah load balancer berfungsi sesuai ekspektasi adalah dengan menskalakan Deployment contoh, mengirimkan permintaan pengujian ke Ingress, dan memverifikasi bahwa jumlah replika yang merespons sudah benar.
Menskalakan Deployment
neg-demo-app
dari satu instance menjadi dua instance:kubectl scale deployment neg-demo-app --replicas 2
Pemrosesan perintah ini mungkin memerlukan waktu beberapa menit.
Pastikan peluncuran selesai:
kubectl get deployment neg-demo-app
Output harus menyertakan dua replika yang tersedia:
NAME DESIRED CURRENT UP-TO-DATE AVAILABLE AGE neg-demo-app 2 2 2 2 26m
Dapatkan alamat IP Ingress:
kubectl describe ingress neg-demo-ing
Jika perintah ini menampilkan error 404, tunggu beberapa menit hingga load balancer dimulai, lalu coba lagi.
Hitung jumlah respons yang berbeda dari load balancer:
for i in `seq 1 100`; do \ curl --connect-timeout 1 -s IP_ADDRESS && echo; \ done | sort | uniq -c
Ganti
IP_ADDRESS
dengan alamat IP Ingress.Outputnya mirip dengan hal berikut ini:
44 neg-demo-app-7f7dfd7bc6-dcn95 56 neg-demo-app-7f7dfd7bc6-jrmzf
Dalam output ini, jumlah respons yang berbeda sama dengan jumlah replika, yang menunjukkan bahwa semua Pod backend melayani traffic.
Pembersihan
Setelah menyelesaikan tugas di halaman ini, ikuti langkah-langkah berikut untuk menghapus resource guna mencegah timbulnya biaya yang tidak diinginkan pada akun Anda:
Menghapus cluster
gcloud
gcloud container clusters delete neg-demo-cluster
Konsol
Buka halaman Google Kubernetes Engine di konsol Google Cloud.
Pilih neg-demo-cluster lalu klik delete Delete.
Saat diminta untuk mengonfirmasi, klik Delete.
Pemecahan masalah
Gunakan teknik di bawah ini untuk memverifikasi konfigurasi jaringan Anda. Bagian berikut menjelaskan cara menyelesaikan masalah tertentu terkait load balancing berbasis container.
Lihat dokumentasi load balancing untuk mengetahui cara mencantumkan grup endpoint jaringan Anda.
Anda dapat menemukan nama dan zona NEG yang sesuai dengan layanan dalam anotasi
neg-status
layanan. Dapatkan spesifikasi Layanan dengan:kubectl get svc SVC_NAME -o yaml
Anotasi
metadata:annotations:cloud.google.com/neg-status
mencantumkan nama NEG yang terkait dengan layanan dan zona NEG.Anda dapat memeriksa responsivitas layanan backend yang sesuai dengan NEG menggunakan perintah berikut:
gcloud compute backend-services --project PROJECT_NAME \ get-health BACKEND_SERVICE_NAME --global
Layanan backend memiliki nama yang sama dengan NEG-nya.
Untuk mencetak log aktivitas layanan:
kubectl describe svc SERVICE_NAME
String nama layanan mencakup nama dan namespace Layanan GKE yang terkait.
Tidak dapat membuat cluster dengan IP alias
- Gejala
Saat mencoba membuat cluster dengan IP alias, Anda mungkin mengalami error berikut:
ResponseError: code=400, message=IP aliases cannot be used with a legacy network.
- Kemungkinan penyebab
Anda mengalami error ini jika mencoba membuat cluster dengan IP alias yang juga menggunakan jaringan lama.
- Resolusi
Pastikan Anda tidak membuat cluster dengan IP alias dan jaringan lama yang diaktifkan secara bersamaan. Untuk mengetahui informasi selengkapnya tentang penggunaan IP alias, lihat Membuat cluster VPC native.
Traffic tidak mencapai endpoint
- Gejala
- Error 502/503 atau koneksi ditolak.
- Kemungkinan penyebab
Endpoint baru umumnya dapat dijangkau setelah memasangkan endpoint tersebut ke load balancer, asalkan endpoint itu merespons health check. Anda mungkin mengalami error 502 atau koneksi ditolak jika traffic tidak dapat mencapai endpoint.
Error 502 dan koneksi yang ditolak juga dapat disebabkan oleh container yang tidak menangani
SIGTERM
. Jika container tidak menanganiSIGTERM
secara eksplisit, container tersebut akan segera menghentikan dan berhenti menangani permintaan. Load balancer terus mengirim traffic masuk ke container yang dihentikan, sehingga menyebabkan error.Load balancer berbasis container hanya memiliki satu endpoint backend. Selama update berkelanjutan, endpoint lama di-deprogram sebelum endpoint baru diprogram.
Pod Backend akan di-deploy ke zona baru untuk pertama kalinya setelah load balancer berbasis container disediakan. Infrastruktur load balancer diprogram di zona saat setidaknya ada satu endpoint di zona tersebut. Saat endpoint baru ditambahkan ke suatu zona, infrastruktur load balancer diprogram dan menyebabkan gangguan layanan.
- Resolusi
Konfigurasikan container untuk menangani
SIGTERM
dan terus respons permintaan selama masa tenggang penghentian (30 detik secara default). Konfigurasi Pod untuk mulai gagal dalam health check saat menerimaSIGTERM
. Sinyal ini akan memberi tahu load balancer untuk berhenti mengirim traffic ke Pod saat proses deprogram endpoint sedang berlangsung.Jika aplikasi Anda tidak dinonaktifkan dengan baik dan berhenti merespons permintaan saat menerima
SIGTERM
, hook preStop dapat digunakan untuk menanganiSIGTERM
dan tetap menyalurkan traffic saat proses deprogram endpoint sedang berlangsung.lifecycle: preStop: exec: # if SIGTERM triggers a quick exit; keep serving traffic instead command: ["sleep","60"]
Jika backend load balancer hanya memiliki satu instance, konfigurasi strategi peluncuran agar tidak menghilangkan satu-satunya instance sebelum instance baru diprogram sepenuhnya. Untuk pod aplikasi yang dikelola oleh workload
Deployment
, hal ini dapat dicapai dengan mengonfigurasi strategi peluncuran dengan parametermaxUnavailable
yang setara dengan0
.strategy: rollingUpdate: maxSurge: 1 maxUnavailable: 0
Untuk memecahkan masalah traffic yang tidak mencapai endpoint, pastikan aturan firewall mengizinkan traffic TCP masuk ke endpoint Anda dalam rentang
130.211.0.0/22
dan35.191.0.0/16
. Untuk mempelajari lebih lanjut, lihat Menambahkan Health Check di dokumentasi Cloud Load Balancing.Lihat layanan backend di project Anda. String nama layanan backend yang relevan mencakup nama dan namespace Layanan GKE yang sesuai:
gcloud compute backend-services list
Ambil status respons backend dari layanan backend:
gcloud compute backend-services get-health BACKEND_SERVICE_NAME
Jika semua backend tidak responsif, firewall, Ingress, atau Layanan Anda mungkin salah dikonfigurasi.
Jika beberapa backend tidak responsif dalam waktu singkat, kemungkinan penyebabnya adalah latensi pemrograman jaringan.
Jika beberapa backend tidak muncul dalam daftar layanan backend, kemungkinan penyebabnya adalah latensi pemrograman. Anda dapat memverifikasinya dengan menjalankan perintah berikut, dengan
NEG_NAME
adalah nama layanan backend. (NEG dan layanan backend menggunakan nama yang sama):gcloud compute network-endpoint-groups list-network-endpoints NEG_NAME
Periksa apakah semua endpoint yang diharapkan ada di NEG.
Jika Anda memiliki sedikit backend (misalnya, 1 Pod) yang dipilih oleh load balancer berbasis container, sebaiknya tingkatkan jumlah replika dan distribusikan Pod backend di semua zona yang dicakup cluster GKE. Tindakan ini akan memastikan infrastruktur load balancer dasar sudah diprogram sepenuhnya. Jika tidak, pertimbangkan untuk membatasi Pod backend ke satu zona.
Jika Anda mengonfigurasi kebijakan jaringan untuk endpoint, pastikan traffic masuk dari subnet khusus Proxy diizinkan.
Peluncuran terhenti
- Gejala
- Peluncuran peluncuran Deployment yang diupdate terhenti, dan jumlah replika terbaru tidak sesuai dengan jumlah replika yang diinginkan.
- Kemungkinan penyebab
Health check deployment gagal. Image container mungkin buruk atau health check mungkin salah dikonfigurasi. Penggantian peluncuran Pod menunggu hingga Pod yang baru dimulai lulus gate kesiapan Pod-nya. Ini hanya terjadi jika Pod merespons health check load balancer. Jika Pod tidak merespons, atau jika health check salah dikonfigurasi, kondisi gate kesiapan tidak dapat terpenuhi dan peluncuran tidak dapat dilanjutkan.
Jika menggunakan
kubectl
1.13 atau yang lebih tinggi, Anda dapat memeriksa status gateway kesiapan Pod dengan perintah berikut:kubectl get pod POD_NAME -o wide
Periksa kolom
READINESS GATES
.Kolom ini tidak ada di
kubectl
1.12 dan versi sebelumnya. Pod yang ditandai sebagai berada dalam statusREADY
mungkin memiliki gate kesiapan yang gagal. Untuk memastikannya, gunakan perintah berikut:kubectl get pod POD_NAME -o yaml
Gate kesiapan dan statusnya tercantum di output.
- Resolusi
Verifikasi bahwa image container di spesifikasi Pod Deployment Anda berfungsi dengan benar dan dapat merespons health check. Pastikan health check dikonfigurasi dengan benar.
Error mode yang terdegradasi
- Gejala
Mulai dari GKE versi 1.29.2-gke.1643000, Anda mungkin mendapatkan peringatan berikut di layanan Anda di Logs Explorer saat NEG diperbarui:
Entering degraded mode for NEG <service-namespace>/<service-name>-<neg-name>... due to sync err: endpoint has missing nodeName field
- Kemungkinan penyebab
Peringatan ini menunjukkan bahwa GKE telah mendeteksi kesalahan konfigurasi endpoint selama update NEG berdasarkan objek
EndpointSlice
, yang memicu proses penghitungan yang lebih mendalam yang disebut mode menurun. GKE terus memperbarui NEG berdasarkan upaya terbaik, dengan memperbaiki kesalahan konfigurasi atau mengecualikan endpoint yang tidak valid dari update NEG.Beberapa error umum adalah:
endpoint has missing pod/nodeName field
endpoint corresponds to an non-existing pod/node
endpoint information for attach/detach operation is incorrect
- Resolusi
Biasanya, status sementara menyebabkan peristiwa ini dan peristiwa ini akan diperbaiki dengan sendirinya. Namun, peristiwa yang disebabkan oleh kesalahan konfigurasi dalam objek
EndpointSlice
kustom tetap tidak terselesaikan. Untuk memahami kesalahan konfigurasi, periksa objekEndpointSlice
yang sesuai dengan layanan:kubectl get endpointslice -l kubernetes.io/service-name=<service-name>
Validasi setiap endpoint berdasarkan error dalam peristiwa.
Untuk mengatasi masalah ini, Anda harus mengubah objek
EndpointSlice
secara manual. Pembaruan tersebut memicu NEG untuk diperbarui lagi. Setelah kesalahan konfigurasi tidak ada lagi, output-nya akan mirip dengan yang berikut ini:NEG <service-namespace>/<service-name>-<neg-name>... is no longer in degraded mode
Masalah umum
Load balancing berbasis container di GKE memiliki masalah umum berikut:
Pembersihan sampah memori tidak selesai
Sampah GKE membersihkan load balancer berbasis container setiap dua menit. Jika cluster dihapus sebelum load balancer sepenuhnya dihapus, Anda harus menghapus NEG load balancer secara manual.
Lihat NEG di project Anda dengan menjalankan perintah berikut:
gcloud compute network-endpoint-groups list
Di output perintah, cari NEG yang relevan.
Untuk menghapus NEG, jalankan perintah berikut, dengan mengganti NEG_NAME
dengan nama NEG:
gcloud compute network-endpoint-groups delete NEG_NAME
Menyelaraskan peluncuran workload dengan penerapan endpoint
Saat Anda men-deploy workload ke cluster, atau saat mengupdate workload yang sudah ada, load balancer berbasis container dapat memerlukan waktu lebih lama untuk menerapkan endpoint baru daripada yang diperlukan untuk menyelesaikan peluncuran workload. Contoh Deployment yang Anda deploy dalam panduan ini menggunakan dua kolom untuk menyelaraskan peluncurannya dengan penerapan endpoint: terminationGracePeriodSeconds
dan minReadySeconds
.
terminationGracePeriodSeconds
memungkinkan Pod
dimatikan secara tuntas dengan menunggu koneksi dihentikan setelah Pod
dijadwalkan untuk dihapus.
minReadySeconds
akan menambahkan periode latensi setelah Pod
dibuat. Anda menentukan jumlah detik minimum kapan Pod baru akan berada dalam
status Ready
,
tanpa container-nya mengalami error,
agar Pod dapat dianggap tersedia.
Anda harus mengonfigurasi nilai minReadySeconds
dan terminationGracePeriodSeconds
workload menjadi 60 detik atau lebih untuk memastikan layanan tidak terganggu karena peluncuran workload.
terminationGracePeriodSeconds
tersedia di semua spesifikasi Pod, dan minReadySeconds
tersedia untuk Deployment dan DaemonSet.
Untuk mempelajari lebih lanjut cara menyesuaikan peluncuran, lihat RollingUpdateStrategy.
initialDelaySeconds
di Pod readinessProbe
tidak dipatuhi
Anda mungkin berharap konfigurasi initialDelaySeconds
di readinessProbe
Pod akan dipatuhi oleh load balancer berbasis container. Namun, readinessProbe
diterapkan oleh kubelet, dan konfigurasi initialDelaySeconds
akan mengontrol health check kubelet, bukan load balancer berbasis container. Load balancing berbasis container memiliki health check load balancing-nya sendiri.
Langkah berikutnya
- Pelajari lebih lanjut NEG.
- Pelajari lebih lanjut cluster VPC native.