Circuit Breaker๋กœ ๋ฌธ์ œ ์žˆ๋Š” ์›Œํฌ๋กœ๋“œ๋ฅผ ์ œ์™ธ์‹œํ‚ค๊ธฐ ๐Ÿšง

4 minute read

์‚ฌ์ „ ์ค€๋น„

$ kubectl apply -n default -f https://raw.githubusercontent.com/istio/istio/1.20.2/samples/helloworld/helloworld.yaml
service/helloworld created
deployment.apps/helloworld-v1 created
deployment.apps/helloworld-v2 created

์•„ ๊ทธ๋Ÿฐ๋ฐ ์œ„์˜ helloworld v1/v2 ๋‘˜๋‹ค resource limits๊ฐ€ ์•ˆ ๊ฑธ๋ ค ์žˆ์–ด์„œ ์ง์ ‘ k edit deploy๋กœ ์ˆ˜์ •ํ•ด resource limits๋ฅผ ๋„ฃ์–ด์ฃผ์ž. (k edit pod ...์œผ๋กœ ํ•˜๋ ค๊ณ  ํ•˜๋‹ˆ Pod์—์„œ๋Š” resource ์ˆ˜์ •์ด ์•ˆ ๋จ ใ… ใ… )

...
      resources:
        requests:
          cpu: "100m" # default
        limits:
          cpu: "100m"
          memory: "200Mi"
...

๊ทธ๋ฆฌ๊ณ  ๊ฐ ๋ฒ„์ „๋ณ„ K8s svc๋„ ์ถ”๊ฐ€๋กœ deploy ํ•˜์ž.

$ kubectl apply -f - <<EOF
apiVersion: v1
kind: Service
metadata:
  name: helloworld-v1
  labels:
    app: helloworld
    service: helloworld
    version: v1
spec:
  ports:
  - port: 5000
    name: http
  selector:
    app: helloworld
    version: v1
---
apiVersion: v1
kind: Service
metadata:
  name: helloworld-v2
  labels:
    app: helloworld
    service: helloworld
    version: v2
spec:
  ports:
  - port: 5000
    name: http
  selector:
    app: helloworld
    version: v2
EOF
$ kubectl get svc
NAME            TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)    AGE
helloworld      ClusterIP   10.43.135.30    <none>        5000/TCP   ...
helloworld-v1   ClusterIP   10.43.70.96     <none>        5000/TCP   ...
helloworld-v2   ClusterIP   10.43.248.127   <none>        5000/TCP   ...

Helloworld ์›Œํฌ๋กœ๋“œ๋ฅผ ๋ชจ๋‘ ๋””ํ”Œ๋กœ์ด ํ•˜๊ณ  ๋‚˜๋ฉด, ํ…Œ์ŠคํŠธ์šฉ Pod์— ์ ‘์†ํ•ด์„œ ์•„๋ž˜ ๋ช…๋ น์–ด๋ฅผ ๋‚ ๋ฆฌ๋ฉด์„œ ์‘๋‹ต์„ ๋ชจ๋‹ˆํ„ฐ๋ง ํ•˜๊ณ  ์žˆ์ž.

$ k exec ... -it -- sh
~ $ while true; do curl "http://helloworld.default.svc.cluster.local:5000/hello"; done;

Circuit Breaker๋ž€

ํŠธ๋ž˜ํ”ฝ์„ ๋ฐ›๋Š” ์›Œํฌ๋กœ๋“œ ์ง‘ํ•ฉ ์ค‘์— ์žฅ์• ๊ฐ€ ๋ฐœ์ƒํ–ˆ์„ ๋•Œ, ํ•ด๋‹น ์›Œํฌ๋กœ๋“œ๋ฅผ ํŠธ๋ž˜ํ”ฝ ๋ผ์šฐํŒ…์—์„œ ์ œ์™ธํ•จ์œผ๋กœ์จ ๋„คํŠธ์›Œํฌ์˜ ์•ˆ์ •์„ฑ์„ ๋†’์ด๋Š” ํŒจํ„ด์ด๋‹ค.

Istio์—์„œ Network Resiliency(ํƒ„๋ ฅ์„ฑ)๊ณผ Fault Tolerance๋ฅผ ๊ฐ–์ถ”๊ธฐ ์œ„ํ•ด ์‚ฌ์šฉํ•œ๋‹ค.

fortio๋กœ Pod ๋ถ€ํ•˜ ์ƒ์„ฑํ•˜๊ธฐ

์‚ฌ์ „ ์ž‘์—…์—์„œ ๋งŒ๋“ค์–ด๋‘” Helloworld ์›Œํฌ๋กœ๋“œ ์ค‘์— v1์— ๊ฐ•์ œ๋กœ ๋ถ€ํ•˜๋ฅผ ์ค„ ๊ฒƒ์ด๋‹ค. ์ด๋ฅผ ์œ„ํ•ด ๋กœ๋“œ ํ…Œ์ŠคํŠธ ํˆด์ธ fortio๋ฅผ ๋””ํ”Œ๋กœ์ด ํ•˜์ž.

$ kubectl apply -f - <<EOF
apiVersion: v1
kind: Pod
metadata:
  name: fortio
  labels:
    app: fortio
spec:
  containers:
  - image: docker.io/fortio/fortio:latest_release
    imagePullPolicy: IfNotPresent
    name: fortio
    ports:
    - containerPort: 8080
      name: http-fortio
    - containerPort: 8079
      name: grpc-ping
EOF

๊ทธ๋ฆฌ๊ณ  ์•„๋ž˜ ๋ช…๋ น์–ด๋ฅผ ์ž…๋ ฅํ•ด helloworld v1 ์›Œํฌ๋กœ๋“œ์— ๋ถ€ํ•˜๋ฅผ ์ฃผ์ž.

$ kubectl exec -it fortio  -- /usr/bin/fortio load -c 2 -t 30m -qps 0 http://helloworld-v1.default:5000/hello

์ด๋•Œ, -c 2๋Š” concurrent thread 2๊ฐœ์—, -t 30m์€ 30๋ถ„ ๋™์•ˆ, -qps 0์€ ๊ธฐ๋‹ค๋ฆผ ์—†์ด ๊ณ„์† ์š”์ฒญ์„ ๋ณด๋‚ด๋„๋ก ๋งŒ๋“ ๋‹ค.

๊ทธ๋Ÿฌ๋ฉด ์ด์ œ 1์ดˆ๋งˆ๋‹ค curl ๋ณด๋‚ด๋˜๊ฒŒ ๊ธ‰๊ฒฉํžˆ ๋”œ๋ ˆ์ด๊ฐ€ ๊ฑธ๋ฆฌ๊ธฐ ์‹œ์ž‘ํ•œ๋‹ค!!! ๋ฐ˜๋ฉด์— helloworld-v2์—์„œ ์˜ค๋Š” ์‘๋‹ต์€ ๋ฐ”๋กœ๋ฐ”๋กœ ๋ฐ›๊ฒŒ ๋œ๋‹ค.

์‹œ๋ป˜๊ฒŒ์ง„ helloworld-v1โ€ฆ โค๏ธโ€๐Ÿ”ฅ

DestinationRule๋กœ Outlier Detection ์ˆ˜ํ–‰ํ•˜๊ธฐ

์ด์ œ ์ด๋ ‡๊ฒŒ ๋ถ€ํ•˜ ๋•Œ๋ฌธ์— ์žฅ์• ๊ฐ€ ์ƒ๊ธด ์›Œํฌ๋กœ๋“œ๋ฅผ ์ž๋™์œผ๋กœ ์ œ์™ธํ•  ์ˆ˜ ์žˆ๋„๋ก DestinationRule์˜ Outlier Detection ๊ธฐ๋Šฅ์„ ํ†ตํ•ด ๊ตฌํ˜„ํ•ด๋ณด์ž!! ์•„๋ž˜์™€ ๊ฐ™์ด DestinationRule์„ ์ž‘์„ฑํ•ด ๋””ํ”Œ๋กœ์ด ํ•œ๋‹ค.

$ kubectl apply -f - <<EOF
apiVersion: networking.istio.io/v1alpha3
kind: DestinationRule
metadata:
  name: hellowrold
spec:
  host: helloworld.default.svc.cluster.local
  trafficPolicy:
    connectionPool:
      http: # ๋™์‹œ์— ์ ‘์†ํ•  ์ˆ˜ ์žˆ๋Š” connection์„ ์ œํ•œ
        http1MaxPendingRequests: 1
        maxRequestsPerConnection: 1
      tcp:
        maxConnections: 1
    outlierDetection:
      consecutive5xxErrors: 3 # 503 service unavailable
      interval: 1m
      baseEjectionTime: 5m
      maxEjectionPercent: 100
EOF

์ด๋ ‡๊ฒŒ ํ•  ๊ฒฝ์šฐ, helloworld-v1 ์›Œํฌ๋กœ๋“œ์—์„œ connection pool ์ œํ•œ์œผ๋กœ ์ธํ•ด 503์—๋Ÿฌ๋ฅผ ๋ฐ›๊ฒŒ ๋˜๊ณ , ์ฒ˜์Œ์— while ... curl ...๋กœ ๋ณด๋‚ด๋˜ ํ˜ธ์ถœ๋„ ์ด์ œ๋Š” helloworld-v2์˜ ์‘๋‹ต๋งŒ์„ ๋ฐ›๊ฒŒ ๋œ๋‹ค!!

์ฐธ๊ณ ์ž๋ฃŒ