Blog AWS Indonesia
Mengekspos Aplikasi Kubernetes, Bagian 3: NGINX Ingress Controller
Perkenalan
Seri Mengekspos Aplikasi Kubernetes berfokus pada cara untuk mengekspos aplikasi yang berjalan di Kubernetes cluster untuk akses eksternal.
Di Bagian 1 dari seri ini, kita membahas resource Service dan Ingress yang menentukan dua cara untuk mengontrol traffic masuk dalam Kubernetes cluster. Kita membahas penanganan tipe resource ini melalui Service dan Ingress controller, diikuti dengan gambaran umum kelebihan dan kekurangan beberapa varian implementasi controller.
Di Bagian 2, kita telah membahas pengaturan, konfigurasi, kemungkinan use case, dan keterbatasan implementasi dari open-source Ingress controller, AWS Load Balancer Controller.
Dalam posting ini, Bagian 3, kita akan berfokus pada tambahan implementasi open-source Ingress controller: NGINX Ingress Controller. Kami akan memberi panduan atas beberapa fitur dan perbedaannya dengan AWS Load Balancer Controller.
Arsitektur NGINX Ingress Controller
Di Bagian 1, kami mendeskripsikan tipe Ingress controller yang menggunakan in-cluster layer 7 reverse proxy, yang diwakili oleh diagram berikut:
Implementasi NGINX Ingress Controller mengikuti arsitektur di atas:
Controller tersebut mendeploy, mengonfigurasi, dan mengatur Pod yang berisi instans nginx, open-source populer untuk HTTP dan reverse proxy server. Pod itu diekspos melalui Service resource dari controller tersebut, yang menerima semua trafik untuk aplikasi-aplikasi yang diwakili oleh Ingress dan backend Service resource. Controller tersebut menerjemahkan konfigurasi Ingress dan Service, dikombinasikan dengan tambahan parameter yang disediakan secara statik, ke dalam konfigurasi standar nginx. Controller kemudian menginjeksi konfigurasi tersebut ke dalam Pod nginx, yang melakukan routing trafik ke Pod aplikasi.
Service dari NGINX Ingress controller diekspos untuk trafik eksternal melalui sebuah load balancer. Service yang sama itu dapat dikonsumsi secara internal melalui nama cluster DNS yang lazim:<service-name>.<namespace-name>.svc.cluster.local.
Panduan
Sekarang kita paham bagaimana NGINX Ingress Controller beroperasi, saatnya untuk menjalankannya.
Prasyarat
1. Memiliki Akses ke akun AWS
Anda akan memerlukan akun AWS dan kemampuan untuk berkomunikasi dengannya dari terminal Anda, menggunakan AWS Command Line Interface (AWS CLI) dan tool serupa.
Dalam contoh kode berikutnya, kita akan menemukan beberapa token yang tidak dapat diberikan nilai aslinya (misalnya, yang mengacu pada ID akun atau Region AWS). Ini harus diganti dengan nilai yang sesuai dengan environment Anda.
2. Buat Cluster
Kita akan menggunakan eksctl untuk membuat cluster Amazon EKS, yang selain membuat cluster itu sendiri, juga membuat dan mengonfigurasi network resource yang diperlukan (sebuah virtual private cloud — VPC, subnet, dan security group).
File konfigurasi eksctl
berikut mendefinisikan cluster Amazon EKS dan pengaturannya:
apiVersion: eksctl.io/v1alpha5
kind: ClusterConfig
metadata:
name: nginx-ingress-controller-walkthrough
region: ${AWS_REGION}
version: '1.23'
iam:
withOIDC: true
managedNodeGroups:
- name: main-ng
instanceType: m5.large
desiredCapacity: 1
privateNetworking: true
Masukkan kode di atas dalam file config.yml
.
Verifikasi keberadaan environment variables berikut: AWS_REGION
dan AWS_ACCOUNT
dan buat cluster:
envsubst < config.yml | eksctl create cluster -f -
Panduan ini menggunakan platform Amazon EKS versi eks.3
untuk Kubernetes versi 1.23
.
Untuk singkatnya, konfigurasi di atas tidak mempertimbangkan banyak aspek pembuatan dan manajemen cluster Kubernetes seperti security dan monitoring. Untuk informasi selengkapnya dan praktik terbaik, jelajahi dokumentasi Amazon EKS dan eksctl.
Verifikasi bahwa cluster aktif dan berjalan:
kubectl get nodes
kubectl get pods -A
Perintah di atas harus mengembalikan satu node Amazon EKS dan empat Pod yang sedang berjalan.
4. Instalasi Helm
Kita akan menggunakan Helm, package manager populer untuk Kubernetes, untuk menginstal dan mengonfigurasi controller. Ikuti petunjuk instalasi Helm di sini.
Menginstal NGINX Ingress Controller
1. Menginstal Controller menggunakan Helm
helm repo add ingress-nginx https://kubernetes.github.io/ingress-nginx
helm upgrade -i ingress-nginx ingress-nginx/ingress-nginx \
--version 4.2.3 \
--namespace kube-system \
--set controller.service.type=ClusterIP
kubectl -n kube-system rollout status deployment ingress-nginx-controller
kubectl get deployment -n kube-system ingress-nginx-controller
Kita mengatur Service controller ke ClusterIP
untuk mencegah pembuatan-ulang load balancer ketika kita mengubah berbagai parameter konfigurasi dari controller selama panduan. Kita akan membahas pembuatan load balancer menjelang akhir artikel.
Mendeploy Service untuk Testing
1. Membuat Namespace untuk Service
kubectl create namespace apps
2. Membuat Manifest File untuk Service
apiVersion: apps/v1
kind: Deployment
metadata:
name: ${SERVICE_NAME}
namespace: ${NS}
labels:
app.kubernetes.io/name: ${SERVICE_NAME}
spec:
selector:
matchLabels:
app.kubernetes.io/name: ${SERVICE_NAME}
replicas: 1
template:
metadata:
labels:
app.kubernetes.io/name: ${SERVICE_NAME}
spec:
terminationGracePeriodSeconds: 0
containers:
- name: ${SERVICE_NAME}
image: hashicorp/http-echo
imagePullPolicy: IfNotPresent
args:
- -listen=:3000
- -text=${SERVICE_NAME}
ports:
- name: app-port
containerPort: 3000
resources:
requests:
cpu: 0.125
memory: 50Mi
---
apiVersion: v1
kind: Service
metadata:
name: ${SERVICE_NAME}
namespace: ${NS}
labels:
app.kubernetes.io/name: ${SERVICE_NAME}
spec:
type: ClusterIP
selector:
app.kubernetes.io/name: ${SERVICE_NAME}
ports:
- name: svc-port
port: 80
targetPort: app-port
protocol: TCP
Service di atas, berdasarkan http-echo container image, yang menjawab permintaan apa pun dengan nama Service tersebut, sebagaimana didefinisikan di atas oleh token ${SERVICE_NAME}
. Kami juga mendefinisikan hanya satu replica agar tidak rumit.
3. Deploy dan Verifikasi Service
Jalankan perintah berikut (kami akan menggunakan Service ini di seluruh posting):
SERVICE_NAME=first NS=apps envsubst < service.yml | kubectl apply -f -
SERVICE_NAME=second NS=apps envsubst < service.yml | kubectl apply -f -
SERVICE_NAME=third NS=apps envsubst < service.yml | kubectl apply -f -
SERVICE_NAME=fourth NS=apps envsubst < service.yml | kubectl apply -f -
SERVICE_NAME=error NS=apps envsubst < service.yml | kubectl apply -f -
SERVICE_NAME=another-error NS=apps envsubst < service.yml | kubectl apply -f -
Verifikasi bahwa semua resource terdeploy:
kubectl get pod,svc -n apps
Deploy Ingress Sederhana
1. Buat Manifest File untuk Ingress dan Deploy Ingress
Salin kode berikut ke dalam file ingress.yml
:
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ${NS}-ingress
namespace: ${NS}
spec:
ingressClassName: nginx
rules:
- http:
paths:
- path: /first
pathType: Prefix
backend:
service:
name: first
port:
name: svc-port
- path: /second
pathType: Prefix
backend:
service:
name: second
port:
name: svc-port
Dengan cara sama yang telah kita lihat dengan AWS Load Balancer Controller, kita menargetkan NGINX Ingress Controller dengan menggunakan property ingressClassName
yang ditetapkan ke nginx
, yang merupakan nama dari default IngressClass yang terinstall bersama controller.
Deploy Ingress dengan menjalankan perintah berikut:
NS=apps envsubst < ingress.yml | kubectl apply -f -
Setelah beberapa saat (IP address binding dapat memakan waktu sedikit lebih lama) kita semestinya dapat melihat status dari Ingress resource:
kubectl get ingress -n apps
Hasilnya semestinya akan mirip seperti:
Kolom ADDRESS
dan PORT
di atas telah ditetapkan sesuai dengan IP address dan port dari Service milik controller.
Karena kita mengonfigurasi controller untuk membuat Service-nya dengan tipe ClusterIP
, kita perlu membuat cara untuk berkomunikasi dengannya dengan menyiapkan port-forwarding ke service tersebut.
kubectl port-forward -n kube-system svc/ingress-nginx-controller 8080:80
2. Menguji Ingress
Sekarang, kita dapat mengirim requests ke Controller service:
curl -sS localhost:8080/first
curl -sS localhost:8080/second
curl -sS localhost:8080/third
Hasil berikut mengindikasikan bahwa Ingress resource telah dideploy dan dikonfigurasi dengan tepat:
Sekilas mengenai IngressClass
Seperti yang kami sebutkan, sebuah IngressClass bernama nginx
diinstal bersamaan dengan controller dan semestinya nampak seperti berikut:
apiVersion: networking.k8s.io/v1
kind: IngressClass
metadata:
name: nginx
labels:
app.kubernetes.io/name: nginx
...
spec:
controller: k8s.io/ingress-nginx
Berbeda dengan AWS Load Balancer Controller, NGINX Ingress Controller tidak mendukung IngressClass parameters.
Kita dapat mendefinisikan sebuah IngressClass untuk menjadi default dengan menambahkan anotasi ingressclass.kubernetes.io/is-default-class: "true"
atau menetapkan IngressClass yang diinstal bersama controller untuk menjadi defaultnya:
helm upgrade -i ingress-nginx ingress-nginx/ingress-nginx \
--namespace kube-system \
--set controller.ingressClassResource.default=true \
...
Default Backend dan Penanganan Error
Kita telah melihat bahwa ketika kita mengirim sebuah request ke sebuah path yang tidak ditangani oleh salah satu Ingress resource, nginx merespon dengan 404
. Respon ini ini datang dari default backend yang diinstal bersama dengan controller. Satu cara untuk menyesuaikannya adalah dengan menetapkan konfigurasi controller.defaultBackend
, misalnya melalui Helm file values.yaml
, yang nanti ditampilkan di posting ini. Cara lainnya adalah dengan menetapkan anotasi nginx.ingress.kubernetes.io/default-backend
pada Ingress resource.
Setelah itu, kita dapat mengonfigurasinya sesuai dengan spesifikasi, yang nanti ditampilkan.
1. Update dan Mendeploy Ingress
Perbaharui file ingress.yml
dengan konten berikut:
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ${NS}-ingress
namespace: ${NS}
spec:
ingressClassName: nginx
defaultBackend:
service:
name: error
port:
name: svc-port
rules:
- http:
paths:
- path: /first
pathType: Prefix
backend:
service:
name: first
port:
name: svc-port
- path: /second
pathType: Prefix
backend:
service:
name: second
port:
name: svc-port
Mendeploy:
NS=apps envsubst < ingress.yml | kubectl apply -f -
2. Menguji Ingress
Sekarang, kita dapat mengirim request lagi:
curl -sS localhost:8080/first
curl -sS localhost:8080/second
curl -sS localhost:8080/third
Ini akan bekerja seperti yang diharapkan, dengan default backend:
Lebih dari Satu Resource Ingress
Sering terjadi adanya lebih dari satu ingress resource yang mungkin dimiliki tim-tim yang berbeda atau bagian-bagian terpisah dari aplikasi yang lebih besar. Resource tersebut butuh dikembangkan dan dideploy terpisah, namun tidak membutuhkan konfigurasi berbeda dan dapat ditangani oleh satu instalasi controller.
NGINX Ingress Controller mendukung penggabungan Ingress resource, namun tanpa dapat mendefinisikan urutan dan pengelompokan resource tersebut dengan spesifik, seperti yang telah kita lihat pada AWS Load Balancer Controller.
Routing berbasis Host
Sejauh ini, semua contoh berasumsi bahwa semua requests dirouting ke domain yang sama dan Ingress resource digabungkan di bawah host *.*
yang sama. Anda dapat juga mendefinisikan secara eksplisit Service mana yang dilayani domain yang mana dan membuat segmentasi resource tersebut (atau gabungan dari mereka) di bawah pengaturan host di Ingress.
1. Update dan Mendeploy Ingress
Perbaharui ingress.yml
:
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ${NS}-ingress
namespace: ${NS}
spec:
ingressClassName: nginx
defaultBackend:
service:
name: error
port:
name: svc-port
rules:
- host: a.example.com
http:
paths:
- path: /first
pathType: Prefix
backend:
service:
name: first
port:
name: svc-port
- host: b.example.com
http:
paths:
- path: /second
pathType: Prefix
backend:
service:
name: second
port:
name: svc-port
Jalankan:
NS=apps envsubst < ingress.yml | kubectl apply -f -
2. Menguji Ingress
Kita dapat membuat simulasi requests ke domains yang berbeda dengan curl
:
curl localhost:8080/first -H 'Host: a.example.com'
curl localhost:8080/second -H 'Host: b.example.com'
curl localhost:8080/first -H 'Host: b.example.com'
curl localhost:8080/first -H 'Host: b.example.net'
Hasilnya semestinya sebagai berikut:
Kita harapkan dua requests terakhir dirouting ke default backend, karena yang satu dikirim ke path yang tidak didefinisikan di host tersebut dan satu lainnya menggunakan nilai host yang non-exist.
Kita dapat menangani kedua hosts dengan mengarahkan DNS records untuk a.myapp.com
dan b.myapp.com
ke Service dari NGINX Ingress Controller. Untuk melengkapi tugas ini, kita mengekspos Service ke trafik eksternal (misalnya melalui external load balancer). Kita diskusikan lebih detil nanti di posting ini.
Tipe Ingress Path, Regex dan Rewrite
Sejauh ini, kita telah mendefinisikan Prefix sebagai tipe path untuk Ingress rule kita. Kita dapat juga menetapkannya menjadi Exact, menggunakan regex di path ini atau mendefinisikan rewrite rule.
1. Update dan mendeploy Ingress
Mari ubah definisi Ingress di file ingress.yml
dan deploy ulang:
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: ${NS}-ingress
namespace: ${NS}
annotations:
nginx.ingress.kubernetes.io/rewrite-target: /$2
spec:
ingressClassName: nginx
defaultBackend:
service:
name: error
port:
name: svc-port
rules:
- http:
paths:
- path: /first/(.*)/foo
pathType: Prefix
backend:
service:
name: first
port:
name: svc-port
Anotasi nginx.ingress.kubernetes.io/rewrite-target
mendefinisikan capturing group mana, seperti didefinisikan di path dari rule kita, yang seharusnya dikirim ke Service terkait. Jadi /$2
mengirim konten dari capturing group kedua sebagai path dari request ke Service.
Deploy ingress:
NS=apps envsubst < ingress.yml | kubectl apply -f -
2. Menguji Ingress
Jalankan:
curl -sS localhost:8080/first
curl -sS localhost:8080/first/foo
curl -sS localhost:8080/first/bar
curl -sS localhost:8080/first/bar/foo
Sekarang kita akan dapatkan hasil berikut:
Mengekspos NGINX Ingress Controller melalui sebuah Load Balancer
Menggunakan in-tree Service Controller
Cara paling sederhana adalah dengan membiarkan in-tree controller, yang kita diskusikan di Bagian 1, melayani Service. Untuk melakukan hal itu, kita dapat menetapkan tipe Service sebagai LoadBalancer
, yang dapat membuat sebuah AWS Classic Load Balancer:
helm upgrade -i ingress-nginx ingress-nginx/ingress-nginx \
--namespace kube-system \
--set controller.service.type=LoadBalancer \
...
Kita dapat juga mengubahnya ke AWS Network Load Balancer yang direkomendasikan dan lebih modern:
helm upgrade -i ingress-nginx ingress-nginx/ingress-nginx \
--namespace kube-system \
--set controller.service.type=LoadBalancer \
--set controller.service.annotations."service\.beta\.kubernetes\.io/aws-load-balancer-type"="nlb" \
...
Kita dapat juga menggunakan Helm file values.yml
untuk menyediakan parameter konfigurasinya dengan lebih mudah, dengan efek yang sama. Kita lihat contoh penggunaannya di bagian berikutnya.
Penggunaan dengan AWS Load Balancer Controller
Jika kita ingin mengontrol lebih banyak hal terkait Network Load Balancer yang dibuat untuk Service, kita dapat menginstal sebuah Service Controller. AWS Load Balancer Controller adalah pilihan yang direkomendasikan.
Ketika AWS Load Balancer Controller juga menangani Ingress resource, dia melakukannya untuk Ingress class yang berbeda — alb, maka seharusnya tidak ada tabrakan dengan NGINX Ingress Controller.
Membuat AWS NLB untuk NGINX Ingress Controller
Kita telah mendiskusikan instalasi dari controller di Bagian 2 dari seri ini, jadi ini seharusnya cukup familiar.
1. Membuat AWS Load Balancer Controller Identity and Access Management (IAM) Policy
Buat AWSLoadBalancerControllerIAMPolicy
menggunakan instruksi berikut (hanya #2 dan #3) yang mengatur IAM Roles for Service Accounts untuk menyediakan permissions untuk controller.
Perhatikan bahwa registrasi OIDC IAM provider dilakukan secara otomatis oleh eksctl
menggunakan konfigurasi cluster di atas dan tidak perlu dilakukan secara eksplisit.
2. Membuat sebuah Service Account untuk AWS Load Balancer Controller
Pada Bagian 2 dari seri, kita membuat sebuah service account untuk AWS Load Balancer Controller sebagai bagian dari pembuatan eksctl
cluster. Kali ini kita akan membuatnya secara terpisah.
eksctl create iamserviceaccount \
--cluster=nginx-ingress-controller-walkthrough \
--name=aws-load-balancer-controller \
--namespace=kube-system \
--attach-policy-arn=arn:aws:iam::${AWS_ACCOUNT}:policy/AWSLoadBalancerControllerIAMPolicy \
--approve
3. Menginstal CRD
Perintah berikut menginstal CustomResourceDefinitions
yang dibutuhkan agar Controller dapat berfungsi.
kubectl apply -k \
"github.com/aws/eks-charts/stable/aws-load-balancer-controller/crds?ref=master"
4. Menginstal Controller menggunakan Helm
helm repo add eks https://aws.github.io/eks-charts
helm upgrade -i aws-load-balancer-controller eks/aws-load-balancer-controller \
-n kube-system \
--set clusterName=nginx-ingress-controller-walkthrough \
--set serviceAccount.create=false \
--set serviceAccount.name=aws-load-balancer-controller
kubectl -n kube-system rollout status deployment aws-load-balancer-controller
kubectl get deployment -n kube-system aws-load-balancer-controller
5. Mendeploy ulang NGINX Ingress Controller
Ubah konfigurasi untuk Helm chart controller dan buat sebuah file values.yml
:
controller:
service:
type: LoadBalancer
annotations:
service.beta.kubernetes.io/aws-load-balancer-name: apps-ingress
service.beta.kubernetes.io/aws-load-balancer-type: external
service.beta.kubernetes.io/aws-load-balancer-scheme: internet-facing
service.beta.kubernetes.io/aws-load-balancer-nlb-target-type: ip
service.beta.kubernetes.io/aws-load-balancer-healthcheck-protocol: http
service.beta.kubernetes.io/aws-load-balancer-healthcheck-path: /healthz
service.beta.kubernetes.io/aws-load-balancer-healthcheck-port: 10254
Di sini, kita mengubah tipe Service, mendefinisikan nama load balancer (yang akan menjadi sebuah Network Load Balancer), membuatnya dapat diakses dari internet sehingga kita dapat mengaksesnya, mendefinisikan tipe targetnya menjadi ip
, dan mengonfigurasikan health check untuk NGINX server.
Untuk informasi lebih lanjut mengenai AWS Load Balancer Controller Service annotations, lihat di sini.
Deploy ulang controller:
helm upgrade -i ingress-nginx ingress-nginx/ingress-nginx \
--version 4.2.3 \
--namespace kube-system \
--values values.yml
kubectl -n kube-system rollout status deployment ingress-nginx-controller
kubectl get deployment -n kube-system ingress-nginx-controller
6. Menguji Ingress
Perhatikan bahwa kita menggunakan definisi Ingress yang sama yang kita gunakan untuk mengilustrasikan tipe path dan fitur rewrite dari controller.
Simpan URL dari Network Load Balancer:
export NLB_URL=$(kubectl get -n kube-system service/ingress-nginx-controller \
-o jsonpath='{.status.loadBalancer.ingress[0].hostname}')
Setelah beberapa menit, load balancer akan tersedia dan kita dapat mengirim requests:
curl ${NLB_URL}/first
curl ${NLB_URL}/first/foo
curl ${NLB_URL}/first/bar
curl ${NLB_URL}/first/bar/foo
Ini akan menghasilkan hasil yang kita terima sebelumnya, seperti yang kita harapkan:
Menghubungkan NGINX Ingress Controller ke Load Balancer yang ada
Di samping cara Service controller yang kita deskripsikan sebelumnya, kita juga dapat membuat AWS Application Load Balancer atau Network Load Balander melalui AWS CLI atau Infrastructure-as-Code (misalnya AWS CloudFormation, AWS CDK, atau Terraform).
Kemudian kita dapat menggunakan TargetGroupBinding
, yang merupakan bagian dari custom resource definitions yang telah diinstal di atas. Resource tersebut mengikat sebuah Service (yang dipilih dengan Amazon Resource Name (ARN) nya) dengan mendaftarkan Pod dari Service tersebut (atau instance yang mendasarinya) sebagai target dalam grup tersebut.
Hal ini mungkin berguna ketika load balancernya digunakan oleh compute resource lainnya. Pada kasus yang jarang terjadi, hal itu juga berguna jika Anda perlu menetapkan sebuah Application Load Balancer untuk menggunakan salah satu fitur unik di atas in-cluster Layer 7 proxy.
Lebih dari Satu Ingress Controller
Pada beberapa kasus, kita dapat mengonfigurasi beberapa instans NGINX Ingress Controller dalam cluster untuk menangani Ingress resource yang berbeda. Hal ini dapat dicapai dengan memberikan beberapa konfigurasi berbeda pada controller. Berbeda dengan AWS Load Balancer Controller, NGINX Ingress Controller mendukung setup semacam itu.
Berikut adalah contoh NGINX Ingress Controller, dengan nama unik, Ingress class, dan nilai controller yang tercermin di Ingress class:
helm upgrade -i ingress-nginx-one ingress-nginx/ingress-nginx \
--namespace kube-system \
--set controller.ingressClassResource.controllerValue=k8s.io/ingress-nginx-one \
--set controller.ingressClassResource.name=nginx-one \
...
Sekarang, Ingress resource dapat menarget controller ini melalui ingressClassName
mereka dengan menetapkan nilainya ke nginx-one
.
Pembersihan
Panduan kami telah sampai diakhir. Untuk menghapus resource yang dibuat selama panduan, Anda dapat menjalankan:
helm uninstall -n kube-system ingress-nginx
helm uninstall -n kube-system aws-load-balancer-controller
envsubst < config.yml | eksctl delete cluster -f -
aws iam delete-policy --policy-arn arn:aws:iam::${AWS_ACCOUNT}:policy/AWSLoadBalancerControllerIAMPolicy
Kesimpulan
Selama seri ini, kami menunjukkan variasi dari Ingress controller, sambil menyoroti beberapa hal berbeda yang mereka lakukan.
NGINX Ingress Controller memanfaatkan fitur nginx. Meskipun controller ini adalah controller yang lebih fleksibel, dia memiliki kekurangan terkait maintenance, patching, dan scaling pada komponen di data path dari request.
Sebaliknya, AWS Load Balancer Controller mengalihkan beban tersebut ke layanan managed AWS Elastic Load Balancing yang highly available, scalable, dan telah teruji, dengan fitur-fiturnya tersebut menyediakan pilihan konfigurasi yang dibutuhkan.
Pilihan antara fleksibilitas yang ekstrim dan kesederhanaan operasional didasari kebutuhan dari aplikasi yang dideploy. Hal ini, beserta Service dan Ingress controller lain yang belum kita bahas di seri ini, semestinya menyediakan banyak pilihan untuk mengekspos aplikasi-aplikasi ini untuk trafik eksternal.
Artikel ini diterjemahkan dari artikel asli berjudul “Exposing Kubernetes Applications, Part 3: NGINX Ingress Controller” yang ditulis oleh Dmitry Notels dan Tsahi Duek.