AWS EKS MetricsServer + VPA + CAS 설정하기
이 문서는 AWS EKS Cluster AutoScaler 도입과 관련한 문서입니다.
다수의 글을 참고하여 AWS EKS Cluster에 AutoScaler를 적용하기 위한 A to Z 설정법을 다루고 있습니다.
개요
이 문서에서는 단순하게 배포되어 있는 K8S 환경에 확장성을 더하는 법을 배우게 될 것입니다. 이 문서에서 저희는 NGINX를 확장성 있게 배포하기 위해 다음의 3가지 차트를 사용하게 됩니다.
Metrics Server / metrics-server/metrics-server
VPC Controller / autoscaler/vertical-pod-autoscaler
CAS / cluster-autoscaler-
Metrics
K8s에서 다양항 Pod 확장 전략을 선택하기 위해서는 참고할 지표(Metric)이 필요합니다.
이번 장에서는 Metric이 필요한 이유부터 실제로 Metrics 수집 도구인 metrics-server를 사용해서 지표를 수집하는 방법을 알아봅니다.
Metrics Server 필요한 이유
Metrics Addons 비교
Metrics Server 설치하기
Metrics 필요한 이유
Metrics Server는 2가지 역할을 합니다.
HPA(Horizontal Pod Autoscaler)가 Pod를 스케일 인, 아웃 처리하기 위한 파드 매트릭 수집
kubectl top 명령어를 수행하기 위한 노드 매트릭 수집
EKS Cluster에서 kubectl top 명령어를 사용하면 아래와 같은 오류가 발생합니다.
$ kubectl top node error: Metrics API not available
$ kubectl top pod error : Metrics API not available
이 경우, EKS 클러스터에
metrics-server
가 미설치된 상태라 메트릭을 수집할 수 없어서 발생하는 문제입니다.— younsl (blog) | metrics-server helm chart
Metrics Addons 비교
Metrics Server 역할을 할 수 있는 애드온은 2가지가 존재합니다.
kube-state-metrics / 모든 k8s object에 대한 정보 수집
metrics-server / resource metrics api 등의 제한적인 범위만 수집
Metrics Server 설치하기
Helm Repository 추가하기
$ helm repo add metrics-server https://kubernetes-sigs.github.io/metrics-server/ $ helm repo list $ helm repo update
Helm Pakcage 가져오기
$ helm pull metrics-server/metrics-server
values.yaml 파일 작성하기
# PrivateECR 권장 image: repository: registry.k8s.io/metrics-server/metrics-server tag: "" pullPolicy: IfNotPresent # HA replicas: 2 imagePullSecrets: [] nameOverride: "" fullnameOverride: "" serviceAccount: create: true annotations: {} name: "" secrets: [] rbac: create: true pspEnabled: false apiService: create: true annotations: {] insecureSkipTLSVerify: true caBundle: "" commonLables: {} podLabels: {} podAnnotations: {} podSecurityContext: {} securityContext: allowPrivilegeEscalation: false readOnlyRootFilesystem: true runAsNonRoot: true runAsUser: 1000 priorityClassName: system-cluster-critical containerPort: 10250 hostNetwork: enabled: false updateStrategy: {} podDisruptionBudget: # https://kubernetes.io/docs/tasks/run-application/configure-pdb/ enabled: false minAvailable: maxUnavailable: defaultArgs: - --cert-dir=/tmp - --kubelet-preferred-address-types=InternalIP,ExternalIP,Hostname - --kubelet-use-node-status-port - --metric-resolution=15s args: [] livenessProbe: httpGet: path: /livez port: https scheme: HTTPS initialDelaySeconds: 0 periodSeconds: 10 failureThreshold: 3 readinessProbe: httpGet: path: /readyz port: https scheme: HTTPS initialDelaySeconds: 20 periodSeconds: 10 failureThreshold: 3 service: type: ClusterIP port: 443 annotations: {} labels: {} addonResizer: enabled: false image: repository: registry.k8s.io/autoscaling/addon-resizer tag: 1.8.14 resources: limits: cpu: 40m memory: 25Mi requests: cpu: 40m memory: 25Mi nanny: cpu: 20m extraCpu: 1m extraMemory: 2Mi memory: 15Mi minClusterSize: 10 pollPeriod: 300000 threshold: 5 metrics: enabled: false serviceMonitor: enabled: false additionalLabels: {} interval: 1m scrapeTimeout: 10s metricRelabelings: [] relabelings: [] # See https://github.com/kubernetes-sigs/metrics-server#scaling resources: {} extraVolumeMounts: [] extraVolumes: [] nodeSelector: {} tolerations: [] affinity: {} topologySpreadConstraints: [] # Annotations to add to the deployment deploymentAnnotations: {} schedulerName: ""
Metrics Server Relaese 하기
helm update \ --install metrics-server metrics-server/metrics-server \ --namespace kube-system \ --values. values.yaml \ --wait
Metrics Server Release 체크하기
helm status metrics-server -n kube-system
Metirc Server Pods 체크하기
kubectl get all \ -l app.kubernetes.io/instance=metrics-server \ -n kube-system
Pod Scaler
Pod Scaler가 필요한 이유
Pod Scaler의 종류
Pod Scaler 별 사용 사례 및 분석
HPA 설치하기…
VPA, KEDA
Pod Scaler가 필요한 이유
사용자 활동에 따라서 Pod를 늘렸다가 줄였다가 하는 것은 비효율적입니다.
따라서 이를 자동으로 늘어나고 줄어들게 하는 것이 바로 Pod Scaler입니다.
Pod Scaler의 종류
Pod Scaler는 크게 다음의 3가지가 존재합니다.
HPA(Horizontal Pod Autoscaler)/ 지표에 따라서 pods의 수량 조절
VPA(Vertical Pod Autoscaler) / 지표에 따라서 pods의 CPU, MEM 등 제한 조절
KEDA(Kubernetes Event Driven Autoscaler) / 이벤트 기반으로 HPA+VPA수행
Pod Scaler 별 사용 사례 및 특징 분석
구분 | HPA | VPA | KEDA |
---|---|---|---|
방향 | 수평 | 수직 | 수평/수직 |
트리거 | 리소스 활용 지표 | 리소스 활용도 측정 | 외부/내부 트리거 기반 |
사용 사례 | 애플리케이션 로드 또는 트래픽 패턴 변화 처리 | 과잉 프로비저닝 방지를 위해서 리소스 활용도 최적화 | 이벤트(SQS, HTTP Reqeust) 기반 |
복잡성 | 간단한 | 복잡험 | 매우 복잡함 |
지원되는 워크로드 | Stateless Workload | All kind of Workload | Stateless/Stateful |
K8s 리소스 통합 | Deployment, ReplicaSet, StatefulSet | Deployment, | + |
도구 | metrics-server ++ | metrics-server와 VPA 내부 요소와 통합 | KEDA Controller & EventSource 필요 |
HPA 설치하기…
기존에 서비스를 배포하기 위해서 작성한 Helm Chart안에 조건부로 HPA를 활성화하는 항목을 추가하면, 이를 바로 사용할 수 있을 것 같습니다.
Manifest 파일이므로 간단한 설명이나 감 정도만 잡는데 사용할 것입니다.
— SpectroCloud (Blog) | Kubernetes autoscaling patterns: HPA, VPA and KEDA
HPA 설치하기
apiVersion: autoscaling/v2 kind: HorizontalPodAutoscaler metadata: name: <APP_NAME> spec: scaleTargetRef: apiVersion: apps/v1 kind: Deployment name: <APP_NAME> minReplicas: 2 maxReplicas: 10 metrics: - type: Resource resource: name: cpu target: type: Utilization averageUtilization: 50
HPA 부하 테스트하기
kubectl expoase deployment <APP_NAME> \ --port=80 \ --type=ClusterIP \ --name=nginx-service kubectl run \ --it \ --rm load-generator \ --image=busybox /bin/sh while true; do wget -q -O- http://nginx-service:80; done
HPA 모니터링
kubectl get hpa kubectl get deployment <APP_NAME>
VPA,KEDA
VPA, KEDA는 별도 문서에서 다루겠습니다.
Node Scaler
Node Scaler가 필요한 이유
Node Scaler의 종류
CAS(Cluster AutoScaler) 설치하기
Node Scaler가 필요한 이유
Pod Scaler를 통해서 확장성을 갖추더라도 근본적으로 Node의 수량은 변하지 않습니다.
따라서 Node의 수량을 늘리고 줄일 수 있는 Node Scaler가 필요합니다.
이를 통해서 다음과 같은 이점을 누릴 수 있습니다.
자동 확장 및 축소
비용 효율성
성능 유지
Node Scaler의 종류
Node Scaler에는 다음과 같이 2가지 종류가 존재합니다.
AWS CAS(Cluster Autoscaler)
Karpenter
이 중에서 더 고도화되고 빠른 확장성을 자랑하는 것은 Karpenter입니다.
하지만 이 문서에서는 AWS CAS(Cluster Autoscaler)를 다룰 예정입니다.
CAS(Cluster AutoScaler) 설치하기
AWS CAS Repository 등록하기
$ helm repo add autoscaler https://kubernetes.github.io/autoscaler $ helm repo update autoscaler
AWS CAS Helm Chart Package 가져오기
$ helm pull autoscaler/cluster-autoscaler
values-dev.yaml 수정하기
# https://github.com/terraform-aws-modules/terraform-aws-eks/issues/801#issuecomment-696733518clusterName: <CLUSTER_NAME> nodeSelector: <NODE_SELECTOR> awsRegion: <AWS_REGION> rbac: serviceAccount: name: cluster-autosclaer annotations: # IRSA Options add...
AWS CAS Helm Chart Release 하기
$ helm upgrade cluster-autoscaler autoscaler/cluster-autoscaler \ --install -f values.yaml \ --namespace kube-system $ helm upgrade cluster-autoscaler autoscaler/cluster-autoscaler \ --f values.yaml \ --namespace kube-system
참고 자료
metrics-server
pod scaler (hpa, vpa, keda)
node scaler (cas, karpenter)