가시다(gasida) 님이 진행하는 Istio Hands-on Study 1기 과정을 참여하여 정리한 글입니다. 3주차는 Traffic control, Resilience 주제로 학습을 진행하였습니다
5장에서는 서비스 간 트래픽을 세밀하게 제어하는 방법에 대해 다룹니다.
VirtualService로 정의하고,ServiceEntry로 통제하고,Sidecar 리소스로 제한하거나 조정하며,Gateway를 통해 제어한다.이런 구성들을 통해 Istio는 안정적이고 유연한 트래픽 관리를 가능하게 한다.
✅ 리소스에 대한 한 줄 요약
| 리소스 | 한 줄 설명 |
|---|---|
VirtualService | 서비스에 대한 세부적인 트래픽 라우팅 규칙을 정의한다. |
ServiceEntry | 클러스터 외부 서비스와의 통신을 허용하고 이를 제어한다. |
Sidecar | 특정 네임스페이스 또는 워크로드의 프록시 설정 범위와 아웃바운드 제어를 구성한다. |
Gateway | 클러스터 외부에서 내부로 들어오는 트래픽을 제어하는 진입 지점이다. |
MeshConfig | Istio 메시 전역 설정을 담은 기본 설정값들의 모음이다. |
#
git clone https://github.com/AcornPublishing/istio-in-action
cd istio-in-action/book-source-code-master
pwd # 각자 자신의 pwd 경로
code .
# 아래 extramounts 생략 시, myk8s-control-plane 컨테이너 sh/bash 진입 후 직접 git clone 가능
kind create cluster --name myk8s --image kindest/node:v1.23.17 --config - <<EOF
kind: Cluster
apiVersion: kind.x-k8s.io/v1alpha4
nodes:
- role: control-plane
extraPortMappings:
- containerPort: 30000 # Sample Application (istio-ingrssgateway) HTTP
hostPort: 30000
- containerPort: 30001 # Prometheus
hostPort: 30001
- containerPort: 30002 # Grafana
hostPort: 30002
- containerPort: 30003 # Kiali
hostPort: 30003
- containerPort: 30004 # Tracing
hostPort: 30004
- containerPort: 30005 # Sample Application (istio-ingrssgateway) HTTPS
hostPort: 30005
- containerPort: 30006 # TCP Route
hostPort: 30006
- containerPort: 30007 # kube-ops-view
hostPort: 30007
extraMounts: # 해당 부분 생략 가능
- hostPath: /Users/sjkim/Labs/CloudNeta/istio/istio-in-action/book-source-code-master
# 각자 자신의 pwd 경로로 설정
containerPath: /istiobook
networking:
podSubnet: 10.10.0.0/16
serviceSubnet: 10.200.1.0/24
EOF
Creating cluster "myk8s" ...
✓ Ensuring node image (kindest/node:v1.23.17) 🖼
✓ Preparing nodes 📦
✓ Writing configuration 📜
✓ Starting control-plane 🕹️
✓ Installing CNI 🔌
✓ Installing StorageClass 💾
Set kubectl context to "kind-myk8s"
You can now use your cluster with:
kubectl cluster-info --context kind-myk8s
Have a nice day! 👋
# 설치 확인
docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
35c362211d0d kindest/node:v1.23.17 "/usr/local/bin/entr…" About a minute ago Up About a minute 0.0.0.0:30000-30007->30000-30007/tcp, 127.0.0.1:55153->6443/tcp myk8s-control-plane
# 노드에 기본 툴 설치
docker exec -it myk8s-control-plane sh -c 'apt update && apt install tree psmisc lsof wget bridge-utils net-tools dnsutils tcpdump ngrep iputils-ping git vim -y'
# (옵션) kube-ops-view
helm repo add geek-cookbook https://geek-cookbook.github.io/charts/
helm install kube-ops-view geek-cookbook/kube-ops-view --version 1.2.2 --set service.main.type=NodePort,service.main.ports.http.nodePort=30007 --set env.TZ="Asia/Seoul" --namespace kube-system
kubectl get deploy,pod,svc,ep -n kube-system -l app.kubernetes.io/instance=kube-ops-view
NAME READY UP-TO-DATE AVAILABLE AGE
deployment.apps/kube-ops-view 1/1 1 1 6m31s
NAME READY STATUS RESTARTS AGE
pod/kube-ops-view-79df45849b-92ksk 1/1 Running 0 6m31s
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/kube-ops-view NodePort 10.200.1.144 <none> 8080:30007/TCP 6m31s
NAME ENDPOINTS AGE
endpoints/kube-ops-view 10.10.0.3:8080 6m31s
## kube-ops-view 접속 URL 확인
open "http://localhost:30007/#scale=1.5"
open "http://localhost:30007/#scale=1.3"
# (옵션) metrics-server
helm repo add metrics-server https://kubernetes-sigs.github.io/metrics-server/
helm install metrics-server metrics-server/metrics-server --set 'args[0]=--kubelet-insecure-tls' -n kube-system
kubectl get all -n kube-system -l app.kubernetes.io/instance=metrics-server
# myk8s-control-plane 진입 후 설치 진행
docker exec -it myk8s-control-plane bash
-----------------------------------
# (옵션) 코드 파일들 마운트 확인
tree /istiobook/ -L 1
혹은
git clone ... /istiobook
# istioctl 설치
export ISTIOV=1.17.8
echo 'export ISTIOV=1.17.8' >> /root/.bashrc
curl -s -L https://istio.io/downloadIstio | ISTIO_VERSION=$ISTIOV sh -
cp istio-$ISTIOV/bin/istioctl /usr/local/bin/istioctl
istioctl version --remote=false
# default 프로파일 컨트롤 플레인 배포
istioctl install --set profile=default -y
# 설치 확인 : istiod, istio-ingressgateway, crd 등
kubectl get istiooperators -n istio-system -o yaml
kubectl get all,svc,ep,sa,cm,secret,pdb -n istio-system
NAME READY STATUS RESTARTS AGE
pod/istio-ingressgateway-996bc6bb6-n6trq 1/1 Running 0 81s
pod/istiod-7df6ffc78d-fhwmc 1/1 Running 0 97s
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/istio-ingressgateway LoadBalancer 10.200.1.172 <pending> 15021:32112/TCP,80:31965/TCP,443:30838/TCP 80s
service/istiod ClusterIP 10.200.1.182 <none> 15010/TCP,15012/TCP,443/TCP,15014/TCP 97s
NAME READY UP-TO-DATE AVAILABLE AGE
deployment.apps/istio-ingressgateway 1/1 1 1 81s
deployment.apps/istiod 1/1 1 1 97s
NAME DESIRED CURRENT READY AGE
replicaset.apps/istio-ingressgateway-996bc6bb6 1 1 1 81s
replicaset.apps/istiod-7df6ffc78d 1 1 1 97s
NAME REFERENCE TARGETS MINPODS MAXPODS REPLICAS AGE
horizontalpodautoscaler.autoscaling/istio-ingressgateway Deployment/istio-ingressgateway 7%/80% 1 5 1 80s
horizontalpodautoscaler.autoscaling/istiod Deployment/istiod 0%/80% 1 5 1 97s
NAME ENDPOINTS AGE
endpoints/istio-ingressgateway 10.10.0.8:15021,10.10.0.8:8080,10.10.0.8:8443 80s
endpoints/istiod 10.10.0.7:15012,10.10.0.7:15010,10.10.0.7:15017 + 1 more... 97s
NAME SECRETS AGE
serviceaccount/default 1 98s
serviceaccount/istio-ingressgateway-service-account 1 81s
serviceaccount/istio-reader-service-account 1 98s
serviceaccount/istiod 1 97s
serviceaccount/istiod-service-account 1 98s
NAME DATA AGE
configmap/istio 2 97s
configmap/istio-ca-root-cert 1 82s
configmap/istio-gateway-deployment-leader 0 83s
configmap/istio-gateway-status-leader 0 83s
configmap/istio-leader 0 83s
configmap/istio-namespace-controller-election 0 82s
configmap/istio-sidecar-injector 2 97s
configmap/kube-root-ca.crt 1 98s
NAME TYPE DATA AGE
secret/default-token-mt7sx kubernetes.io/service-account-token 3 98s
secret/istio-ca-secret istio.io/ca-root 5 83s
secret/istio-ingressgateway-service-account-token-q82j8 kubernetes.io/service-account-token 3 81s
secret/istio-reader-service-account-token-hwmrs kubernetes.io/service-account-token 3 98s
secret/istiod-service-account-token-x7bk2 kubernetes.io/service-account-token 3 98s
secret/istiod-token-kmnq7 kubernetes.io/service-account-token 3 97s
NAME MIN AVAILABLE MAX UNAVAILABLE ALLOWED DISRUPTIONS AGE
poddisruptionbudget.policy/istio-ingressgateway 1 N/A 0 81s
poddisruptionbudget.policy/istiod 1 N/A 0 97s
kubectl get cm -n istio-system istio -o yaml
kubectl get crd | grep istio.io | sort
NAME MIN AVAILABLE MAX UNAVAILABLE ALLOWED DISRUPTIONS AGE
poddisruptionbudget.policy/istio-ingressgateway 1 N/A 0 81s
poddisruptionbudget.policy/istiod 1 N/A 0 97s
root@myk8s-control-plane:/# kubectl get crd | grep istio.io | sort
authorizationpolicies.security.istio.io 2025-04-26T06:39:16Z
destinationrules.networking.istio.io 2025-04-26T06:39:16Z
envoyfilters.networking.istio.io 2025-04-26T06:39:16Z
gateways.networking.istio.io 2025-04-26T06:39:16Z
istiooperators.install.istio.io 2025-04-26T06:39:16Z
peerauthentications.security.istio.io 2025-04-26T06:39:16Z
proxyconfigs.networking.istio.io 2025-04-26T06:39:16Z
requestauthentications.security.istio.io 2025-04-26T06:39:16Z
serviceentries.networking.istio.io 2025-04-26T06:39:16Z
sidecars.networking.istio.io 2025-04-26T06:39:16Z
telemetries.telemetry.istio.io 2025-04-26T06:39:16Z
virtualservices.networking.istio.io 2025-04-26T06:39:16Z
wasmplugins.extensions.istio.io 2025-04-26T06:39:16Z
workloadentries.networking.istio.io 2025-04-26T06:39:16Z
workloadgroups.networking.istio.io 2025-04-26T06:39:16Z
# 보조 도구 설치
kubectl apply -f istio-$ISTIOV/samples/addons
serviceaccount/grafana created
configmap/grafana created
service/grafana created
deployment.apps/grafana created
configmap/istio-grafana-dashboards created
configmap/istio-services-grafana-dashboards created
deployment.apps/jaeger created
service/tracing created
service/zipkin created
service/jaeger-collector created
serviceaccount/kiali created
configmap/kiali created
clusterrole.rbac.authorization.k8s.io/kiali-viewer created
clusterrole.rbac.authorization.k8s.io/kiali created
clusterrolebinding.rbac.authorization.k8s.io/kiali created
role.rbac.authorization.k8s.io/kiali-controlplane created
rolebinding.rbac.authorization.k8s.io/kiali-controlplane created
service/kiali created
deployment.apps/kiali created
serviceaccount/prometheus created
configmap/prometheus created
clusterrole.rbac.authorization.k8s.io/prometheus created
clusterrolebinding.rbac.authorization.k8s.io/prometheus created
service/prometheus created
deployment.apps/prometheus created
kubectl get pod -n istio-system
grafana-b854c6c8-87bw8 1/1 Running 0 86s
istio-ingressgateway-996bc6bb6-n6trq 1/1 Running 0 3m46s
istiod-7df6ffc78d-fhwmc 1/1 Running 0 4m2s
jaeger-5556cd8fcf-v9n2x 1/1 Running 0 86s
kiali-648847c8c4-mnwfb 1/1 Running 0 86s
prometheus-7b8b9dd44c-8jqrb 2/2 Running 0 86s
# 빠져나오기
exit
-----------------------------------
# 실습을 위한 네임스페이스 설정
kubectl create ns istioinaction
kubectl label namespace istioinaction istio-injection=enabled
kubectl get ns --show-labels
# istio-ingressgateway 서비스 : NodePort 변경 및 nodeport 지정 변경 , externalTrafficPolicy 설정 (ClientIP 수집)
kubectl patch svc -n istio-system istio-ingressgateway -p '{"spec": {"type": "NodePort", "ports": [{"port": 80, "targetPort": 8080, "nodePort": 30000}]}}'
kubectl patch svc -n istio-system istio-ingressgateway -p '{"spec": {"type": "NodePort", "ports": [{"port": 443, "targetPort": 8443, "nodePort": 30005}]}}'
kubectl patch svc -n istio-system istio-ingressgateway -p '{"spec":{"externalTrafficPolicy": "Local"}}'
kubectl describe svc -n istio-system istio-ingressgateway
# NodePort 변경 및 nodeport 30001~30003으로 변경 : prometheus(30001), grafana(30002), kiali(30003), tracing(30004)
kubectl patch svc -n istio-system prometheus -p '{"spec": {"type": "NodePort", "ports": [{"port": 9090, "targetPort": 9090, "nodePort": 30001}]}}'
kubectl patch svc -n istio-system grafana -p '{"spec": {"type": "NodePort", "ports": [{"port": 3000, "targetPort": 3000, "nodePort": 30002}]}}'
kubectl patch svc -n istio-system kiali -p '{"spec": {"type": "NodePort", "ports": [{"port": 20001, "targetPort": 20001, "nodePort": 30003}]}}'
kubectl patch svc -n istio-system tracing -p '{"spec": {"type": "NodePort", "ports": [{"port": 80, "targetPort": 16686, "nodePort": 30004}]}}'
# Prometheus 접속 : envoy, istio 메트릭 확인
open http://127.0.0.1:30001
# Grafana 접속
open http://127.0.0.1:30002
# Kiali 접속 1 : NodePort
open http://127.0.0.1:30003
# (옵션) Kiali 접속 2 : Port forward
kubectl port-forward deployment/kiali -n istio-system 20001:20001 &
open http://127.0.0.1:20001
# tracing 접속 : 예거 트레이싱 대시보드
open http://127.0.0.1:30004
# 내부 접속 테스트용 netshoot 파드 생성
cat <<EOF | kubectl apply -f -
apiVersion: v1
kind: Pod
metadata:
name: netshoot
spec:
containers:
- name: netshoot
image: nicolaka/netshoot
command: ["tail"]
args: ["-f", "/dev/null"]
terminationGracePeriodSeconds: 0
EOF
DevOps, MSA, 그리고 서비스 운영을 하다 보면 "배포"와 "릴리스"를 비슷하게 쓰는 경우가 많다. 하지만 이 둘은 실제로 다루는 범위와 목적이 다르다.
배포는 코드를 서버에 올리는 것, 릴리스는 사용자에게 기능을 오픈하는 것이다.
배포는 새로운 버전의 코드, 바이너리, 애플리케이션을 운영 환경(Production)에 설치하거나 배치하는 과정을 말한다.
예시: 새로운 버전의 백엔드 API를 서버에 배포했지만, 아직 모든 트래픽을 보내진 않은 상태
릴리스는 운영 환경에 배포된 버전을 사용자가 실제로 사용할 수 있게 하는 과정이다.
예시: 일부 사용자(5%)에게만 새로운 기능을 오픈하고 문제 없으면 점진적으로 전체 공개하는 것
과거에는 "배포 = 릴리스"였다. 하지만 현대 소프트웨어에서는 이 둘을 분리해서 다음과 같은 이점을 얻는다:
VirtualService는 요청을 어떤 서비스의 어떤 버전(서브셋)으로 보낼지 정의하는 Istio 리소스다.
🔧 주요 기능
# Let’s deploy v1 of our catalog service. From the root of the book’s source code, run the following command
kubectl apply -f services/catalog/kubernetes/catalog.yaml -n istioinaction
serviceaccount/catalog created
service/catalog created
deployment.apps/catalog created
# 확인
kubectl get pod -n istioinaction -owide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
catalog-6cf4b97d-5hwg7 2/2 Running 0 26s 10.10.0.14 myk8s-control-plane <none> <none>
# 도메인 질의를 위한 임시 설정 : 실습 완료 후에는 삭제 해둘 것
echo "127.0.0.1 catalog.istioinaction.io" | sudo tee -a /etc/hosts
cat /etc/hosts | tail -n 1
127.0.0.1 catalog.istioinaction.io
# netshoot로 내부에서 catalog 접속 확인
kubectl exec -it netshoot -- curl -s http://catalog.istioinaction/items | jq
[
{
"id": 1,
"color": "amber",
"department": "Eyewear",
"name": "Elinor Glasses",
"price": "282.00"
},
{
"id": 2,
"color": "cyan",
"department": "Clothing",
"name": "Atlas Shirt",
"price": "127.00"
},
{
"id": 3,
"color": "teal",
"department": "Clothing",
"name": "Small Metal Shoes",
"price": "232.00"
},
{
"id": 4,
"color": "red",
"department": "Watches",
"name": "Red Dragon Watch",
"price": "232.00"
}
]
# 외부 노출을 위해 Gateway 설정
cat ch5/catalog-gateway.yaml
apiVersion: networking.istio.io/v1alpha3
kind: Gateway
metadata:
name: catalog-gateway
spec:
selector:
istio: ingressgateway
servers:
- port:
number: 80
name: http
protocol: HTTP
hosts:
- "catalog.istioinaction.io"
kubectl apply -f ch5/catalog-gateway.yaml -n istioinaction
# 트래픽을 catalog 서비스로 라우팅하는 VirtualService 리소스 설정
cat ch5/catalog-vs.yaml
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: catalog-vs-from-gw
spec:
hosts:
- "catalog.istioinaction.io"
gateways:
- catalog-gateway
http:
- route:
- destination:
host: catalog
kubectl apply -f ch5/catalog-vs.yaml -n istioinaction
# 확인
kubectl get gw,vs -n istioinaction
NAME AGE
gateway.networking.istio.io/catalog-gateway 93s
NAME GATEWAYS HOSTS AGE
virtualservice.networking.istio.io/catalog-vs-from-gw ["catalog-gateway"] ["catalog.istioinaction.io"] 10s
# 도메인 질의를 위한 임시 설정 : 실습 완료 후에는 삭제 해둘 것
echo "127.0.0.1 catalog.istioinaction.io" | sudo tee -a /etc/hosts
cat /etc/hosts | tail -n 2
# istio-ingressgateway Service(NodePort)에 포트 정보 확인
kubectl get svc -n istio-system istio-ingressgateway -o jsonpath="{.spec.ports}" | jq
[
{
"name": "status-port",
"nodePort": 32112,
"port": 15021,
"protocol": "TCP",
"targetPort": 15021
},
{
"name": "http2",
"nodePort": 30000, # 순서1
"port": 80,
"protocol": "TCP",
"targetPort": 8080 # 순서2
},
{
"name": "https",
"nodePort": 30005,
"port": 443,
"protocol": "TCP",
"targetPort": 8443
}
]
# 호스트에서 NodePort(Service)로 접속 확인
curl -v -H "Host: catalog.istioinaction.io" http://localhost:30000
* Host localhost:30000 was resolved.
* IPv6: ::1
* IPv4: 127.0.0.1
* Trying [::1]:30000...
* Connected to localhost (::1) port 30000
* using HTTP/1.x
> GET / HTTP/1.1
> Host: catalog.istioinaction.io
> User-Agent: curl/8.13.0
> Accept: */*
>
* Request completely sent off
< HTTP/1.1 200 OK
< x-powered-by: Express
< vary: Origin, Accept-Encoding
< access-control-allow-credentials: true
< accept-ranges: bytes
< cache-control: public, max-age=0
< last-modified: Sat, 26 Oct 1985 08:15:00 GMT
< etag: W/"46f-7438674ba0"
< content-type: text/html; charset=UTF-8
< content-length: 1135
< date: Sat, 26 Apr 2025 08:36:44 GMT
< x-envoy-upstream-service-time: 28
< server: istio-envoy
<
<html>
<head>
<title>JSON Server</title>
<link rel="shortcut icon" href="favicon.ico"><link href="main.css" rel="stylesheet"></head>
<body>
<header>
<div class="container">
<h3>JSON Server</h3>
</div>
</header>
<main>
<div class="container">
<h4>Congrats!</h4>
<p>
You're successfully running JSON Server
<br> ✧*。٩(ˊᗜˋ*)و✧*。
</p>
<div id="resources"></div>
<p>
To access and modify resources, you can use any HTTP method
<br>
<code>GET</code>
<code>POST</code>
<code>PUT</code>
<code>PATCH</code>
<code>DELETE</code>
<code>OPTIONS</code>
</p>
<div id="custom-routes"></div>
<h4>Documentation</h4>
<p>
View
<a href="https://github.com/typicode/json-server">README</a>
</p>
</div>
</main>
<footer>
<div class="container">
<p>
To replace this page, create a
<code>./public/index.html</code> file.
</p>
</div>
</footer>
<script type="text/javascript" src="main.js"></script></body>
</html>
kubectl stern -l app=catalog -n istioinaction
+ catalog-6cf4b97d-5hwg7 › catalog
+ catalog-6cf4b97d-5hwg7 › istio-init
+ catalog-6cf4b97d-5hwg7 › istio-proxy
catalog-6cf4b97d-5hwg7 catalog JSON Server is running
catalog-6cf4b97d-5hwg7 catalog request path: /items
catalog-6cf4b97d-5hwg7 catalog blowups: {}
catalog-6cf4b97d-5hwg7 catalog number of blowups: 0
catalog-6cf4b97d-5hwg7 catalog GET catalog.istioinaction /items 200 502 - 2.367 ms
catalog-6cf4b97d-5hwg7 catalog GET /items 200 2.367 ms - 502
catalog-6cf4b97d-5hwg7 catalog GET catalog.istioinaction.io / 200 1135 - 6.165 ms
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164205Z info FLAG: --concurrency="2"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164222Z info FLAG: --domain="istioinaction.svc.cluster.local"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164225Z info FLAG: --help="false"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164226Z info FLAG: --log_as_json="false"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164227Z info FLAG: --log_caller=""
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164228Z info FLAG: --log_output_level="default:info"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164229Z info FLAG: --log_rotate=""
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164230Z info FLAG: --log_rotate_max_age="30"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164231Z info FLAG: --log_rotate_max_backups="1000"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164232Z info FLAG: --log_rotate_max_size="104857600"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164233Z info FLAG: --log_stacktrace_level="default:none"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164235Z info FLAG: --log_target="[stdout]"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164236Z info FLAG: --meshConfig="./etc/istio/config/mesh"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164237Z info FLAG: --outlierLogPath=""
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164239Z info FLAG: --proxyComponentLogLevel="misc:error"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164240Z info FLAG: --proxyLogLevel="warning"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164241Z info FLAG: --serviceCluster="istio-proxy"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164242Z info FLAG: --stsPort="0"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164243Z info FLAG: --templateFile=""
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164244Z info FLAG: --tokenManagerPlugin="GoogleTokenExchange"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164245Z info FLAG: --vklog="0"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.164246Z info Version 1.17.8-a781f9ee6c511d8f22140d8990c31e577b2a9676-Clean
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.165342Z info Maximum file descriptors (ulimit -n): 1048576
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.165476Z info Proxy role ips=[10.10.0.14] type=sidecar id=catalog-6cf4b97d-5hwg7.istioinaction domain=istioinaction.svc.cluster.local
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.165524Z info Apply proxy config from env {}
catalog-6cf4b97d-5hwg7 istio-proxy
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.166553Z info Effective config: binaryPath: /usr/local/bin/envoy
catalog-6cf4b97d-5hwg7 istio-proxy concurrency: 2
catalog-6cf4b97d-5hwg7 istio-proxy configPath: ./etc/istio/proxy
catalog-6cf4b97d-5hwg7 istio-proxy controlPlaneAuthPolicy: MUTUAL_TLS
catalog-6cf4b97d-5hwg7 istio-proxy discoveryAddress: istiod.istio-system.svc:15012
catalog-6cf4b97d-5hwg7 istio-proxy drainDuration: 45s
catalog-6cf4b97d-5hwg7 istio-proxy proxyAdminPort: 15000
catalog-6cf4b97d-5hwg7 istio-proxy serviceCluster: istio-proxy
catalog-6cf4b97d-5hwg7 istio-proxy statNameLength: 189
catalog-6cf4b97d-5hwg7 istio-proxy statusPort: 15020
catalog-6cf4b97d-5hwg7 istio-proxy terminationDrainDuration: 5s
catalog-6cf4b97d-5hwg7 istio-proxy tracing:
catalog-6cf4b97d-5hwg7 istio-proxy zipkin:
catalog-6cf4b97d-5hwg7 istio-proxy address: zipkin.istio-system:9411
catalog-6cf4b97d-5hwg7 istio-proxy
catalog-6cf4b97d-5hwg7 istio-init 2025-04-26T08:21:40.997431Z info Istio iptables environment:
catalog-6cf4b97d-5hwg7 istio-init ENVOY_PORT=
catalog-6cf4b97d-5hwg7 istio-init INBOUND_CAPTURE_PORT=
catalog-6cf4b97d-5hwg7 istio-init ISTIO_INBOUND_INTERCEPTION_MODE=
catalog-6cf4b97d-5hwg7 istio-init ISTIO_INBOUND_TPROXY_ROUTE_TABLE=
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.166563Z info JWT policy is third-party-jwt
catalog-6cf4b97d-5hwg7 istio-init ISTIO_INBOUND_PORTS=
catalog-6cf4b97d-5hwg7 istio-init ISTIO_OUTBOUND_PORTS=
catalog-6cf4b97d-5hwg7 istio-init ISTIO_LOCAL_EXCLUDE_PORTS=
catalog-6cf4b97d-5hwg7 istio-init ISTIO_EXCLUDE_INTERFACES=
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.166565Z info using credential fetcher of JWT type in cluster.local trust domain
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.367954Z info Workload SDS socket not found. Starting Istio SDS Server
catalog-6cf4b97d-5hwg7 istio-init ISTIO_SERVICE_CIDR=
catalog-6cf4b97d-5hwg7 istio-init ISTIO_SERVICE_EXCLUDE_CIDR=
catalog-6cf4b97d-5hwg7 istio-init ISTIO_META_DNS_CAPTURE=
catalog-6cf4b97d-5hwg7 istio-init INVALID_DROP=
catalog-6cf4b97d-5hwg7 istio-init
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.367993Z info CA Endpoint istiod.istio-system.svc:15012, provider Citadel
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.368006Z info Using CA istiod.istio-system.svc:15012 cert with certs: var/run/secrets/istio/root-cert.pem
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.367939Z info Opening status port 15020
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.376814Z info ads All caches have been synced up in 215.203667ms, marking server ready
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.377027Z info xdsproxy Initializing with upstream address "istiod.istio-system.svc:15012" and cluster "Kubernetes"
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.377246Z info sds Starting SDS grpc server
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.378197Z info Pilot SAN: [istiod.istio-system.svc]
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.378238Z info starting Http service at 127.0.0.1:15004
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.378816Z info Starting proxy agent
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.378840Z info starting
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.378852Z info Envoy command: [-c etc/istio/proxy/envoy-rev.json --drain-time-s 45 --drain-strategy immediate --local-address-ip-version v4 --file-flush-interval-msec 1000 --disable-hot-restart --allow-unknown-static-fields --log-format %Y-%m-%dT%T.%fZ %l envoy %n %g:%# %v thread=%t -l warning --component-log-level misc:error --concurrency 2]
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.423014Z info xdsproxy connected to upstream XDS server: istiod.istio-system.svc:15012
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.433838Z info ads ADS: new connection for node:catalog-6cf4b97d-5hwg7.istioinaction-1
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.433916Z info ads ADS: new connection for node:catalog-6cf4b97d-5hwg7.istioinaction-2
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.444446Z info cache generated new workload certificate latency=67.201709ms ttl=23h59m59.555560656s
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.444462Z info cache Root cert has changed, start rotating root cert
catalog-6cf4b97d-5hwg7 istio-init 2025-04-26T08:21:40.997477Z info Istio iptables variables:
catalog-6cf4b97d-5hwg7 istio-init PROXY_PORT=15001
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.444469Z info ads XDS: Incremental Pushing:0 ConnectedEndpoints:2 Version:
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.444490Z info cache returned workload trust anchor from cache ttl=23h59m59.555511031s
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.444508Z info cache returned workload trust anchor from cache ttl=23h59m59.555491864s
catalog-6cf4b97d-5hwg7 istio-init PROXY_INBOUND_CAPTURE_PORT=15006
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.444656Z info ads SDS: PUSH request for node:catalog-6cf4b97d-5hwg7.istioinaction resources:1 size:1.1kB resource:ROOTCA
catalog-6cf4b97d-5hwg7 istio-init PROXY_TUNNEL_PORT=15008
catalog-6cf4b97d-5hwg7 istio-init PROXY_UID=1337
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.444682Z info cache returned workload trust anchor from cache ttl=23h59m59.555318822s
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.444700Z info cache returned workload certificate from cache ttl=23h59m59.555300739s
catalog-6cf4b97d-5hwg7 istio-init PROXY_GID=1337
catalog-6cf4b97d-5hwg7 istio-init INBOUND_INTERCEPTION_MODE=REDIRECT
catalog-6cf4b97d-5hwg7 istio-init INBOUND_TPROXY_MARK=1337
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:53.444741Z info ads SDS: PUSH request for node:catalog-6cf4b97d-5hwg7.istioinaction resources:1 size:4.0kB resource:default
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:54.857115Z info Readiness succeeded in 1.699475209s
catalog-6cf4b97d-5hwg7 istio-init INBOUND_TPROXY_ROUTE_TABLE=133
catalog-6cf4b97d-5hwg7 istio-proxy 2025-04-26T08:21:54.857713Z info Envoy proxy is ready
catalog-6cf4b97d-5hwg7 istio-init INBOUND_PORTS_INCLUDE=*
catalog-6cf4b97d-5hwg7 istio-init INBOUND_PORTS_EXCLUDE=15090,15021,15020
catalog-6cf4b97d-5hwg7 istio-init OUTBOUND_OWNER_GROUPS_INCLUDE=*
catalog-6cf4b97d-5hwg7 istio-init OUTBOUND_OWNER_GROUPS_EXCLUDE=
catalog-6cf4b97d-5hwg7 istio-init OUTBOUND_IP_RANGES_INCLUDE=*
catalog-6cf4b97d-5hwg7 istio-init OUTBOUND_IP_RANGES_EXCLUDE=
catalog-6cf4b97d-5hwg7 istio-init OUTBOUND_PORTS_INCLUDE=
catalog-6cf4b97d-5hwg7 istio-init OUTBOUND_PORTS_EXCLUDE=
catalog-6cf4b97d-5hwg7 istio-init KUBE_VIRT_INTERFACES=
catalog-6cf4b97d-5hwg7 istio-init ENABLE_INBOUND_IPV6=false
catalog-6cf4b97d-5hwg7 istio-init DNS_CAPTURE=false
catalog-6cf4b97d-5hwg7 istio-init DROP_INVALID=false
catalog-6cf4b97d-5hwg7 istio-init CAPTURE_ALL_DNS=false
catalog-6cf4b97d-5hwg7 istio-init DNS_SERVERS=[],[]
catalog-6cf4b97d-5hwg7 istio-init NETWORK_NAMESPACE=
catalog-6cf4b97d-5hwg7 istio-init CNI_MODE=false
catalog-6cf4b97d-5hwg7 istio-init HOST_NSENTER_EXEC=false
catalog-6cf4b97d-5hwg7 istio-init EXCLUDE_INTERFACES=
catalog-6cf4b97d-5hwg7 istio-init
catalog-6cf4b97d-5hwg7 istio-init 2025-04-26T08:21:40.997520Z info Running iptables-restore with the following input:
catalog-6cf4b97d-5hwg7 istio-init * nat
catalog-6cf4b97d-5hwg7 istio-init -N ISTIO_INBOUND
catalog-6cf4b97d-5hwg7 istio-init -N ISTIO_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init -N ISTIO_IN_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init -N ISTIO_OUTPUT
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp --dport 15008 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_REDIRECT -p tcp -j REDIRECT --to-ports 15001
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_IN_REDIRECT -p tcp -j REDIRECT --to-ports 15006
catalog-6cf4b97d-5hwg7 istio-init -A PREROUTING -p tcp -j ISTIO_INBOUND
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp --dport 15090 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp --dport 15021 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp --dport 15020 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp -j ISTIO_IN_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init -A OUTPUT -p tcp -j ISTIO_OUTPUT
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -o lo -s 127.0.0.6/32 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -o lo ! -d 127.0.0.1/32 -m owner --uid-owner 1337 -j ISTIO_IN_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -o lo -m owner ! --uid-owner 1337 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -m owner --uid-owner 1337 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -o lo ! -d 127.0.0.1/32 -m owner --gid-owner 1337 -j ISTIO_IN_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -o lo -m owner ! --gid-owner 1337 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -m owner --gid-owner 1337 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -d 127.0.0.1/32 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -j ISTIO_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init COMMIT
catalog-6cf4b97d-5hwg7 istio-init 2025-04-26T08:21:40.997525Z info Running command: iptables-restore --noflush
catalog-6cf4b97d-5hwg7 istio-init 2025-04-26T08:21:41.001598Z info Running ip6tables-restore with the following input:
catalog-6cf4b97d-5hwg7 istio-init
catalog-6cf4b97d-5hwg7 istio-init 2025-04-26T08:21:41.001611Z info Running command: ip6tables-restore --noflush
catalog-6cf4b97d-5hwg7 istio-init 2025-04-26T08:21:41.001979Z info Running command: iptables-save
catalog-6cf4b97d-5hwg7 istio-init 2025-04-26T08:21:41.002598Z info Command output:
catalog-6cf4b97d-5hwg7 istio-init # Generated by iptables-save v1.8.7 on Sat Apr 26 08:21:41 2025
catalog-6cf4b97d-5hwg7 istio-init *nat
catalog-6cf4b97d-5hwg7 istio-init :PREROUTING ACCEPT [0:0]
catalog-6cf4b97d-5hwg7 istio-init :INPUT ACCEPT [0:0]
catalog-6cf4b97d-5hwg7 istio-init :OUTPUT ACCEPT [0:0]
catalog-6cf4b97d-5hwg7 istio-init :POSTROUTING ACCEPT [0:0]
catalog-6cf4b97d-5hwg7 istio-init :ISTIO_INBOUND - [0:0]
catalog-6cf4b97d-5hwg7 istio-init :ISTIO_IN_REDIRECT - [0:0]
catalog-6cf4b97d-5hwg7 istio-init :ISTIO_OUTPUT - [0:0]
catalog-6cf4b97d-5hwg7 istio-init :ISTIO_REDIRECT - [0:0]
catalog-6cf4b97d-5hwg7 istio-init -A PREROUTING -p tcp -j ISTIO_INBOUND
catalog-6cf4b97d-5hwg7 istio-init -A OUTPUT -p tcp -j ISTIO_OUTPUT
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp -m tcp --dport 15008 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp -m tcp --dport 15090 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp -m tcp --dport 15021 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp -m tcp --dport 15020 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_INBOUND -p tcp -j ISTIO_IN_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_IN_REDIRECT -p tcp -j REDIRECT --to-ports 15006
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -s 127.0.0.6/32 -o lo -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT ! -d 127.0.0.1/32 -o lo -m owner --uid-owner 1337 -j ISTIO_IN_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -o lo -m owner ! --uid-owner 1337 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -m owner --uid-owner 1337 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT ! -d 127.0.0.1/32 -o lo -m owner --gid-owner 1337 -j ISTIO_IN_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -o lo -m owner ! --gid-owner 1337 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -m owner --gid-owner 1337 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -d 127.0.0.1/32 -j RETURN
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_OUTPUT -j ISTIO_REDIRECT
catalog-6cf4b97d-5hwg7 istio-init -A ISTIO_REDIRECT -p tcp -j REDIRECT --to-ports 15001
catalog-6cf4b97d-5hwg7 istio-init COMMIT
catalog-6cf4b97d-5hwg7 istio-init # Completed on Sat Apr 26 08:21:41 2025
catalog-6cf4b97d-5hwg7 istio-init
- catalog-6cf4b97d-5hwg7 › istio-init
open http://localhost:30000 ⛔️ 접속 불가
open http://catalog.istioinaction.io:30000
open http://catalog.istioinaction.io:30000/items


# 신규 터미널 : 반복 접속 실행 해두기
while true; do curl -s http://catalog.istioinaction.io:30000/items/ ; sleep 1; echo; done
while true; do curl -s http://catalog.istioinaction.io:30000/items/ -I | head -n 1 ; date "+%Y-%m-%d %H:%M:%S" ; sleep 1; echo; done
while true; do curl -s http://catalog.istioinaction.io:30000/items/ -I | head -n 1 ; date "+%Y-%m-%d %H:%M:%S" ; sleep 0.5; echo; done



#
docker exec -it myk8s-control-plane istioctl proxy-status
NAME CLUSTER CDS LDS EDS RDS ECDS ISTIOD VERSION
catalog-6cf4b97d-5hwg7.istioinaction Kubernetes SYNCED SYNCED SYNCED SYNCED NOT SENT istiod-7df6ffc78d-fhwmc 1.17.8
istio-ingressgateway-996bc6bb6-n6trq.istio-system Kubernetes SYNCED SYNCED SYNCED SYNCED NOT SENT istiod-7df6ffc78d-fhwmc 1.17.8
# istio-ingressgateway
## LDS - Listener Discovery Service
docker exec -it myk8s-control-plane istioctl proxy-config listener deploy/istio-ingressgateway.istio-system
ADDRESS PORT MATCH DESTINATION
0.0.0.0 8080 ALL Route: http.8080
0.0.0.0 15021 ALL Inline Route: /healthz/ready*
0.0.0.0 15090 ALL Inline Route: /stats/prometheus*
docker exec -it myk8s-control-plane istioctl proxy-config listener deploy/istio-ingressgateway.istio-system --port 8080
ADDRESS PORT MATCH DESTINATION
0.0.0.0 8080 ALL Route: http.8080
docker exec -it myk8s-control-plane istioctl proxy-config listener deploy/istio-ingressgateway.istio-system --port 8080 -o json
[
{
"name": "0.0.0.0_8080",
"address": {
"socketAddress": {
"address": "0.0.0.0",
"portValue": 8080
}
},
"filterChains": [
{
"filters": [
{
"name": "istio_authn",
"typedConfig": {
"@type": "type.googleapis.com/udpa.type.v1.TypedStruct",
"typeUrl": "type.googleapis.com/io.istio.network.authn.Config"
}
},
{
"name": "envoy.filters.network.http_connection_manager",
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.filters.network.http_connection_manager.v3.HttpConnectionManager",
"statPrefix": "outbound_0.0.0.0_8080",
"rds": {
"configSource": {
"ads": {},
"initialFetchTimeout": "0s",
"resourceApiVersion": "V3"
},
"routeConfigName": "http.8080"
},
"httpFilters": [
{
"name": "istio.metadata_exchange",
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.filters.http.wasm.v3.Wasm",
"config": {
"vmConfig": {
"runtime": "envoy.wasm.runtime.null",
"code": {
"local": {
"inlineString": "envoy.wasm.metadata_exchange"
}
}
},
"configuration": {
"@type": "type.googleapis.com/envoy.tcp.metadataexchange.config.MetadataExchange"
}
}
}
},
{
"name": "envoy.filters.http.grpc_stats",
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.filters.http.grpc_stats.v3.FilterConfig",
"emitFilterState": true,
"statsForAllMethods": false
}
},
{
"name": "istio.alpn",
"typedConfig": {
"@type": "type.googleapis.com/istio.envoy.config.filter.http.alpn.v2alpha1.FilterConfig",
"alpnOverride": [
{
"alpnOverride": [
"istio-http/1.0",
"istio",
"http/1.0"
]
},
{
"upstreamProtocol": "HTTP11",
"alpnOverride": [
"istio-http/1.1",
"istio",
"http/1.1"
]
},
{
"upstreamProtocol": "HTTP2",
"alpnOverride": [
"istio-h2",
"istio",
"h2"
]
}
]
}
},
{
"name": "envoy.filters.http.fault",
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.filters.http.fault.v3.HTTPFault"
}
},
{
"name": "envoy.filters.http.cors",
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.filters.http.cors.v3.Cors"
}
},
{
"name": "istio.stats",
"typedConfig": {
"@type": "type.googleapis.com/udpa.type.v1.TypedStruct",
"typeUrl": "type.googleapis.com/stats.PluginConfig",
"value": {
"disable_host_header_fallback": true
}
}
},
{
"name": "envoy.filters.http.router",
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.filters.http.router.v3.Router"
}
}
],
"tracing": {
"clientSampling": {
"value": 100
},
"randomSampling": {
"value": 1
},
"overallSampling": {
"value": 100
},
"customTags": [
{
"tag": "istio.authorization.dry_run.allow_policy.name",
"metadata": {
"kind": {
"request": {}
},
"metadataKey": {
"key": "envoy.filters.http.rbac",
"path": [
{
"key": "istio_dry_run_allow_shadow_effective_policy_id"
}
]
}
}
},
{
"tag": "istio.authorization.dry_run.allow_policy.result",
"metadata": {
"kind": {
"request": {}
},
"metadataKey": {
"key": "envoy.filters.http.rbac",
"path": [
{
"key": "istio_dry_run_allow_shadow_engine_result"
}
]
}
}
},
{
"tag": "istio.authorization.dry_run.deny_policy.name",
"metadata": {
"kind": {
"request": {}
},
"metadataKey": {
"key": "envoy.filters.http.rbac",
"path": [
{
"key": "istio_dry_run_deny_shadow_effective_policy_id"
}
]
}
}
},
{
"tag": "istio.authorization.dry_run.deny_policy.result",
"metadata": {
"kind": {
"request": {}
},
"metadataKey": {
"key": "envoy.filters.http.rbac",
"path": [
{
"key": "istio_dry_run_deny_shadow_engine_result"
}
]
}
}
},
{
"tag": "istio.canonical_revision",
"literal": {
"value": "latest"
}
},
{
"tag": "istio.canonical_service",
"literal": {
"value": "istio-ingressgateway"
}
},
{
"tag": "istio.mesh_id",
"literal": {
"value": "cluster.local"
}
},
{
"tag": "istio.namespace",
"literal": {
"value": "istio-system"
}
}
]
},
"httpProtocolOptions": {},
"serverName": "istio-envoy",
"streamIdleTimeout": "0s",
"useRemoteAddress": true,
"forwardClientCertDetails": "SANITIZE_SET",
"setCurrentClientCertDetails": {
"subject": true,
"cert": true,
"dns": true,
"uri": true
},
"upgradeConfigs": [
{
"upgradeType": "websocket"
}
],
"normalizePath": true,
"pathWithEscapedSlashesAction": "KEEP_UNCHANGED",
"requestIdExtension": {
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.request_id.uuid.v3.UuidRequestIdConfig",
"useRequestIdForTraceSampling": true
}
}
}
}
]
}
],
"trafficDirection": "OUTBOUND"
}
]
## RDS - Route Discovery Service
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/istio-ingressgateway.istio-system
NAME DOMAINS MATCH VIRTUAL SERVICE
http.8080 catalog.istioinaction.io /* catalog-vs-from-gw.istioinaction
* /healthz/ready*
* /stats/prometheus*
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/istio-ingressgateway.istio-system --name http.8080
NAME DOMAINS MATCH VIRTUAL SERVICE
http.8080 catalog.istioinaction.io /* catalog-vs-from-gw.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/istio-ingressgateway.istio-system --name http.8080 -o json
[
{
"name": "http.8080",
"virtualHosts": [
{
"name": "catalog.istioinaction.io:80",
"domains": [
"catalog.istioinaction.io"
],
"routes": [
{
"match": {
"prefix": "/"
},
"route": {
"cluster": "outbound|80||catalog.istioinaction.svc.cluster.local",
"timeout": "0s",
"retryPolicy": {
"retryOn": "connect-failure,refused-stream,unavailable,cancelled,retriable-status-codes",
"numRetries": 2,
"retryHostPredicate": [
{
"name": "envoy.retry_host_predicates.previous_hosts",
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.retry.host.previous_hosts.v3.PreviousHostsPredicate"
}
}
],
"hostSelectionRetryMaxAttempts": "5",
"retriableStatusCodes": [
503
]
},
"maxGrpcTimeout": "0s"
},
"metadata": {
"filterMetadata": {
"istio": {
"config": "/apis/networking.istio.io/v1alpha3/namespaces/istioinaction/virtual-service/catalog-vs-from-gw"
}
}
},
"decorator": {
"operation": "catalog.istioinaction.svc.cluster.local:80/*"
}
}
],
"includeRequestAttemptCount": true
}
],
"validateClusters": false,
"ignorePortInHostMatching": true
}
]
## CDS - Cluseter Discovery Service
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
BlackHoleCluster - - - STATIC
agent - - - STATIC
catalog.istioinaction.svc.cluster.local 80 - outbound EDS
grafana.istio-system.svc.cluster.local 3000 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 80 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 443 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 15021 - outbound EDS
istiod.istio-system.svc.cluster.local 443 - outbound EDS
istiod.istio-system.svc.cluster.local 15010 - outbound EDS
istiod.istio-system.svc.cluster.local 15012 - outbound EDS
istiod.istio-system.svc.cluster.local 15014 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 9411 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 14250 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 14268 - outbound EDS
kiali.istio-system.svc.cluster.local 9090 - outbound EDS
kiali.istio-system.svc.cluster.local 20001 - outbound EDS
kube-dns.kube-system.svc.cluster.local 53 - outbound EDS
kube-dns.kube-system.svc.cluster.local 9153 - outbound EDS
kube-ops-view.kube-system.svc.cluster.local 8080 - outbound EDS
kubernetes.default.svc.cluster.local 443 - outbound EDS
metrics-server.kube-system.svc.cluster.local 443 - outbound EDS
prometheus.istio-system.svc.cluster.local 9090 - outbound EDS
prometheus_stats - - - STATIC
sds-grpc - - - STATIC
tracing.istio-system.svc.cluster.local 80 - outbound EDS
tracing.istio-system.svc.cluster.local 16685 - outbound EDS
xds-grpc - - - STATIC
zipkin - - - STRICT_DNS
zipkin.istio-system.svc.cluster.local 9411 - outbound EDS
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn catalog.istioinaction.svc.cluster.local
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
catalog.istioinaction.svc.cluster.local 80 - outbound EDS
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn catalog.istioinaction.svc.cluster.local -o json
[
{
"transportSocketMatches": [
{
"name": "tlsMode-istio",
"match": {
"tlsMode": "istio"
},
"transportSocket": {
"name": "envoy.transport_sockets.tls",
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.transport_sockets.tls.v3.UpstreamTlsContext",
"commonTlsContext": {
"tlsParams": {
"tlsMinimumProtocolVersion": "TLSv1_2",
"tlsMaximumProtocolVersion": "TLSv1_3"
},
"tlsCertificateSdsSecretConfigs": [
{
"name": "default",
"sdsConfig": {
"apiConfigSource": {
"apiType": "GRPC",
"transportApiVersion": "V3",
"grpcServices": [
{
"envoyGrpc": {
"clusterName": "sds-grpc"
}
}
],
"setNodeOnFirstMessageOnly": true
},
"initialFetchTimeout": "0s",
"resourceApiVersion": "V3"
}
}
],
"combinedValidationContext": {
"defaultValidationContext": {
"matchSubjectAltNames": [
{
"exact": "spiffe://cluster.local/ns/istioinaction/sa/catalog"
}
]
},
"validationContextSdsSecretConfig": {
"name": "ROOTCA",
"sdsConfig": {
"apiConfigSource": {
"apiType": "GRPC",
"transportApiVersion": "V3",
"grpcServices": [
{
"envoyGrpc": {
"clusterName": "sds-grpc"
}
}
],
"setNodeOnFirstMessageOnly": true
},
"initialFetchTimeout": "0s",
"resourceApiVersion": "V3"
}
}
},
"alpnProtocols": [
"istio-peer-exchange",
"istio"
]
},
"sni": "outbound_.80_._.catalog.istioinaction.svc.cluster.local"
}
}
},
{
"name": "tlsMode-disabled",
"match": {},
"transportSocket": {
"name": "envoy.transport_sockets.raw_buffer",
"typedConfig": {
"@type": "type.googleapis.com/envoy.extensions.transport_sockets.raw_buffer.v3.RawBuffer"
}
}
}
],
"name": "outbound|80||catalog.istioinaction.svc.cluster.local",
"type": "EDS",
"edsClusterConfig": {
"edsConfig": {
"ads": {},
"initialFetchTimeout": "0s",
"resourceApiVersion": "V3"
},
"serviceName": "outbound|80||catalog.istioinaction.svc.cluster.local"
},
"connectTimeout": "10s",
"lbPolicy": "LEAST_REQUEST",
"circuitBreakers": {
"thresholds": [
{
"maxConnections": 4294967295,
"maxPendingRequests": 4294967295,
"maxRequests": 4294967295,
"maxRetries": 4294967295,
"trackRemaining": true
}
]
},
"commonLbConfig": {
"localityWeightedLbConfig": {}
},
"metadata": {
"filterMetadata": {
"istio": {
"default_original_port": 80,
"services": [
{
"host": "catalog.istioinaction.svc.cluster.local",
"name": "catalog",
"namespace": "istioinaction"
}
]
}
}
},
"filters": [
{
"name": "istio.metadata_exchange",
"typedConfig": {
"@type": "type.googleapis.com/envoy.tcp.metadataexchange.config.MetadataExchange",
"protocol": "istio-peer-exchange"
}
}
]
}
]
## EDS - Endpoint Discovery Service
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.10:53 HEALTHY OK outbound|53||kube-dns.kube-system.svc.cluster.local
10.10.0.10:9153 HEALTHY OK outbound|9153||kube-dns.kube-system.svc.cluster.local
10.10.0.11:8080 HEALTHY OK outbound|8080||kube-ops-view.kube-system.svc.cluster.local
10.10.0.12:9090 HEALTHY OK outbound|9090||prometheus.istio-system.svc.cluster.local
10.10.0.13:8080 HEALTHY OK outbound|80||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.13:8443 HEALTHY OK outbound|443||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.13:15021 HEALTHY OK outbound|15021||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.2:53 HEALTHY OK outbound|53||kube-dns.kube-system.svc.cluster.local
10.10.0.2:9153 HEALTHY OK outbound|9153||kube-dns.kube-system.svc.cluster.local
10.10.0.3:3000 HEALTHY OK outbound|3000||grafana.istio-system.svc.cluster.local
10.10.0.4:9411 HEALTHY OK outbound|9411||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:9411 HEALTHY OK outbound|9411||zipkin.istio-system.svc.cluster.local
10.10.0.4:14250 HEALTHY OK outbound|14250||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:14268 HEALTHY OK outbound|14268||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:16685 HEALTHY OK outbound|16685||tracing.istio-system.svc.cluster.local
10.10.0.4:16686 HEALTHY OK outbound|80||tracing.istio-system.svc.cluster.local
10.10.0.6:10250 HEALTHY OK outbound|443||metrics-server.kube-system.svc.cluster.local
10.10.0.8:15010 HEALTHY OK outbound|15010||istiod.istio-system.svc.cluster.local
10.10.0.8:15012 HEALTHY OK outbound|15012||istiod.istio-system.svc.cluster.local
10.10.0.8:15014 HEALTHY OK outbound|15014||istiod.istio-system.svc.cluster.local
10.10.0.8:15017 HEALTHY OK outbound|443||istiod.istio-system.svc.cluster.local
10.10.0.9:9090 HEALTHY OK outbound|9090||kiali.istio-system.svc.cluster.local
10.10.0.9:20001 HEALTHY OK outbound|20001||kiali.istio-system.svc.cluster.local
10.200.1.6:9411 HEALTHY OK zipkin
127.0.0.1:15000 HEALTHY OK prometheus_stats
127.0.0.1:15020 HEALTHY OK agent
172.19.0.2:6443 HEALTHY OK outbound|443||kubernetes.default.svc.cluster.local
unix://./etc/istio/proxy/XDS HEALTHY OK xds-grpc
unix://./var/run/secrets/workload-spiffe-uds/socket HEALTHY OK sds-grpc
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80||catalog.istioinaction.svc.cluster.local'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80||catalog.istioinaction.svc.cluster.local' -o json
[
{
"name": "outbound|80||catalog.istioinaction.svc.cluster.local",
"addedViaApi": true,
"hostStatuses": [
{
"address": {
"socketAddress": {
"address": "10.10.0.14",
"portValue": 3000
}
},
"stats": [
{
"name": "cx_connect_fail"
},
{
"value": "13",
"name": "cx_total"
},
{
"name": "rq_error"
},
{
"value": "9737",
"name": "rq_success"
},
{
"name": "rq_timeout"
},
{
"value": "9737",
"name": "rq_total"
},
{
"type": "GAUGE",
"value": "13",
"name": "cx_active"
},
{
"type": "GAUGE",
"name": "rq_active"
}
],
"healthStatus": {
"edsHealthStatus": "HEALTHY"
},
"weight": 1,
"locality": {}
}
],
"circuitBreakers": {
"thresholds": [
{
"maxConnections": 4294967295,
"maxPendingRequests": 4294967295,
"maxRequests": 4294967295,
"maxRetries": 4294967295
},
{
"priority": "HIGH",
"maxConnections": 1024,
"maxPendingRequests": 1024,
"maxRequests": 1024,
"maxRetries": 3
}
]
},
"observabilityName": "outbound|80||catalog.istioinaction.svc.cluster.local",
"edsServiceName": "outbound|80||catalog.istioinaction.svc.cluster.local"
}
]
# catalog
docker exec -it myk8s-control-plane istioctl proxy-config listener deploy/catalog.istioinaction
ADDRESS PORT MATCH DESTINATION
10.200.1.10 53 ALL Cluster: outbound|53||kube-dns.kube-system.svc.cluster.local
0.0.0.0 80 Trans: raw_buffer; App: http/1.1,h2c Route: 80
0.0.0.0 80 ALL PassthroughCluster
10.200.1.1 443 ALL Cluster: outbound|443||kubernetes.default.svc.cluster.local
10.200.1.17 443 ALL Cluster: outbound|443||metrics-server.kube-system.svc.cluster.local
10.200.1.172 443 ALL Cluster: outbound|443||istio-ingressgateway.istio-system.svc.cluster.local
10.200.1.182 443 ALL Cluster: outbound|443||istiod.istio-system.svc.cluster.local
10.200.1.190 3000 Trans: raw_buffer; App: http/1.1,h2c Route: grafana.istio-system.svc.cluster.local:3000
10.200.1.190 3000 ALL Cluster: outbound|3000||grafana.istio-system.svc.cluster.local
0.0.0.0 8080 Trans: raw_buffer; App: http/1.1,h2c Route: 8080
0.0.0.0 8080 ALL PassthroughCluster
0.0.0.0 9090 Trans: raw_buffer; App: http/1.1,h2c Route: 9090
0.0.0.0 9090 ALL PassthroughCluster
10.200.1.10 9153 Trans: raw_buffer; App: http/1.1,h2c Route: kube-dns.kube-system.svc.cluster.local:9153
10.200.1.10 9153 ALL Cluster: outbound|9153||kube-dns.kube-system.svc.cluster.local
0.0.0.0 9411 Trans: raw_buffer; App: http/1.1,h2c Route: 9411
0.0.0.0 9411 ALL PassthroughCluster
10.200.1.53 14250 Trans: raw_buffer; App: http/1.1,h2c Route: jaeger-collector.istio-system.svc.cluster.local:14250
10.200.1.53 14250 ALL Cluster: outbound|14250||jaeger-collector.istio-system.svc.cluster.local
10.200.1.53 14268 Trans: raw_buffer; App: http/1.1,h2c Route: jaeger-collector.istio-system.svc.cluster.local:14268
10.200.1.53 14268 ALL Cluster: outbound|14268||jaeger-collector.istio-system.svc.cluster.local
0.0.0.0 15001 ALL PassthroughCluster
0.0.0.0 15001 Addr: *:15001 Non-HTTP/Non-TCP
0.0.0.0 15006 Addr: *:15006 Non-HTTP/Non-TCP
0.0.0.0 15006 Trans: tls; App: istio-http/1.0,istio-http/1.1,istio-h2; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: raw_buffer; App: http/1.1,h2c; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: tls; App: TCP TLS; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: raw_buffer; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: tls; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: tls; App: istio,istio-peer-exchange,istio-http/1.0,istio-http/1.1,istio-h2; Addr: *:3000 Cluster: inbound|3000||
0.0.0.0 15006 Trans: raw_buffer; Addr: *:3000 Cluster: inbound|3000||
0.0.0.0 15010 Trans: raw_buffer; App: http/1.1,h2c Route: 15010
0.0.0.0 15010 ALL PassthroughCluster
10.200.1.182 15012 ALL Cluster: outbound|15012||istiod.istio-system.svc.cluster.local
0.0.0.0 15014 Trans: raw_buffer; App: http/1.1,h2c Route: 15014
0.0.0.0 15014 ALL PassthroughCluster
0.0.0.0 15021 ALL Inline Route: /healthz/ready*
10.200.1.172 15021 Trans: raw_buffer; App: http/1.1,h2c Route: istio-ingressgateway.istio-system.svc.cluster.local:15021
10.200.1.172 15021 ALL Cluster: outbound|15021||istio-ingressgateway.istio-system.svc.cluster.local
0.0.0.0 15090 ALL Inline Route: /stats/prometheus*
0.0.0.0 16685 Trans: raw_buffer; App: http/1.1,h2c Route: 16685
0.0.0.0 16685 ALL PassthroughCluster
0.0.0.0 20001 Trans: raw_buffer; App: http/1.1,h2c Route: 20001
0.0.0.0 20001 ALL PassthroughCluster
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/catalog.istioinaction
routes deploy/catalog.istioinaction
NAME DOMAINS MATCH VIRTUAL SERVICE
80 catalog, catalog.istioinaction + 1 more... /*
80 istio-ingressgateway.istio-system, 10.200.1.172 /*
80 tracing.istio-system, 10.200.1.164 /*
8080 kube-ops-view.kube-system, 10.200.1.144 /*
9090 kiali.istio-system, 10.200.1.26 /*
9090 prometheus.istio-system, 10.200.1.104 /*
9411 jaeger-collector.istio-system, 10.200.1.53 /*
9411 zipkin.istio-system, 10.200.1.6 /*
15010 istiod.istio-system, 10.200.1.182 /*
15014 istiod.istio-system, 10.200.1.182 /*
istio-ingressgateway.istio-system.svc.cluster.local:15021 * /*
jaeger-collector.istio-system.svc.cluster.local:14268 * /*
20001 kiali.istio-system, 10.200.1.26 /*
16685 tracing.istio-system, 10.200.1.164 /*
jaeger-collector.istio-system.svc.cluster.local:14250 * /*
kube-dns.kube-system.svc.cluster.local:9153 * /*
grafana.istio-system.svc.cluster.local:3000 * /*
InboundPassthroughClusterIpv4 * /*
* /stats/prometheus*
InboundPassthroughClusterIpv4 * /*
* /healthz/ready*
inbound|3000|| * /*
inbound|3000|| * /*
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/catalog.istioinaction
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
3000 - inbound ORIGINAL_DST
BlackHoleCluster - - - STATIC
InboundPassthroughClusterIpv4 - - - ORIGINAL_DST
PassthroughCluster - - - ORIGINAL_DST
agent - - - STATIC
catalog.istioinaction.svc.cluster.local 80 - outbound EDS
grafana.istio-system.svc.cluster.local 3000 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 80 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 443 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 15021 - outbound EDS
istiod.istio-system.svc.cluster.local 443 - outbound EDS
istiod.istio-system.svc.cluster.local 15010 - outbound EDS
istiod.istio-system.svc.cluster.local 15012 - outbound EDS
istiod.istio-system.svc.cluster.local 15014 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 9411 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 14250 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 14268 - outbound EDS
kiali.istio-system.svc.cluster.local 9090 - outbound EDS
kiali.istio-system.svc.cluster.local 20001 - outbound EDS
kube-dns.kube-system.svc.cluster.local 53 - outbound EDS
kube-dns.kube-system.svc.cluster.local 9153 - outbound EDS
kube-ops-view.kube-system.svc.cluster.local 8080 - outbound EDS
kubernetes.default.svc.cluster.local 443 - outbound EDS
metrics-server.kube-system.svc.cluster.local 443 - outbound EDS
prometheus.istio-system.svc.cluster.local 9090 - outbound EDS
prometheus_stats - - - STATIC
sds-grpc - - - STATIC
tracing.istio-system.svc.cluster.local 80 - outbound EDS
tracing.istio-system.svc.cluster.local 16685 - outbound EDS
xds-grpc - - - STATIC
zipkin - - - STRICT_DNS
zipkin.istio-system.svc.cluster.local 9411 - outbound EDS
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/catalog.istioinaction
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.10:53 HEALTHY OK outbound|53||kube-dns.kube-system.svc.cluster.local
10.10.0.10:9153 HEALTHY OK outbound|9153||kube-dns.kube-system.svc.cluster.local
10.10.0.11:8080 HEALTHY OK outbound|8080||kube-ops-view.kube-system.svc.cluster.local
10.10.0.12:9090 HEALTHY OK outbound|9090||prometheus.istio-system.svc.cluster.local
10.10.0.13:8080 HEALTHY OK outbound|80||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.13:8443 HEALTHY OK outbound|443||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.13:15021 HEALTHY OK outbound|15021||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.14:3000 HEALTHY OK inbound|3000||
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.2:53 HEALTHY OK outbound|53||kube-dns.kube-system.svc.cluster.local
10.10.0.2:9153 HEALTHY OK outbound|9153||kube-dns.kube-system.svc.cluster.local
10.10.0.3:3000 HEALTHY OK outbound|3000||grafana.istio-system.svc.cluster.local
10.10.0.4:9411 HEALTHY OK outbound|9411||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:9411 HEALTHY OK outbound|9411||zipkin.istio-system.svc.cluster.local
10.10.0.4:14250 HEALTHY OK outbound|14250||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:14268 HEALTHY OK outbound|14268||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:16685 HEALTHY OK outbound|16685||tracing.istio-system.svc.cluster.local
10.10.0.4:16686 HEALTHY OK outbound|80||tracing.istio-system.svc.cluster.local
10.10.0.6:10250 HEALTHY OK outbound|443||metrics-server.kube-system.svc.cluster.local
10.10.0.8:15010 HEALTHY OK outbound|15010||istiod.istio-system.svc.cluster.local
10.10.0.8:15012 HEALTHY OK outbound|15012||istiod.istio-system.svc.cluster.local
10.10.0.8:15014 HEALTHY OK outbound|15014||istiod.istio-system.svc.cluster.local
10.10.0.8:15017 HEALTHY OK outbound|443||istiod.istio-system.svc.cluster.local
10.10.0.9:9090 HEALTHY OK outbound|9090||kiali.istio-system.svc.cluster.local
10.10.0.9:20001 HEALTHY OK outbound|20001||kiali.istio-system.svc.cluster.local
10.200.1.6:9411 HEALTHY OK zipkin
127.0.0.1:15000 HEALTHY OK prometheus_stats
127.0.0.1:15020 HEALTHY OK agent
172.19.0.2:6443 HEALTHY OK outbound|443||kubernetes.default.svc.cluster.local
unix://./etc/istio/proxy/XDS HEALTHY OK xds-grpc
unix://./var/run/secrets/workload-spiffe-uds/socket HEALTHY OK sds-grpc
# 신규 터미널 : istio-ingressgateway 파드
kubectl port-forward deploy/istio-ingressgateway -n istio-system 15000:15000
#
open http://127.0.0.1:15000

# catalog 서비스 v2 를 배포 : v2에서는 imageUrl 필드가 추가
kubectl apply -f services/catalog/kubernetes/catalog-deployment-v2.yaml -n istioinaction
deployment.apps/catalog-v2 created
#
kubectl get deploy -n istioinaction --show-labels
catalog 1/1 1 1 135m app=catalog,version=v1
catalog-v2 1/1 1 1 20s app=catalog,version=v2
kubectl get pod -n istioinaction -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
catalog-6cf4b97d-5hwg7 2/2 Running 0 135m 10.10.0.14 myk8s-control-plane <none> <none>
catalog-v2-6df885b555-q7xnv 2/2 Running 0 40s 10.10.0.15 myk8s-control-plane <none> <none>
docker exec -it myk8s-control-plane istioctl proxy-status
NAME CLUSTER CDS LDS EDS RDS ECDS ISTIOD VERSION
catalog-6cf4b97d-5hwg7.istioinaction Kubernetes SYNCED SYNCED SYNCED SYNCED NOT SENT istiod-7df6ffc78d-fhwmc 1.17.8
catalog-v2-6df885b555-q7xnv.istioinaction Kubernetes SYNCED SYNCED SYNCED SYNCED NOT SENT istiod-7df6ffc78d-fhwmc 1.17.8
istio-ingressgateway-996bc6bb6-n6trq.istio-system Kubernetes SYNCED SYNCED SYNCED SYNCED NOT SENT istiod-7df6ffc78d-fhwmc 1.17.8
# 호출 테스트 : v1 , v2 호출 확인
for i in {1..10}; do curl -s http://catalog.istioinaction.io:30000/items/ ; printf "\n\n"; done
# istio-ingressgateway proxy-config 확인
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn catalog.istioinaction.svc.cluster.local
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
catalog.istioinaction.svc.cluster.local 80 - outbound EDS
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn catalog.istioinaction.svc.cluster.local -o json
...
"name": "outbound|80||catalog.istioinaction.svc.cluster.local",
"type": "EDS",
"edsClusterConfig": {
"edsConfig": {
"ads": {},
"initialFetchTimeout": "0s",
"resourceApiVersion": "V3"
},
"serviceName": "outbound|80||catalog.istioinaction.svc.cluster.local"
},
"connectTimeout": "10s",
"lbPolicy": "LEAST_REQUEST",
"circuitBreakers": {
"thresholds": [
{
"maxConnections": 4294967295,
"maxPendingRequests": 4294967295,
"maxRequests": 4294967295,
"maxRetries": 4294967295,
"trackRemaining": true
}
]
},
"commonLbConfig": {
"localityWeightedLbConfig": {}
},
...
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80||catalog.istioinaction.svc.cluster.local'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.16:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.17:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80||catalog.istioinaction.svc.cluster.local' -o json
...
{
"name": "outbound|80||catalog.istioinaction.svc.cluster.local",
"addedViaApi": true,
"hostStatuses": [
{
"address": {
"socketAddress": {
"address": "10.10.0.14",
"portValue": 3000
}
},
"stats": [
{
"name": "cx_connect_fail"
},
{
"value": "8",
"name": "cx_total"
},
{
"name": "rq_error"
},
{
"value": "315",
"name": "rq_success"
},
{
"name": "rq_timeout"
},
{
"value": "315",
"name": "rq_total"
},
{
"type": "GAUGE",
"value": "8",
"name": "cx_active"
},
{
"type": "GAUGE",
"name": "rq_active"
}
],
"healthStatus": {
"edsHealthStatus": "HEALTHY"
},
"weight": 1,
"locality": {}
},
{
"address": {
"socketAddress": {
"address": "10.10.0.15",
"portValue": 3000
}
},
"stats": [
{
"name": "cx_connect_fail"
},
{
"value": "8",
"name": "cx_total"
},
{
"name": "rq_error"
},
{
"value": "308",
"name": "rq_success"
},
{
"name": "rq_timeout"
},
{
"value": "308",
"name": "rq_total"
},
{
"type": "GAUGE",
"value": "8",
"name": "cx_active"
},
{
"type": "GAUGE",
"name": "rq_active"
}
],
"healthStatus": {
"edsHealthStatus": "HEALTHY"
},
"weight": 1,
"locality": {}
}
],
"circuitBreakers": {
"thresholds": [
{
"maxConnections": 4294967295,
"maxPendingRequests": 4294967295,
"maxRequests": 4294967295,
"maxRetries": 4294967295
},
{
"priority": "HIGH",
"maxConnections": 1024,
"maxPendingRequests": 1024,
"maxRequests": 1024,
"maxRetries": 3
}
]
},
"observabilityName": "outbound|80||catalog.istioinaction.svc.cluster.local",
"edsServiceName": "outbound|80||catalog.istioinaction.svc.cluster.local"
},
...

app:catalog, version:v1 을 사용한다.app:catalog, version:v2 을 사용한다.DestinationRule 을 만들어준다.
#
kubectl get pod -l app=catalog -n istioinaction --show-labels
NAME READY STATUS RESTARTS AGE LABELS
catalog-6cf4b97d-5hwg7 2/2 Running 0 147m app=catalog,pod-template-hash=6cf4b97d,security.istio.io/tlsMode=istio,service.istio.io/canonical-name=catalog,service.istio.io/canonical-revision=v1,version=v1
catalog-v2-6df885b555-q7xnv 2/2 Running 0 13m app=catalog,pod-template-hash=6df885b555,security.istio.io/tlsMode=istio,service.istio.io/canonical-name=catalog,service.istio.io/canonical-revision=v2,version=v2
#
cat ch5/catalog-dest-rule.yaml
apiVersion: networking.istio.io/v1alpha3
kind: DestinationRule
metadata:
name: catalog
spec:
host: catalog.istioinaction.svc.cluster.local
subsets:
- name: version-v1
labels:
version: v1
- name: version-v2
labels:
version: v2
kubectl apply -f ch5/catalog-dest-rule.yaml -n istioinaction
destinationrule.networking.istio.io/catalog created
# 확인
kubectl get destinationrule -n istioinaction
NAME HOST AGE
catalog catalog.istioinaction.svc.cluster.local 20s
# catalog proxy-config 확인 : SUBSET(v1, v2, -) 확인
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn catalog.istioinaction.svc.cluster.local
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
catalog.istioinaction.svc.cluster.local 80 - outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v1 outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v2 outbound EDS catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --subset version-v1 -o json
...
"name": "outbound|80|version-v1|catalog.istioinaction.svc.cluster.local",
"type": "EDS",
"edsClusterConfig": {
"edsConfig": {
"ads": {},
"initialFetchTimeout": "0s",
"resourceApiVersion": "V3"
},
"serviceName": "outbound|80|version-v1|catalog.istioinaction.svc.cluster.local"
},
"connectTimeout": "10s",
"lbPolicy": "LEAST_REQUEST",
...
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --subset version-v2 -o json
...
"name": "outbound|80|version-v2|catalog.istioinaction.svc.cluster.local",
"type": "EDS",
"edsClusterConfig": {
"edsConfig": {
"ads": {},
"initialFetchTimeout": "0s",
"resourceApiVersion": "V3"
},
"serviceName": "outbound|80|version-v2|catalog.istioinaction.svc.cluster.local"
},
"connectTimeout": "10s",
"lbPolicy": "LEAST_REQUEST",
...
#
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn catalog.istioinaction.svc.cluster.local -o json
...
"name": "outbound|80||catalog.istioinaction.svc.cluster.local",
"type": "EDS",
"edsClusterConfig": {
"edsConfig": {
"ads": {},
"initialFetchTimeout": "0s",
"resourceApiVersion": "V3"
},
"serviceName": "outbound|80||catalog.istioinaction.svc.cluster.local"
},
...
#
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system | egrep 'ENDPOINT|istioinaction'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.14:3000 HEALTHY OK outbound|80|version-v1|catalog.istioinaction.svc.cluster.local
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80|version-v2|catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80|version-v1|catalog.istioinaction.svc.cluster.local'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.14:3000 HEALTHY OK outbound|80|version-v1|catalog.istioinaction.svc.cluster.local
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80|version-v1|catalog.istioinaction.svc.cluster.local' -o json
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80|version-v2|catalog.istioinaction.svc.cluster.local'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.15:3000 HEALTHY OK outbound|80|version-v2|catalog.istioinaction.svc.cluster.local
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80|version-v2|catalog.istioinaction.svc.cluster.local' -o json
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80||catalog.istioinaction.svc.cluster.local'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
# VirtualService 수정 (subset 추가)
cat ch5/catalog-vs-v1.yaml
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: catalog-vs-from-gw
spec:
hosts:
- "catalog.istioinaction.io"
gateways:
- catalog-gateway
http:
- route:
- destination:
host: catalog
subset: version-v1
kubectl apply -f ch5/catalog-vs-v1.yaml -n istioinaction
virtualservice.networking.istio.io/catalog-vs-from-gw configured
# 호출 테스트 : v1
for i in {1..10}; do curl -s http://catalog.istioinaction.io:30000/items/ ; printf "\n\n"; done
# 세부 정보 확인
# routes 에 virtualHosts 항목에 routes.route 에 cluster 부분이 ...version-v1... 설정 확인
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/istio-ingressgateway.istio-system
NAME DOMAINS MATCH VIRTUAL SERVICE
http.8080 catalog.istioinaction.io /* catalog-vs-from-gw.istioinaction
* /healthz/ready*
* /stats/prometheus*
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/istio-ingressgateway.istio-system --name http.8080 -o json
...
"virtualHosts": [
{
"name": "catalog.istioinaction.io:80",
"domains": [
"catalog.istioinaction.io"
],
"routes": [
{
"match": {
"prefix": "/"
},
"route": {
"cluster": "outbound|80|version-v1|catalog.istioinaction.svc.cluster.local",
"timeout": "0s",
"retryPolicy": {
"retryOn": "connect-failure,refused-stream,unavailable,cancelled,retriable-status-codes",
"numRetries": 2,
...
# cluster
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn catalog.istioinaction.svc.cluster.local
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
catalog.istioinaction.svc.cluster.local 80 - outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v1 outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v2 outbound EDS catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --subset version-v1
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
catalog.istioinaction.svc.cluster.local 80 version-v1 outbound EDS catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --subset version-v1 -o json
...
"name": "outbound|80|version-v1|catalog.istioinaction.svc.cluster.local",
"type": "EDS",
"edsClusterConfig": {
"edsConfig": {
"ads": {},
"initialFetchTimeout": "0s",
"resourceApiVersion": "V3"
},
"serviceName": "outbound|80|version-v1|catalog.istioinaction.svc.cluster.local"
},
...
"metadata": {
"filterMetadata": {
"istio": {
"config": "/apis/networking.istio.io/v1alpha3/namespaces/istioinaction/destination-rule/catalog",
"default_original_port": 80,
"services": [
{
"host": "catalog.istioinaction.svc.cluster.local",
"name": "catalog",
"namespace": "istioinaction"
}
],
"subset": "version-v1"
...
# endpoint
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system | egrep 'ENDPOINT|istioinaction'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.14:3000 HEALTHY OK outbound|80|version-v1|catalog.istioinaction.svc.cluster.local
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80|version-v2|catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80|version-v1|catalog.istioinaction.svc.cluster.local'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.14:3000 HEALTHY OK outbound|80|version-v1|catalog.istioinaction.svc.cluster.local
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80|version-v1|catalog.istioinaction.svc.cluster.local' -o json
...
# istio-proxy (catalog)
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/catalog.istioinaction --subset version-v1 -o json
...
"metadata": {
"filterMetadata": {
"istio": {
"config": "/apis/networking.istio.io/v1alpha3/namespaces/istioinaction/destination-rule/catalog",
"default_original_port": 80,
"services": [
{
"host": "catalog.istioinaction.svc.cluster.local",
"name": "catalog",
"namespace": "istioinaction"
}
],
"subset": "version-v1"
}
}
},
...

✅ 이 시점에서 모든 트래픽이 v1 라우팅 된다.
✅ 이제 특정 요청들을 통제된 방식으로 v2 라우팅하고 싶다. 다음 절에서 알아보자.

#
cat ch5/catalog-vs-v2-request.yaml
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: catalog-vs-from-gw
spec:
hosts:
- "catalog.istioinaction.io"
gateways:
- catalog-gateway
http:
- match:
- headers:
x-istio-cohort:
exact: "internal"
route:
- destination:
host: catalog
subset: version-v2
- route:
- destination:
host: catalog
subset: version-v1
kubectl apply -f ch5/catalog-vs-v2-request.yaml -n istioinaction
# 호출 테스트 : 여전히 v1
for i in {1..10}; do curl -s http://catalog.istioinaction.io:30000/items/ ; printf "\n\n"; done
# 요청 헤더 포함 호출 테스트 : v2!
curl http://catalog.istioinaction.io:30000/items -H "x-istio-cohort: internal"
# (옵션) 신규 터미널 : v2 반복 접속
while true; do curl -s http://catalog.istioinaction.io:30000/items/ -H "x-istio-cohort: internal" -I | head -n 1 ; date "+%Y-%m-%d %H:%M:%S" ; sleep 2; echo; done
# 상세 확인
# route 추가 : routes 에 2개의 route 확인 - 위에서 부터 적용되는 순서 중요!
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/istio-ingressgateway.istio-system --name http.8080
NAME DOMAINS MATCH VIRTUAL SERVICE
http.8080 catalog.istioinaction.io /* catalog-vs-from-gw.istioinaction
http.8080 catalog.istioinaction.io /* catalog-vs-from-gw.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/istio-ingressgateway.istio-system --name http.8080 -o json
...
"virtualHosts": [
{
"name": "catalog.istioinaction.io:80",
"domains": [
"catalog.istioinaction.io"
],
"routes": [
{
"match": {
"prefix": "/",
"caseSensitive": true,
"headers": [
{
"name": "x-istio-cohort",
"stringMatch": {
"exact": "internal"
}
}
]
},
"route": {
"cluster": "outbound|80|version-v2|catalog.istioinaction.svc.cluster.local",
"timeout": "0s",
...
{
"match": {
"prefix": "/"
},
"route": {
"cluster": "outbound|80|version-v1|catalog.istioinaction.svc.cluster.local",
...
#
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn catalog.istioinaction.svc.cluster.local
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system | egrep 'ENDPOINT|istioinaction'
# istio-proxy (catalog)에는 routes 정보가 아래 cluster 로 보내는 1개만 있다. 즉 istio-proxy(istio-ingressgateway)가 routes 분기 처리하는 것을 알 수 있다.
## "cluster": "outbound|80||catalog.istioinaction.svc.cluster.local"
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/catalog.istioinaction --name 80 -o json
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/catalog.istioinaction | grep catalog
80 catalog, catalog.istioinaction + 1 more... /*


# 초기화
kubectl delete gateway,virtualservice,destinationrule --all -n istioinaction
serviceaccount/webapp created
service/webapp created
deployment.apps/webapp created
serviceaccount/catalog unchanged
service/catalog unchanged
deployment.apps/catalog unchanged
# webapp 기동
kubectl apply -n istioinaction -f services/webapp/kubernetes/webapp.yaml
kubectl apply -f services/catalog/kubernetes/catalog.yaml -n istioinaction # 이미 배포 상태
kubectl apply -f services/catalog/kubernetes/catalog-deployment-v2.yaml -n istioinaction # 이미 배포 상태
# 확인
kubectl get deploy,pod,svc,ep -n istioinaction
NAME READY UP-TO-DATE AVAILABLE AGE
deployment.apps/catalog 1/1 1 1 3h13m
deployment.apps/catalog-v2 1/1 1 1 58m
deployment.apps/webapp 1/1 1 1 5m54s
NAME READY STATUS RESTARTS AGE
pod/catalog-6cf4b97d-5hwg7 2/2 Running 0 3h13m
pod/catalog-v2-6df885b555-q7xnv 2/2 Running 0 58m
pod/webapp-7685bcb84-xphnb 2/2 Running 0 5m54s
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
service/catalog ClusterIP 10.200.1.174 <none> 80/TCP 3h13m
service/webapp ClusterIP 10.200.1.206 <none> 80/TCP 5m54s
NAME ENDPOINTS AGE
endpoints/catalog 10.10.0.14:3000,10.10.0.15:3000 3h13m
endpoints/webapp 10.10.0.16:8080 5m54s
# Now, set up the Istio ingress gateway to route to the webapp service
cat services/webapp/istio/webapp-catalog-gw-vs.yaml
---
apiVersion: networking.istio.io/v1alpha3
kind: Gateway
metadata:
name: coolstore-gateway
spec:
selector:
istio: ingressgateway # use istio default controller
servers:
- port:
number: 80
name: http
protocol: HTTP
hosts:
- "webapp.istioinaction.io"
---
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: webapp-virtualservice
spec:
hosts:
- "webapp.istioinaction.io"
gateways:
- coolstore-gateway
http:
- route:
- destination:
host: webapp
port:
number: 80
kubectl apply -f services/webapp/istio/webapp-catalog-gw-vs.yaml -n istioinaction
gateway.networking.istio.io/coolstore-gateway created
virtualservice.networking.istio.io/webapp-virtualservice created
# 확인
kubectl get gw,vs -n istioinaction
NAME AGE
gateway.networking.istio.io/catalog-gateway 3h15m
gateway.networking.istio.io/coolstore-gateway 3m21s
NAME GATEWAYS HOSTS AGE
virtualservice.networking.istio.io/catalog-vs-from-gw ["catalog-gateway"] ["catalog.istioinaction.io"] 3h13m
virtualservice.networking.istio.io/webapp-virtualservice ["coolstore-gateway"] ["webapp.istioinaction.io"] 3m21s
# 도메인 질의를 위한 임시 설정 : 실습 완료 후에는 삭제 해둘 것
echo "127.0.0.1 webapp.istioinaction.io" | sudo tee -a /etc/hosts
cat /etc/hosts | tail -n 3
127.0.0.1 catalog.istioinaction.io
127.0.0.1 webapp.istioinaction.io
# 호출테스트 : 외부(web, curl) → ingressgw → webapp → catalog (v1, v2)
curl -s http://webapp.istioinaction.io:30000/api/catalog | jq
# 반복 호출테스트 : 신규터미널 2개에 아래 각각 실행 해두기
while true; do curl -s http://webapp.istioinaction.io:30000/api/catalog -I | head -n 1 ; date "+%Y-%m-%d %H:%M:%S" ; sleep 1; echo; done
while true; do curl -s http://webapp.istioinaction.io:30000/api/catalog -H "x-istio-cohort: internal" -I | head -n 1 ; date "+%Y-%m-%d %H:%M:%S" ; sleep 2; echo; done
# proxy-config : istio-ingressgateway
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/istio-ingressgateway.istio-system --name http.8080
NAME DOMAINS MATCH VIRTUAL SERVICE
http.8080 webapp.istioinaction.io /* webapp-virtualservice.istioinaction
=> route."cluster": "outbound|80||webapp.istioinaction.svc.cluster.local"
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system | egrep 'webapp|catalog'
catalog.istioinaction.svc.cluster.local 80 - outbound EDS
webapp.istioinaction.svc.cluster.local 80 - outbound EDS
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn webapp.istioinaction.svc.cluster.local -o json
...
"name": "outbound|80||webapp.istioinaction.svc.cluster.local",
"type": "EDS",
...
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system --cluster 'outbound|80||webapp.istioinaction.svc.cluster.local'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.16:8080 HEALTHY OK outbound|80||webapp.istioinaction.svc.cluster.local
# proxy-config : webapp
docker exec -it myk8s-control-plane istioctl proxy-config listener deploy/webapp.istioinaction
ADDRESS PORT MATCH DESTINATION
10.200.1.10 53 ALL Cluster: outbound|53||kube-dns.kube-system.svc.cluster.local
0.0.0.0 80 Trans: raw_buffer; App: http/1.1,h2c Route: 80
0.0.0.0 80 ALL PassthroughCluster
10.200.1.1 443 ALL Cluster: outbound|443||kubernetes.default.svc.cluster.local
10.200.1.17 443 ALL Cluster: outbound|443||metrics-server.kube-system.svc.cluster.local
10.200.1.172 443 ALL Cluster: outbound|443||istio-ingressgateway.istio-system.svc.cluster.local
10.200.1.182 443 ALL Cluster: outbound|443||istiod.istio-system.svc.cluster.local
10.200.1.190 3000 Trans: raw_buffer; App: http/1.1,h2c Route: grafana.istio-system.svc.cluster.local:3000
10.200.1.190 3000 ALL Cluster: outbound|3000||grafana.istio-system.svc.cluster.local
0.0.0.0 8080 Trans: raw_buffer; App: http/1.1,h2c Route: 8080
0.0.0.0 8080 ALL PassthroughCluster
0.0.0.0 9090 Trans: raw_buffer; App: http/1.1,h2c Route: 9090
0.0.0.0 9090 ALL PassthroughCluster
10.200.1.10 9153 Trans: raw_buffer; App: http/1.1,h2c Route: kube-dns.kube-system.svc.cluster.local:9153
10.200.1.10 9153 ALL Cluster: outbound|9153||kube-dns.kube-system.svc.cluster.local
0.0.0.0 9411 Trans: raw_buffer; App: http/1.1,h2c Route: 9411
0.0.0.0 9411 ALL PassthroughCluster
10.200.1.53 14250 Trans: raw_buffer; App: http/1.1,h2c Route: jaeger-collector.istio-system.svc.cluster.local:14250
10.200.1.53 14250 ALL Cluster: outbound|14250||jaeger-collector.istio-system.svc.cluster.local
10.200.1.53 14268 Trans: raw_buffer; App: http/1.1,h2c Route: jaeger-collector.istio-system.svc.cluster.local:14268
10.200.1.53 14268 ALL Cluster: outbound|14268||jaeger-collector.istio-system.svc.cluster.local
0.0.0.0 15001 ALL PassthroughCluster
0.0.0.0 15001 Addr: *:15001 Non-HTTP/Non-TCP
0.0.0.0 15006 Addr: *:15006 Non-HTTP/Non-TCP
0.0.0.0 15006 Trans: tls; App: istio-http/1.0,istio-http/1.1,istio-h2; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: raw_buffer; App: http/1.1,h2c; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: tls; App: TCP TLS; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: raw_buffer; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: tls; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: tls; App: istio,istio-peer-exchange,istio-http/1.0,istio-http/1.1,istio-h2; Addr: *:8080 Cluster: inbound|8080||
0.0.0.0 15006 Trans: raw_buffer; Addr: *:8080 Cluster: inbound|8080||
0.0.0.0 15010 Trans: raw_buffer; App: http/1.1,h2c Route: 15010
0.0.0.0 15010 ALL PassthroughCluster
10.200.1.182 15012 ALL Cluster: outbound|15012||istiod.istio-system.svc.cluster.local
0.0.0.0 15014 Trans: raw_buffer; App: http/1.1,h2c Route: 15014
0.0.0.0 15014 ALL PassthroughCluster
0.0.0.0 15021 ALL Inline Route: /healthz/ready*
10.200.1.172 15021 Trans: raw_buffer; App: http/1.1,h2c Route: istio-ingressgateway.istio-system.svc.cluster.local:15021
10.200.1.172 15021 ALL Cluster: outbound|15021||istio-ingressgateway.istio-system.svc.cluster.local
0.0.0.0 15090 ALL Inline Route: /stats/prometheus*
0.0.0.0 16685 Trans: raw_buffer; App: http/1.1,h2c Route: 16685
0.0.0.0 16685 ALL PassthroughCluster
0.0.0.0 20001 Trans: raw_buffer; App: http/1.1,h2c Route: 20001
0.0.0.0 20001 ALL PassthroughCluster
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/webapp.istioinaction
NAME DOMAINS MATCH VIRTUAL SERVICE
80 catalog, catalog.istioinaction + 1 more... /*
80 istio-ingressgateway.istio-system, 10.200.1.172 /*
80 tracing.istio-system, 10.200.1.164 /*
80 webapp, webapp.istioinaction + 1 more... /*
8080 kube-ops-view.kube-system, 10.200.1.144 /*
9090 kiali.istio-system, 10.200.1.26 /*
9090 prometheus.istio-system, 10.200.1.104 /*
9411 jaeger-collector.istio-system, 10.200.1.53 /*
9411 zipkin.istio-system, 10.200.1.6 /*
15010 istiod.istio-system, 10.200.1.182 /*
15014 istiod.istio-system, 10.200.1.182 /*
16685 tracing.istio-system, 10.200.1.164 /*
grafana.istio-system.svc.cluster.local:3000 * /*
20001 kiali.istio-system, 10.200.1.26 /*
istio-ingressgateway.istio-system.svc.cluster.local:15021 * /*
kube-dns.kube-system.svc.cluster.local:9153 * /*
jaeger-collector.istio-system.svc.cluster.local:14268 * /*
jaeger-collector.istio-system.svc.cluster.local:14250 * /*
* /healthz/ready*
inbound|8080|| * /*
InboundPassthroughClusterIpv4 * /*
* /stats/prometheus*
InboundPassthroughClusterIpv4 * /*
inbound|8080|| * /*
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/webapp.istioinaction
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
8080 - inbound ORIGINAL_DST
BlackHoleCluster - - - STATIC
InboundPassthroughClusterIpv4 - - - ORIGINAL_DST
PassthroughCluster - - - ORIGINAL_DST
agent - - - STATIC
catalog.istioinaction.svc.cluster.local 80 - outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v1 outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v2 outbound EDS catalog.istioinaction
grafana.istio-system.svc.cluster.local 3000 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 80 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 443 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 15021 - outbound EDS
istiod.istio-system.svc.cluster.local 443 - outbound EDS
istiod.istio-system.svc.cluster.local 15010 - outbound EDS
istiod.istio-system.svc.cluster.local 15012 - outbound EDS
istiod.istio-system.svc.cluster.local 15014 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 9411 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 14250 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 14268 - outbound EDS
kiali.istio-system.svc.cluster.local 9090 - outbound EDS
kiali.istio-system.svc.cluster.local 20001 - outbound EDS
kube-dns.kube-system.svc.cluster.local 53 - outbound EDS
kube-dns.kube-system.svc.cluster.local 9153 - outbound EDS
kube-ops-view.kube-system.svc.cluster.local 8080 - outbound EDS
kubernetes.default.svc.cluster.local 443 - outbound EDS
metrics-server.kube-system.svc.cluster.local 443 - outbound EDS
prometheus.istio-system.svc.cluster.local 9090 - outbound EDS
prometheus_stats - - - STATIC
sds-grpc - - - STATIC
tracing.istio-system.svc.cluster.local 80 - outbound EDS
tracing.istio-system.svc.cluster.local 16685 - outbound EDS
webapp.istioinaction.svc.cluster.local 80 - outbound EDS
xds-grpc - - - STATIC
zipkin - - - STRICT_DNS
zipkin.istio-system.svc.cluster.local 9411 - outbound EDS
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/webapp.istioinaction
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.10:53 HEALTHY OK outbound|53||kube-dns.kube-system.svc.cluster.local
10.10.0.10:9153 HEALTHY OK outbound|9153||kube-dns.kube-system.svc.cluster.local
10.10.0.11:8080 HEALTHY OK outbound|8080||kube-ops-view.kube-system.svc.cluster.local
10.10.0.12:9090 HEALTHY OK outbound|9090||prometheus.istio-system.svc.cluster.local
10.10.0.13:8080 HEALTHY OK outbound|80||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.13:8443 HEALTHY OK outbound|443||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.13:15021 HEALTHY OK outbound|15021||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.14:3000 HEALTHY OK outbound|80|version-v1|catalog.istioinaction.svc.cluster.local
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80|version-v2|catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.16:8080 HEALTHY OK inbound|8080||
10.10.0.16:8080 HEALTHY OK outbound|80||webapp.istioinaction.svc.cluster.local
10.10.0.2:53 HEALTHY OK outbound|53||kube-dns.kube-system.svc.cluster.local
10.10.0.2:9153 HEALTHY OK outbound|9153||kube-dns.kube-system.svc.cluster.local
10.10.0.3:3000 HEALTHY OK outbound|3000||grafana.istio-system.svc.cluster.local
10.10.0.4:9411 HEALTHY OK outbound|9411||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:9411 HEALTHY OK outbound|9411||zipkin.istio-system.svc.cluster.local
10.10.0.4:14250 HEALTHY OK outbound|14250||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:14268 HEALTHY OK outbound|14268||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:16685 HEALTHY OK outbound|16685||tracing.istio-system.svc.cluster.local
10.10.0.4:16686 HEALTHY OK outbound|80||tracing.istio-system.svc.cluster.local
10.10.0.6:10250 HEALTHY OK outbound|443||metrics-server.kube-system.svc.cluster.local
10.10.0.8:15010 HEALTHY OK outbound|15010||istiod.istio-system.svc.cluster.local
10.10.0.8:15012 HEALTHY OK outbound|15012||istiod.istio-system.svc.cluster.local
10.10.0.8:15014 HEALTHY OK outbound|15014||istiod.istio-system.svc.cluster.local
10.10.0.8:15017 HEALTHY OK outbound|443||istiod.istio-system.svc.cluster.local
10.10.0.9:9090 HEALTHY OK outbound|9090||kiali.istio-system.svc.cluster.local
10.10.0.9:20001 HEALTHY OK outbound|20001||kiali.istio-system.svc.cluster.local
10.200.1.6:9411 HEALTHY OK zipkin
127.0.0.1:15000 HEALTHY OK prometheus_stats
127.0.0.1:15020 HEALTHY OK agent
172.19.0.2:6443 HEALTHY OK outbound|443||kubernetes.default.svc.cluster.local
unix://./etc/istio/proxy/XDS HEALTHY OK xds-grpc
unix://./var/run/secrets/workload-spiffe-uds/socket HEALTHY OK sds-grpc
# proxy-config : catalog
docker exec -it myk8s-control-plane istioctl proxy-config listener deploy/catalog.istioinaction
ADDRESS PORT MATCH DESTINATION
10.200.1.10 53 ALL Cluster: outbound|53||kube-dns.kube-system.svc.cluster.local
0.0.0.0 80 Trans: raw_buffer; App: http/1.1,h2c Route: 80
0.0.0.0 80 ALL PassthroughCluster
10.200.1.1 443 ALL Cluster: outbound|443||kubernetes.default.svc.cluster.local
10.200.1.17 443 ALL Cluster: outbound|443||metrics-server.kube-system.svc.cluster.local
10.200.1.172 443 ALL Cluster: outbound|443||istio-ingressgateway.istio-system.svc.cluster.local
10.200.1.182 443 ALL Cluster: outbound|443||istiod.istio-system.svc.cluster.local
10.200.1.190 3000 Trans: raw_buffer; App: http/1.1,h2c Route: grafana.istio-system.svc.cluster.local:3000
10.200.1.190 3000 ALL Cluster: outbound|3000||grafana.istio-system.svc.cluster.local
0.0.0.0 8080 Trans: raw_buffer; App: http/1.1,h2c Route: 8080
0.0.0.0 8080 ALL PassthroughCluster
0.0.0.0 9090 Trans: raw_buffer; App: http/1.1,h2c Route: 9090
0.0.0.0 9090 ALL PassthroughCluster
10.200.1.10 9153 Trans: raw_buffer; App: http/1.1,h2c Route: kube-dns.kube-system.svc.cluster.local:9153
10.200.1.10 9153 ALL Cluster: outbound|9153||kube-dns.kube-system.svc.cluster.local
0.0.0.0 9411 Trans: raw_buffer; App: http/1.1,h2c Route: 9411
0.0.0.0 9411 ALL PassthroughCluster
10.200.1.53 14250 Trans: raw_buffer; App: http/1.1,h2c Route: jaeger-collector.istio-system.svc.cluster.local:14250
10.200.1.53 14250 ALL Cluster: outbound|14250||jaeger-collector.istio-system.svc.cluster.local
10.200.1.53 14268 Trans: raw_buffer; App: http/1.1,h2c Route: jaeger-collector.istio-system.svc.cluster.local:14268
10.200.1.53 14268 ALL Cluster: outbound|14268||jaeger-collector.istio-system.svc.cluster.local
0.0.0.0 15001 ALL PassthroughCluster
0.0.0.0 15001 Addr: *:15001 Non-HTTP/Non-TCP
0.0.0.0 15006 Addr: *:15006 Non-HTTP/Non-TCP
0.0.0.0 15006 Trans: tls; App: istio-http/1.0,istio-http/1.1,istio-h2; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: raw_buffer; App: http/1.1,h2c; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: tls; App: TCP TLS; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: raw_buffer; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: tls; Addr: 0.0.0.0/0 InboundPassthroughClusterIpv4
0.0.0.0 15006 Trans: tls; App: istio,istio-peer-exchange,istio-http/1.0,istio-http/1.1,istio-h2; Addr: *:3000 Cluster: inbound|3000||
0.0.0.0 15006 Trans: raw_buffer; Addr: *:3000 Cluster: inbound|3000||
0.0.0.0 15010 Trans: raw_buffer; App: http/1.1,h2c Route: 15010
0.0.0.0 15010 ALL PassthroughCluster
10.200.1.182 15012 ALL Cluster: outbound|15012||istiod.istio-system.svc.cluster.local
0.0.0.0 15014 Trans: raw_buffer; App: http/1.1,h2c Route: 15014
0.0.0.0 15014 ALL PassthroughCluster
0.0.0.0 15021 ALL Inline Route: /healthz/ready*
10.200.1.172 15021 Trans: raw_buffer; App: http/1.1,h2c Route: istio-ingressgateway.istio-system.svc.cluster.local:15021
10.200.1.172 15021 ALL Cluster: outbound|15021||istio-ingressgateway.istio-system.svc.cluster.local
0.0.0.0 15090 ALL Inline Route: /stats/prometheus*
0.0.0.0 16685 Trans: raw_buffer; App: http/1.1,h2c Route: 16685
0.0.0.0 16685 ALL PassthroughCluster
0.0.0.0 20001 Trans: raw_buffer; App: http/1.1,h2c Route: 20001
0.0.0.0 20001 ALL PassthroughCluster
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/catalog.istioinaction
NAME DOMAINS MATCH VIRTUAL SERVICE
80 catalog, catalog.istioinaction + 1 more... /*
80 istio-ingressgateway.istio-system, 10.200.1.172 /*
80 tracing.istio-system, 10.200.1.164 /*
80 webapp, webapp.istioinaction + 1 more... /*
8080 kube-ops-view.kube-system, 10.200.1.144 /*
9090 kiali.istio-system, 10.200.1.26 /*
9090 prometheus.istio-system, 10.200.1.104 /*
9411 jaeger-collector.istio-system, 10.200.1.53 /*
9411 zipkin.istio-system, 10.200.1.6 /*
15010 istiod.istio-system, 10.200.1.182 /*
15014 istiod.istio-system, 10.200.1.182 /*
istio-ingressgateway.istio-system.svc.cluster.local:15021 * /*
jaeger-collector.istio-system.svc.cluster.local:14268 * /*
20001 kiali.istio-system, 10.200.1.26 /*
16685 tracing.istio-system, 10.200.1.164 /*
jaeger-collector.istio-system.svc.cluster.local:14250 * /*
kube-dns.kube-system.svc.cluster.local:9153 * /*
grafana.istio-system.svc.cluster.local:3000 * /*
InboundPassthroughClusterIpv4 * /*
* /stats/prometheus*
InboundPassthroughClusterIpv4 * /*
* /healthz/ready*
inbound|3000|| * /*
inbound|3000|| * /*
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/catalog.istioinaction
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
3000 - inbound ORIGINAL_DST
BlackHoleCluster - - - STATIC
InboundPassthroughClusterIpv4 - - - ORIGINAL_DST
PassthroughCluster - - - ORIGINAL_DST
agent - - - STATIC
catalog.istioinaction.svc.cluster.local 80 - outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v1 outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v2 outbound EDS catalog.istioinaction
grafana.istio-system.svc.cluster.local 3000 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 80 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 443 - outbound EDS
istio-ingressgateway.istio-system.svc.cluster.local 15021 - outbound EDS
istiod.istio-system.svc.cluster.local 443 - outbound EDS
istiod.istio-system.svc.cluster.local 15010 - outbound EDS
istiod.istio-system.svc.cluster.local 15012 - outbound EDS
istiod.istio-system.svc.cluster.local 15014 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 9411 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 14250 - outbound EDS
jaeger-collector.istio-system.svc.cluster.local 14268 - outbound EDS
kiali.istio-system.svc.cluster.local 9090 - outbound EDS
kiali.istio-system.svc.cluster.local 20001 - outbound EDS
kube-dns.kube-system.svc.cluster.local 53 - outbound EDS
kube-dns.kube-system.svc.cluster.local 9153 - outbound EDS
kube-ops-view.kube-system.svc.cluster.local 8080 - outbound EDS
kubernetes.default.svc.cluster.local 443 - outbound EDS
metrics-server.kube-system.svc.cluster.local 443 - outbound EDS
prometheus.istio-system.svc.cluster.local 9090 - outbound EDS
prometheus_stats - - - STATIC
sds-grpc - - - STATIC
tracing.istio-system.svc.cluster.local 80 - outbound EDS
tracing.istio-system.svc.cluster.local 16685 - outbound EDS
webapp.istioinaction.svc.cluster.local 80 - outbound EDS
xds-grpc - - - STATIC
zipkin - - - STRICT_DNS
zipkin.istio-system.svc.cluster.local 9411 - outbound EDS
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/catalog.istioinaction
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.10:53 HEALTHY OK outbound|53||kube-dns.kube-system.svc.cluster.local
10.10.0.10:9153 HEALTHY OK outbound|9153||kube-dns.kube-system.svc.cluster.local
10.10.0.11:8080 HEALTHY OK outbound|8080||kube-ops-view.kube-system.svc.cluster.local
10.10.0.12:9090 HEALTHY OK outbound|9090||prometheus.istio-system.svc.cluster.local
10.10.0.13:8080 HEALTHY OK outbound|80||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.13:8443 HEALTHY OK outbound|443||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.13:15021 HEALTHY OK outbound|15021||istio-ingressgateway.istio-system.svc.cluster.local
10.10.0.14:3000 HEALTHY OK inbound|3000||
10.10.0.14:3000 HEALTHY OK outbound|80|version-v1|catalog.istioinaction.svc.cluster.local
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80|version-v2|catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.16:8080 HEALTHY OK outbound|80||webapp.istioinaction.svc.cluster.local
10.10.0.2:53 HEALTHY OK outbound|53||kube-dns.kube-system.svc.cluster.local
10.10.0.2:9153 HEALTHY OK outbound|9153||kube-dns.kube-system.svc.cluster.local
10.10.0.3:3000 HEALTHY OK outbound|3000||grafana.istio-system.svc.cluster.local
10.10.0.4:9411 HEALTHY OK outbound|9411||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:9411 HEALTHY OK outbound|9411||zipkin.istio-system.svc.cluster.local
10.10.0.4:14250 HEALTHY OK outbound|14250||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:14268 HEALTHY OK outbound|14268||jaeger-collector.istio-system.svc.cluster.local
10.10.0.4:16685 HEALTHY OK outbound|16685||tracing.istio-system.svc.cluster.local
10.10.0.4:16686 HEALTHY OK outbound|80||tracing.istio-system.svc.cluster.local
10.10.0.6:10250 HEALTHY OK outbound|443||metrics-server.kube-system.svc.cluster.local
10.10.0.8:15010 HEALTHY OK outbound|15010||istiod.istio-system.svc.cluster.local
10.10.0.8:15012 HEALTHY OK outbound|15012||istiod.istio-system.svc.cluster.local
10.10.0.8:15014 HEALTHY OK outbound|15014||istiod.istio-system.svc.cluster.local
10.10.0.8:15017 HEALTHY OK outbound|443||istiod.istio-system.svc.cluster.local
10.10.0.9:9090 HEALTHY OK outbound|9090||kiali.istio-system.svc.cluster.local
10.10.0.9:20001 HEALTHY OK outbound|20001||kiali.istio-system.svc.cluster.local
10.200.1.6:9411 HEALTHY OK zipkin
127.0.0.1:15000 HEALTHY OK prometheus_stats
127.0.0.1:15020 HEALTHY OK agent
172.19.0.2:6443 HEALTHY OK outbound|443||kubernetes.default.svc.cluster.local
unix://./etc/istio/proxy/XDS HEALTHY OK xds-grpc
unix://./var/run/secrets/workload-spiffe-uds/socket HEALTHY OK sds-grpc
# webapp istio-proxy 로그 활성화
# 신규 터미널
kubectl logs -n istioinaction -l app=webapp -c istio-proxy -f
# webapp istio-proxy 로그 활성화 적용
cat << EOF | kubectl apply -f -
apiVersion: telemetry.istio.io/v1alpha1
kind: Telemetry
metadata:
name: webapp
namespace: istioinaction
spec:
selector:
matchLabels:
app: webapp
accessLogging:
- providers:
- name: envoy #2 액세스 로그를 위한 프로바이더 설정
disabled: false #3 disable 를 false 로 설정해 활성화한다
EOF
# webapp → catalog 는 k8s service(clusterIP) 라우팅 사용 확인!
kubectl logs -n istioinaction -l app=webapp -c istio-proxy -f
[2025-04-26T11:55:50.148Z] "HEAD /api/catalog HTTP/1.1" 200 - via_upstream - "-" 0 0 8 7 "192.168.65.1" "curl/8.13.0" "30cebb96-305a-4764-88bc-e38d6ca72781" "webapp.istioinaction.io:30000" "10.10.0.16:8080" inbound|8080|| 127.0.0.6:41909 10.10.0.16:8080 192.168.65.1:0 outbound_.80_._.webapp.istioinaction.svc.cluster.local default
=> 이 로그는 webapp 서비스의 사이드카 프록시가 클라이언트로부터 직접 HTTP 요청을 받은 장면이고, 이 요청을 10.10.0.16:8080 (즉, webapp 서비스의 실제 컨테이너)으로 보냄을 의미
[2025-04-26T11:55:50.973Z] "GET /items HTTP/1.1" 200 - via_upstream - "-" 0 698 3 2 "192.168.65.1" "beegoServer" "9f3517f7-1848-4d04-bf5b-cef53f09dd95" "catalog.istioinaction:80" "10.10.0.15:3000" outbound|80||catalog.istioinaction.svc.cluster.local 10.10.0.16:46044 10.200.1.174:80 192.168.65.1:0 - default
=> 이 로그는 webapp 서비스가 catalog 서비스로 HTTP 요청을 보낸 상황이에요. Envoy는 catalog.istioinaction이라는 Kubernetes catalog 서비스(clusterIp 10.200.1.174:80)로 라우팅하고, 실제 Pod IP는 10.10.0.15:3000으로 연결되었어요.
...


#
ch5/catalog-dest-rule.yaml
apiVersion: networking.istio.io/v1alpha3
kind: DestinationRule
metadata:
name: catalog
spec:
host: catalog.istioinaction.svc.cluster.local
subsets:
- name: version-v1
labels:
version: v1
- name: version-v2
labels:
version: v2
kubectl apply -f ch5/catalog-dest-rule.yaml -n istioinaction
# istio-proxy
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/istio-ingressgateway.istio-system --fqdn catalog.istioinaction.svc.cluster.local
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
catalog.istioinaction.svc.cluster.local 80 - outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v1 outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v2 outbound EDS catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/istio-ingressgateway.istio-system | egrep 'ENDPOINT|istioinaction'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.14:3000 HEALTHY OK outbound|80|version-v1|catalog.istioinaction.svc.cluster.local
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80|version-v2|catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.16:8080 HEALTHY OK outbound|80||webapp.istioinaction.svc.cluster.local
#
cat ch5/catalog-vs-v1-mesh.yaml
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: catalog
spec:
hosts:
- catalog
gateways: # 만약, gateways 부분을 제외하고 배포하면 암묵적으로 mesh gateways가 적용됨.
- mesh # VirtualService는 메시 내의 모든 사이드카(현재 webapp, catalog)에 적용된다. edge는 제외.
http:
- route:
- destination:
host: catalog
subset: version-v1
kubectl apply -f ch5/catalog-vs-v1-mesh.yaml -n istioinaction
virtualservice.networking.istio.io/catalog created
# VirtualService 확인 : GATEWAYS 에 mesh 확인
kubectl get vs -n istioinaction
NAME GATEWAYS HOSTS AGE
catalog ["mesh"] ["catalog"] 6m44s
catalog-vs-from-gw ["catalog-gateway"] ["catalog.istioinaction.io"] 4h39m
webapp-virtualservice ["coolstore-gateway"] ["webapp.istioinaction.io"] 88m
# 반복 호출테스트 : 신규터미널 2개에 아래 각각 실행 해두기 >> 현재는 v1만 라우팅 처리
while true; do curl -s http://webapp.istioinaction.io:30000/api/catalog -I | head -n 1 ; date "+%Y-%m-%d %H:%M:%S" ; sleep 1; echo; done
while true; do curl -s http://webapp.istioinaction.io:30000/api/catalog -H "x-istio-cohort: internal" -I | head -n 1 ; date "+%Y-%m-%d %H:%M:%S" ; sleep 2; echo; done
# webapp → catalog 호출도 istio 의 DestinationRule 라우팅 전달 처리! : 신규터미널
kubectl logs -n istioinaction -l app=webapp -c istio-proxy -f
[2025-04-26T13:09:36.374Z] "GET /items HTTP/1.1" 200 - via_upstream - "-" 0 502 2 2 "192.168.65.1" "beegoServer" "92af0393-d73f-4731-8c9a-1e8fb43b428e" "catalog.istioinaction:80" "10.10.0.14:3000" outbound|80|version-v1|catalog.istioinaction.svc.cluster.local 10.10.0.16:45786 10.200.1.174:80 192.168.65.1:0 - -
=> 이 로그는 webapp이 내부적으로 catalog 서비스를 호출하는 로그이고, version-v1이라는 **서브셋(subset)**으로 요청이 라우팅되었어요. 이는 DestinationRule에서 subset: version-v1으로 정의된 엔드포인트로 라우팅이 잘 되었다는 뜻이에요.
# proxy-config (webapp) : 기존에 webapp 에서 catalog 로 VirtualService 정보는 없었는데, 추가됨을 확인
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/webapp.istioinaction | egrep 'NAME|catalog'
NAME DOMAINS MATCH VIRTUAL SERVICE
80 catalog, catalog.istioinaction + 1 more... /* catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/webapp.istioinaction --name 80 -o json > webapp-routes.json
cat webapp-routes.json | jq
...
"virtualHosts": [
{
"name": "catalog.istioinaction.svc.cluster.local:80",
"domains": [
"catalog.istioinaction.svc.cluster.local",
"catalog",
"catalog.istioinaction.svc",
"catalog.istioinaction",
"10.200.1.174" # 해당 IP는 catalog service(clusterIP)
],
"routes": [
{
"match": {
"prefix": "/"
},
"route": {
"cluster": "outbound|80|version-v1|catalog.istioinaction.svc.cluster.local",
"timeout": "0s",
...
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/webapp.istioinaction --fqdn catalog.istioinaction.svc.cluster.local
SERVICE FQDN PORT SUBSET DIRECTION TYPE DESTINATION RULE
catalog.istioinaction.svc.cluster.local 80 - outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v1 outbound EDS catalog.istioinaction
catalog.istioinaction.svc.cluster.local 80 version-v2 outbound EDS catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/webapp.istioinaction --subset version-v1 -o json
...
"name": "outbound|80|version-v1|catalog.istioinaction.svc.cluster.local",
"type": "EDS",
...
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/webapp.istioinaction | egrep 'ENDPOINT|catalog'
ENDPOINT STATUS OUTLIER CHECK CLUSTER
10.10.0.14:3000 HEALTHY OK outbound|80|version-v1|catalog.istioinaction.svc.cluster.local
10.10.0.14:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80|version-v2|catalog.istioinaction.svc.cluster.local
10.10.0.15:3000 HEALTHY OK outbound|80||catalog.istioinaction.svc.cluster.local
# proxy-config (catalog) : gateway.mesh 이므로, 메시 내에 모든 사이드카에 VirtualService 적용됨을 확인. 아래 routes 부분
docker exec -it myk8s-control-plane istioctl proxy-config listener deploy/catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/catalog.istioinaction | egrep 'NAME|catalog'
NAME DOMAINS MATCH VIRTUAL SERVICE
80 catalog, catalog.istioinaction + 1 more... /* catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/catalog.istioinaction


#
cat ch5/catalog-vs-v2-request-mesh.yaml
apiVersion: networking.istio.io/v1alpha3
kind: VirtualService
metadata:
name: catalog
spec:
hosts:
- catalog
gateways:
- mesh
http:
- match:
- headers:
x-istio-cohort:
exact: "internal"
route:
- destination:
host: catalog
subset: version-v2
- route:
- destination:
host: catalog
subset: version-v1
kubectl apply -f ch5/catalog-vs-v2-request-mesh.yaml -n istioinaction
virtualservice.networking.istio.io/catalog configured
# 반복 호출테스트 : 신규터미널 2개에 아래 각각 실행 >> v1, v2 각기 라우팅 확인
while true; do curl -s http://webapp.istioinaction.io:30000/api/catalog -I | head -n 1 ; date "+%Y-%m-%d %H:%M:%S" ; sleep 1; echo; done
while true; do curl -s http://webapp.istioinaction.io:30000/api/catalog -H "x-istio-cohort: internal" -I | head -n 1 ; date "+%Y-%m-%d %H:%M:%S" ; sleep 2; echo; done
# proxy-config (webapp) : 기존에 webapp 에서 catalog 로 VirtualService 추가된 2개 항목 확인
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/webapp.istioinaction | egrep 'NAME|catalog'
NAME DOMAINS MATCH VIRTUAL SERVICE
80 catalog, catalog.istioinaction + 1 more... /* catalog.istioinaction
80 catalog, catalog.istioinaction + 1 more... /* catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/webapp.istioinaction --name 80 -o json > webapp-routes.json
cat webapp-routes.json | jq
...
"virtualHosts": [
{
"name": "catalog.istioinaction.svc.cluster.local:80",
"domains": [
"catalog.istioinaction.svc.cluster.local",
"catalog",
"catalog.istioinaction.svc",
"catalog.istioinaction",
"10.200.1.206"
],
"routes": [
{
"match": {
"prefix": "/",
"caseSensitive": true,
"headers": [
{
"name": "x-istio-cohort",
"stringMatch": {
"exact": "internal"
}
}
]
},
"route": {
"cluster": "outbound|80|version-v2|catalog.istioinaction.svc.cluster.local",
....
{
"match": {
"prefix": "/"
},
"route": {
"cluster": "outbound|80|version-v1|catalog.istioinaction.svc.cluster.local",
...
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/webapp.istioinaction --fqdn catalog.istioinaction.svc.cluster.local
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/webapp.istioinaction | egrep 'ENDPOINT|catalog'
# proxy-config (catalog) : mesh 이므로 VS가 아래 routes(catalog)에도 적용됨
docker exec -it myk8s-control-plane istioctl proxy-config listener deploy/catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config routes deploy/catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config cluster deploy/catalog.istioinaction
docker exec -it myk8s-control-plane istioctl proxy-config endpoint deploy/catalog.istioinaction

💘 Manual Canary Release: 가중치로 트래픽을 천천히 넘기는 방법
서비스를 점진적으로 릴리스하는 또 다른 방법,
즉 가중치 기반 카나리 배포에 대해 알아보겠습니다.
이전에는 헤더 기반 라우팅을 이용해 특정 사용자 그룹(예: 내부 직원)에게만
새 버전을 다크 런치하는 방법을 살펴봤는데요,
이번에는 실제 라이브 트래픽을 버전별로 가중치를 나누어 배포하는 방식을 소개하려 합니다.
🤔 왜 가중치 기반 카나리 배포를 할까?
예를 들어, 우리가 catalog 서비스의 새로운 버전인 v2를 다크 런치한 상태라고 해봅시다.
이제 이 v2 버전을 모든 사용자에게 조금씩 노출시키고 싶다면,
v2에 10% 트래픽만 보내도록 설정할 수 있습니다.
이렇게 하면, 새 버전이 시스템 전체에 미치는 영향을 점진적으로 확인할 수 있어
릴리스로 인한 위험을 크게 줄일 수 있습니다.
😂 문제가 생기면?
다크 런치 때와 마찬가지로, 새 버전에서 에러나 장애가 발생하는지 모니터링합니다.
문제가 발견되면?
롤백은 아주 간단합니다.
그냥 v2로 향하는 트래픽 가중치를 줄이면 됩니다.
필요하면 0%로 만들어서 v2 트래픽을 아예 차단할 수도 있죠.
✅ 이스티오로 어떻게 할까?
Istio 같은 서비스 메시는 이런 가중치 기반 트래픽 분배를 아주 쉽게 설정할 수 있습니다.
Istio를 이용해 실제로 가중치 조정하는 방법을 구체적으로 알아볼게요!
✅ Istio로 가중치 기반 카나리 배포하기
앞서 가중치로 트래픽을 나누는 개념을 살펴봤죠?
이번에는 Istio를 사용해 실제로 catalog 서비스의 트래픽을 v1과 v2로 분배하는 방법을 알아보겠습니다.
Istio에서는 VirtualService 리소스를 이용해 트래픽 분배를 설정할 수 있습니다.
아래는 예시 YAML입니다:
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: catalog
spec:
hosts:
- catalog.default.svc.cluster.local
http:
- route:
- destination:
host: catalog
subset: v1
weight: 90
- destination:
host: catalog
subset: v2
weight: 10
✅ 이 설정이 의미하는 것
catalog 서비스로 들어오는 모든 요청은subset은 DestinationRule에서 정의하는 버전 구분입니다.v1과 v2는 각각의 레이블을 가진 버전)그래서 이 설정을 적용하면, 사용자는 특별히 인식하지 못한 채 자연스럽게 일부만 새 버전(v2)을 사용하게 됩니다.
✅ 추가로 필요한 설정: DestinationRule
아까 subset: v1, subset: v2 얘기가 나왔죠?
이걸 사용하려면 DestinationRule도 미리 정의해줘야 합니다.
apiVersion: networking.istio.io/v1beta1
kind: DestinationRule
metadata:
name: catalog
spec:
host: catalog.default.svc.cluster.local
subsets:
- name: v1
labels:
version: v1
- name: v2
labels:
version: v2
여기서는
version: v1 레이블을 가진 pod는 v1 subset으로,version: v2 레이블을 가진 pod는 v2 subset으로 매칭됩니다.catalog 서비스 뒤에 v1, v2 버전 pod들이 각각 떠 있어야 해요!)✅ 트래픽 가중치 조정은?
문제없이 운영된다면 v2의 weight를 점진적으로 늘려가면서 트래픽을 30%, 50%, 70%, 마지막엔 100%까지 늘리는 식으로 롤아웃을 완료할 수 있습니다.
반대로 문제가 생기면? v2의 weight를 0으로 줄이고,
모든 트래픽을 다시 v1으로 보내면 됩니다.
🎯 이렇게 Istio를 이용하면 복잡한 코드 수정 없이 트래픽만 제어해서 안전하게 카나리 배포를 진행할 수 있습니다. 실제 운영 환경에서는 모니터링과 함께 이 방법을 꼭 병행하는 걸 추천합니다.
앞서 요청 수준 라우팅과 트래픽 가중치 전환을 이용해 새 버전을 점진적으로 릴리스하면서 위험을 제어하는 방법을 알아봤습니다.
하지만 이 방법들은 모두 실제 사용자 요청을 새 버전으로 일부 보내기 때문에, 아무리 조심해도 사용자에게 일정 부분 영향이 갈 수밖에 없었습니다.
✅ 트래픽 미러링은 다른 접근이다!
Traffic Mirroring(트래픽 미러링) 은 라이브 트래픽을 진짜 서비스로 보내는 동시에, 복사본을 새 버전의 서비스로 보내는 방법입니다.
이 방식을 사용하면, 운영 환경 트래픽을 기반으로 새 버전이 실제로 어떻게 동작하는지 진짜로 테스트할 수 있습니다.
결론적으로: 트래픽 미러링은 릴리스 위험을 최소화할 수 있는 매우 안전한 전략입니다.
✅ Istio에서 트래픽 미러링 설정 예시
Istio에서는 VirtualService에 mirror 필드를 추가해서 쉽게 설정할 수 있습니다.
아래는 예시 YAML입니다:
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: catalog
spec:
hosts:
- catalog.default.svc.cluster.local
http:
- route:
- destination:
host: catalog
subset: v1
mirror:
host: catalog
subset: v2
mirrorPercentage:
value: 100.0
🤔 이 설정이 의미하는 것
mirrorPercentage를 조절하면, 예를 들어 50%만 미러링하는 것도 가능합니다.
mirrorPercentage:
value: 50.0
(=> 2개 요청 중 1개만 v2로 복사)
✍🏿 정리
| 방법 | 사용자 영향 | 주요 특징 |
|---|---|---|
| 가중치 기반 카나리 릴리스 | 있음 | 일부 사용자만 새 버전 사용 |
| 트래픽 미러링 | 없음 | 사용자 영향 없이 새 버전 검증 가능 |
트래픽 미러링은
배포 전 최종 점검이나
운영 환경 데이터 기반 실전 테스트를 하고 싶을 때
가장 안전한 방법입니다.
✅ 기본 동작
✅ 외부 트래픽 차단 설정
✅ 주의할 점
✅ 보안 위협 예시
➡️ Istio에서 외부 트래픽 제어하기
➡️ 1. 기본 정책 바꾸기: meshConfig 수정
meshConfig에서 outboundTrafficPolicy를 수정해야 해요.➡️ 수정 방법
meshConfig:
outboundTrafficPolicy:
mode: REGISTRY_ONLY
➡️ REGISTRY_ONLY로 설정하면, 명시적으로 등록한 외부 서비스만 통신할 수 있습니다.
🎯 외부 서비스 등록하기: ServiceEntry 사용
REGISTRY_ONLY 모드에서는 외부 서비스로 나가려면 ServiceEntry 리소스를 만들어야 합니다.
🎯 예시: 외부 API 서버 (https://api.example.com) 허용하기
apiVersion: networking.istio.io/v1beta1
kind: ServiceEntry
metadata:
name: allow-api-example
spec:
hosts:
- "api.example.com"
location: MESH_EXTERNAL
ports:
- number: 443
name: https
protocol: HTTPS
resolution: DNS
설명:
hosts: 접근하려는 외부 도메인location: MESH_EXTERNAL: 메시 외부 서비스임을 명시ports: 연결할 포트와 프로토콜 지정resolution: DNS: DNS 이름으로 라우팅이렇게 등록하면, api.example.com으로 가는 트래픽만 허용되고, 나머지는 모두 차단됩니다.
🍎 3. 실제 흐름 요약
| 설정 항목 | 내용 |
|---|---|
| meshConfig outboundTrafficPolicy.mode | REGISTRY_ONLY로 설정해 외부 차단 |
| ServiceEntry | 필요한 외부 서비스만 허용 등록 |
- 회복탄력성의 중요성 이해 Understanding the importance of resilience
- 클라이언트 측 로드 밸런싱 활용 Leveraging client-side load balancing
- 요청 시간 초과 및 재시도 구현 Implementing request timeouts and retries
- 회로 차단 및 연결 풀링 Circuit breaking and connection pooling
- 마이그레이션 Migrating from application libraries used for resilience
#
git clone https://github.com/AcornPublishing/istio-in-action
cd istio-in-action/book-source-code-master
pwd # 각자 자신의 pwd 경로
code .
# 아래 extramounts 생략 시, myk8s-control-plane 컨테이너 sh/bash 진입 후 직접 git clone 가능
kind create cluster --name myk8s --image kindest/node:v1.23.17 --config - <<EOF
kind: Cluster
apiVersion: kind.x-k8s.io/v1alpha4
nodes:
- role: control-plane
extraPortMappings:
- containerPort: 30000 # Sample Application (istio-ingrssgateway) HTTP
hostPort: 30000
- containerPort: 30001 # Prometheus
hostPort: 30001
- containerPort: 30002 # Grafana
hostPort: 30002
- containerPort: 30003 # Kiali
hostPort: 30003
- containerPort: 30004 # Tracing
hostPort: 30004
- containerPort: 30005 # Sample Application (istio-ingrssgateway) HTTPS
hostPort: 30005
- containerPort: 30006 # TCP Route
hostPort: 30006
- containerPort: 30007 # kube-ops-view
hostPort: 30007
extraMounts: # 해당 부분 생략 가능
- hostPath: /Users/sjkim/Labs/CloudNeta/istio/istio-in-action/book-source-code-master # 각자 자신의 pwd 경로로 설정
containerPath: /istiobook
networking:
podSubnet: 10.10.0.0/16
serviceSubnet: 10.200.1.0/24
EOF
# 설치 확인
docker ps
# 노드에 기본 툴 설치
docker exec -it myk8s-control-plane sh -c 'apt update && apt install tree psmisc lsof wget bridge-utils net-tools dnsutils tcpdump ngrep iputils-ping git vim -y'
# (옵션) kube-ops-view
helm repo add geek-cookbook https://geek-cookbook.github.io/charts/
helm install kube-ops-view geek-cookbook/kube-ops-view --version 1.2.2 --set service.main.type=NodePort,service.main.ports.http.nodePort=30007 --set env.TZ="Asia/Seoul" --namespace kube-system
kubectl get deploy,pod,svc,ep -n kube-system -l app.kubernetes.io/instance=kube-ops-view
## kube-ops-view 접속 URL 확인
open "http://localhost:30007/#scale=1.5"
open "http://localhost:30007/#scale=1.3"
# (옵션) metrics-server
helm repo add metrics-server https://kubernetes-sigs.github.io/metrics-server/
helm install metrics-server metrics-server/metrics-server --set 'args[0]=--kubelet-insecure-tls' -n kube-system
kubectl get all -n kube-system -l app.kubernetes.io/instance=metrics-server
# myk8s-control-plane 진입 후 설치 진행
docker exec -it myk8s-control-plane bash
-----------------------------------
# (옵션) 코드 파일들 마운트 확인
tree /istiobook/ -L 1
혹은
git clone ... /istiobook
# istioctl 설치
export ISTIOV=1.17.8
echo 'export ISTIOV=1.17.8' >> /root/.bashrc
curl -s -L https://istio.io/downloadIstio | ISTIO_VERSION=$ISTIOV sh -
cp istio-$ISTIOV/bin/istioctl /usr/local/bin/istioctl
istioctl version --remote=false
# default 프로파일 컨트롤 플레인 배포
istioctl install --set profile=default -y
# 설치 확인 : istiod, istio-ingressgateway, crd 등
kubectl get istiooperators -n istio-system -o yaml
kubectl get all,svc,ep,sa,cm,secret,pdb -n istio-system
kubectl get cm -n istio-system istio -o yaml
kubectl get crd | grep istio.io | sort
# 보조 도구 설치
kubectl apply -f istio-$ISTIOV/samples/addons
kubectl get pod -n istio-system
# 빠져나오기
exit
-----------------------------------
# istio-proxy 로그 출력 설정 : configmap 에 mesh 바로 아래에 accessLogFile 부분 추가
KUBE_EDITOR="nano" kubectl edit cm -n istio-system istio
...
mesh: |-
accessLogFile: /dev/stdout
...
# 실습을 위한 네임스페이스 설정
kubectl create ns istioinaction
kubectl label namespace istioinaction istio-injection=enabled
kubectl get ns --show-labels
# istio-ingressgateway 서비스 : NodePort 변경 및 nodeport 지정 변경 , externalTrafficPolicy 설정 (ClientIP 수집)
kubectl patch svc -n istio-system istio-ingressgateway -p '{"spec": {"type": "NodePort", "ports": [{"port": 80, "targetPort": 8080, "nodePort": 30000}]}}'
kubectl patch svc -n istio-system istio-ingressgateway -p '{"spec": {"type": "NodePort", "ports": [{"port": 443, "targetPort": 8443, "nodePort": 30005}]}}'
kubectl patch svc -n istio-system istio-ingressgateway -p '{"spec":{"externalTrafficPolicy": "Local"}}'
kubectl describe svc -n istio-system istio-ingressgateway
# NodePort 변경 및 nodeport 30001~30003으로 변경 : prometheus(30001), grafana(30002), kiali(30003), tracing(30004)
kubectl patch svc -n istio-system prometheus -p '{"spec": {"type": "NodePort", "ports": [{"port": 9090, "targetPort": 9090, "nodePort": 30001}]}}'
kubectl patch svc -n istio-system grafana -p '{"spec": {"type": "NodePort", "ports": [{"port": 3000, "targetPort": 3000, "nodePort": 30002}]}}'
kubectl patch svc -n istio-system kiali -p '{"spec": {"type": "NodePort", "ports": [{"port": 20001, "targetPort": 20001, "nodePort": 30003}]}}'
kubectl patch svc -n istio-system tracing -p '{"spec": {"type": "NodePort", "ports": [{"port": 80, "targetPort": 16686, "nodePort": 30004}]}}'
# Prometheus 접속 : envoy, istio 메트릭 확인
open http://127.0.0.1:30001
# Grafana 접속
open http://127.0.0.1:30002
# Kiali 접속 1 : NodePort
open http://127.0.0.1:30003
# (옵션) Kiali 접속 2 : Port forward
kubectl port-forward deployment/kiali -n istio-system 20001:20001 &
open http://127.0.0.1:20001
# tracing 접속 : 예거 트레이싱 대시보드
open http://127.0.0.1:30004
# 접속 테스트용 netshoot 파드 생성
cat <<EOF | kubectl apply -f -
apiVersion: v1
kind: Pod
metadata:
name: netshoot
spec:
containers:
- name: netshoot
image: nicolaka/netshoot
command: ["tail"]
args: ["-f", "/dev/null"]
terminationGracePeriodSeconds: 0
EOF


| 항목 | 클라이언트 사이드 | 서버 사이드 |
|---|---|---|
| 누가 로드밸런싱? | 클라이언트 | 로드밸런서 서버 |
| 장점 | 분산, 낮은 지연 | 단순한 클라이언트 |
| 단점 | 복잡성, 상태 관리 필요 | 병목/지연 가능성 |
| 예시 | Ribbon, Envoy | ELB, Nginx, Istio Gateway |
추가로, Istio는 사실 양쪽 모델을 모두 결합해서 사용해!
→ Envoy 사이드카가 클라이언트 사이드처럼 동작하지만, 중앙 Pilot/Control Plane이 서버사이드처럼 인스턴스 목록을 관리해줌.
| 항목 | 설명 |
|---|---|
| 서비스 디스커버리 | Istiod가 관리 (서버사이드) |
| 로드밸런싱 결정 | Envoy가 직접 (클라이언트사이드) |
| 클라이언트 앱 | 별다른 로드밸런싱 로직 없이 사용 가능 |
| 장점 | - 앱 수정 없이 고급 복원력 기능 적용 가능 - 스케일 아웃/장애 상황에 빠르게 반응 가능 |
[서비스 인스턴스 상태 감지] → [Istiod가 Envoy에게 업데이트 전송] → [Envoy가 로컬에서 로드밸런싱 결정] → [최적의 서버로 직접 요청]

apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: service-b-retry
spec:
hosts:
- service-b.default.svc.cluster.local
http:
- retries:
attempts: 3 # 최대 3번 재시도
perTryTimeout: 2s # 각각의 재시도는 2초 타임아웃
retryOn: gateway-error,connect-failure,refused-stream
route:
- destination:
host: service-b
✅ 설명:
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: service-b-timeout
spec:
hosts:
- service-b.default.svc.cluster.local
http:
- timeout: 5s # 요청 하나당 5초 타임아웃
route:
- destination:
host: service-b
✅ 설명:
apiVersion: networking.istio.io/v1beta1
kind: DestinationRule
metadata:
name: service-b-circuit-breaker
spec:
host: service-b.default.svc.cluster.local
trafficPolicy:
connectionPool:
tcp:
maxConnections: 100
http:
http1MaxPendingRequests: 50
maxRequestsPerConnection: 1
outlierDetection:
consecutive5xxErrors: 5
interval: 10s
baseEjectionTime: 30s
maxEjectionPercent: 50
✅ 설명:
apiVersion: networking.istio.io/v1beta1
kind: DestinationRule
metadata:
name: service-b-failover
spec:
host: service-b.default.svc.cluster.local
trafficPolicy:
loadBalancer:
simple: ROUND_ROBIN
outlierDetection:
consecutive5xxErrors: 2
interval: 5s
baseEjectionTime: 15s
subsets:
- name: primary
labels:
version: v1
- name: secondary
labels:
version: v2
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: service-b-failover-vs
spec:
hosts:
- service-b.default.svc.cluster.local
http:
- route:
- destination:
host: service-b
subset: primary
weight: 100
- destination:
host: service-b
subset: secondary
weight: 0
✅ 설명: