여러 머신 유형에 워크로드 마이그레이션

이 가이드에서는 애플리케이션에 다운타임을 일으키지 않고도 GKE 클러스터에서 실행되는 워크로드를 새로운 노드 집합으로 마이그레이션하는 방법을 보여줍니다. 이러한 마이그레이션은 머신 유형이 다른 노드에 작업 부하를 이전하려는 경우에 유용할 수 있습니다.

배경

노드 풀은 머신 유형(CPU 및 메모리) 승인 범위를 포함하여 모두 동일한 구성을 갖는 머신의 하위 집합입니다. 노드 풀은 클러스터 내의 노드 하위 집합을 나타냅니다. 컨테이너 클러스터는 하나 이상의 노드 풀을 포함할 수 있습니다.

Compute Engine 클러스터의 머신 프로필을 변경해야 할 경우, 새 노드 풀을 만들고 워크로드를 새 노드 풀로 마이그레이션할 수 있습니다.

다운타임 없이 작업 부하를 마이그레이션하려면 다음 작업이 필요합니다.

  • 기존 노드 풀을 예약 불가능으로 표시합니다.
  • 기존 노드 풀에서 실행되는 작업 부하를 배출합니다.
  • 기존 노드 풀을 삭제합니다.

GKE 클러스터의 클러스터 조정 시스템인 Kubernetes는 기존 노드 풀을 배출하면서 삭제된 Pod를 자동으로 새로운 노드 풀로 다시 예약합니다.

시작하기 전에

다음 단계에 따라 Kubernetes Engine API를 사용 설정합니다.
  1. Google Cloud Console에서 Kubernetes Engine 페이지로 이동합니다.
  2. 프로젝트를 만들거나 선택합니다.
  3. API 및 관련 서비스가 사용 설정될 때까지 기다립니다. 몇 분 정도 걸릴 수 있습니다.
  4. Google Cloud 프로젝트에 결제가 사용 설정되어 있는지 확인합니다. 프로젝트에 결제가 사용 설정되어 있는지 확인하는 방법을 알아보세요.

이 가이드에 사용된 다음 명령줄 도구를 설치합니다.

  • gcloud는 Kubernetes Engine 클러스터를 만들고 삭제하는 데 사용됩니다. gcloudGoogle Cloud SDK에 포함되어 있습니다.
  • kubectl은 Kubernetes Engine에서 사용되는 클러스터 조정 시스템인 Kubernetes를 관리하는 데 사용됩니다. gcloud를 사용하여 kubectl을 설치할 수 있습니다.
    gcloud components install kubectl

gcloud 명령줄 도구의 기본값 설정

gcloud 명령줄 도구에서 프로젝트 IDCompute Engine 영역 옵션을 입력하는 시간을 절약하려면 기본값을 설정하면 됩니다.
gcloud config set project project-id
gcloud config set compute/zone compute-zone

1단계: GKE 클러스터 만들기

첫 번째 단계는 애플리케이션 워크로드를 실행하도록 컨테이너 클러스터를 만드는 것입니다. 다음 명령어는 기본 머신 유형을 사용하고 5개의 노드가 있는 새 클러스터를 만듭니다(n1-standard-1).

gcloud container clusters create migration-tutorial --num-nodes=5

2단계: 복제된 애플리케이션 배포 실행

다음 명령어는 샘플 웹 애플리케이션 컨테이너 이미지의 6 복제본 배포를 만듭니다.

kubectl run web --image=gcr.io/google-samples/hello-app:1.0 \
  --replicas=6 --limits='cpu=100m,memory=80Mi'

다음을 실행하여 시작된 Pod 목록을 검색할 수 있습니다.

kubectl get pods
출력:
NAME                   READY     STATUS    RESTARTS   AGE
web-2212180648-80q72   1/1       Running   0          10m
web-2212180648-jwj0j   1/1       Running   0          10m
web-2212180648-pf67q   1/1       Running   0          10m
web-2212180648-pqz73   1/1       Running   0          10m
web-2212180648-rrd3b   1/1       Running   0          10m
web-2212180648-v3b18   1/1       Running   0          10m

3단계: 대형 머신 유형의 노드 풀 만들기

기본적으로 GKE는 모든 새 클러스터의 default-pool 노드 풀을 만듭니다.

gcloud container node-pools list --cluster migration-tutorial
결과:
NAME          MACHINE_TYPE   DISK_SIZE_GB  NODE_VERSION
default-pool  n1-standard-1  100           1.5.7

다른 [머신 유형] 또는 다른 인증 범위와 같은 다른 구성의 인스턴스를 사용하려면 새로운 노드 풀을 만들어야 합니다.

다음 명령어는 larger-pool라는 새 노드 풀을 만듭니다. 이 노드 풀에는 n1-highmem-2 머신 유형의 높은 메모리 인스턴스가 5개 있습니다. (GKE 기본 값인 n1-standard-1보다 큰 머신 유형).

gcloud container node-pools create larger-pool \
  --cluster=migration-tutorial \
  --machine-type=n1-highmem-2 \
  --num-nodes=5

이제 컨테이너 클러스터에 노드 풀 두 개가 포함됩니다.

gcloud container node-pools list --cluster migration-tutorial
출력:
NAME          MACHINE_TYPE   DISK_SIZE_GB  NODE_VERSION
default-pool  n1-standard-1  100           1.5.7
larger-pool   n1-highmem-2   100           1.5.7

GKE 클러스터에 추가된 새 노드 풀 인스턴스를 볼 수 있습니다.

kubectl get nodes
결과:
NAME                                                STATUS    AGE       VERSION
gke-migration-tutorial-default-pool-56e3af9a-059q   Ready     40m       v1.5.7
gke-migration-tutorial-default-pool-56e3af9a-0ng4   Ready     40m       v1.5.7
gke-migration-tutorial-default-pool-56e3af9a-k6jm   Ready     40m       v1.5.7
gke-migration-tutorial-default-pool-56e3af9a-lkrv   Ready     40m       v1.5.7
gke-migration-tutorial-default-pool-56e3af9a-p9j4   Ready     40m       v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-2rhk    Ready     4m        v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-4bb2    Ready     4m        v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-7fl0    Ready     4m        v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-cx9q    Ready     4m        v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-hs6p    Ready     4m        v1.5.7

4단계: 워크로드 마이그레이션

새 노드 풀을 생성한 뒤에도 워크로드는 여전히 default-pool에서 실행됩니다. Kubernetes는 Pod가 실행 중이고 사용 가능한 상태일 때 Pod를 다시 예약하지 않습니다.

다음 명령어를 실행하여 포드가 실행 중인 노드를 확인합니다(NODE 열 확인).

kubectl get pods -o=wide
출력:
NAME                          READY     STATUS    IP         NODE
web-2212180648-80q72          1/1       Running   10.8.3.4   gke-migration-tutorial-default-pool-56e3af9a-k6jm
web-2212180648-jwj0j          1/1       Running   10.8.2.5   gke-migration-tutorial-default-pool-56e3af9a-0ng4
web-2212180648-pf67q          1/1       Running   10.8.4.4   gke-migration-tutorial-default-pool-56e3af9a-lkrv
web-2212180648-pqz73          1/1       Running   10.8.2.6   gke-migration-tutorial-default-pool-56e3af9a-0ng4
web-2212180648-rrd3b          1/1       Running   10.8.4.3   gke-migration-tutorial-default-pool-56e3af9a-lkrv
web-2212180648-v3b18          1/1       Running   10.8.1.4   gke-migration-tutorial-default-pool-56e3af9a-p9j4

이러한 Pod를 새로운 노드 풀로 마이그레이션하기 위해서는 다음 단계를 수행해야 합니다.

  1. 기존 노드 풀 차단: 이 작업은 기존 노드 풀(default-pool)에 있는 노드를 예약 불가능으로 표시합니다. 이를 예약 불가능으로 표시한 다음에는 Kubernetes가 이러한 노드에 대한 새 Pod 예약을 중지합니다.

  2. 기존 노드 풀 배출: 이 작업은 기존 노드 풀(default-pool)의 노드에서 실행 중인 워크로드를 정상적으로 제거합니다.

위 단계를 수행하면 기존 노드 풀에서 실행 중인 Pod가 정상적으로 종료되고 Kubernetes가 이를 다른 사용 가능한 노드에 다시 예약합니다. 이 경우, 사용 가능한 유일한 노드는 3단계에서 만든 larger-pool의 노드뿐입니다.

Kubernetes가 애플리케이션을 정상적으로 종료하도록 하려면, 컨테이너가 SIGTERM 신호를 처리해야 합니다. 이 신호를 사용하면 클라이언트에 대한 활성 연결을 닫고 데이터베이스 트랜잭션을 깨끗한 방식으로 커밋하거나 중단할 수 있습니다. Pod의 컨테이너를 중단하기 전 Pod 매니페스트에서 spec.terminationGracePeriodSeconds 필드를 사용하여 Kubernetes의 대기 시간을 지정할 수 있습니다. 기본값은 30초입니다. pod 종료에 대한 자세한 내용은 Kubernetes 문서를 참조하세요.

먼저 default-pool의 노드를 차단합니다. 다음 명령어를 실행하여 이 노드 풀에 있는 노드 목록을 가져올 수 있습니다.

kubectl get nodes -l cloud.google.com/gke-nodepool=default-pool

그런 다음 이전 명령어에서 얻은 이름인 NODE로 대체된 kubectl cordon NODE를 실행해 각 노드를 차단합니다. 다음 명령어는 각 노드의 작업을 반복하고 예약 불가능으로 표시합니다.

for node in $(kubectl get nodes -l cloud.google.com/gke-nodepool=default-pool -o=name); do
  kubectl cordon "$node";
done
결과:
node "gke-migration-tutorial-default-pool-56e3af9a-059q" cordoned
node "gke-migration-tutorial-default-pool-56e3af9a-0ng4" cordoned
node "gke-migration-tutorial-default-pool-56e3af9a-k6jm" cordoned
node "gke-migration-tutorial-default-pool-56e3af9a-lkrv" cordoned
node "gke-migration-tutorial-default-pool-56e3af9a-p9j4" cordoned

이제 노드 목록에서 default-pool 노드가 SchedulingDisabled 상태로 변경된 것을 확인할 수 있습니다.

kubectl get nodes
결과:
NAME                                                STATUS                     AGE       VERSION
gke-migration-tutorial-default-pool-56e3af9a-059q   Ready,SchedulingDisabled   1h        v1.5.7
gke-migration-tutorial-default-pool-56e3af9a-0ng4   Ready,SchedulingDisabled   1h        v1.5.7
gke-migration-tutorial-default-pool-56e3af9a-k6jm   Ready,SchedulingDisabled   1h        v1.5.7
gke-migration-tutorial-default-pool-56e3af9a-lkrv   Ready,SchedulingDisabled   1h        v1.5.7
gke-migration-tutorial-default-pool-56e3af9a-p9j4   Ready,SchedulingDisabled   1h        v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-2rhk    Ready                      1h        v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-4bb2    Ready                      1h        v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-7fl0    Ready                      1h        v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-cx9q    Ready                      1h        v1.5.7
gke-migration-tutorial-larger-pool-b8ec62a6-hs6p    Ready                      1h        v1.5.7

그런 다음 각 노드에서 Pod를 정상적으로 배출합니다. 배출을 수행하려면 각 노드에서 Pod를 제거하는 kubectl drain 명령어를 사용합니다.

NODEkubectl cordon 명령어에 전달된 동일한 이름 목록으로 대체하여 kubectl drain --force NODE를 실행할 수 있습니다.

다음 셸 명령어는 할당된 정상 종료 시간 10초를 사용하여 Pod를 제거하는 방식으로 default-pool에서 각 노드를 반복하여 배출합니다.

for node in $(kubectl get nodes -l cloud.google.com/gke-nodepool=default-pool -o=name); do
  kubectl drain --force --ignore-daemonsets --delete-local-data --grace-period=10 "$node";
done

이 명령어가 완료되면 이제 Pod가 larger-pool 노드에서 실행되는 것을 볼 수 있습니다.

kubectl get pods -o=wide
결과:
NAME                   READY     STATUS    IP         NODE
web-2212180648-3n9hz   1/1       Running   10.8.9.4   gke-migration-tutorial-larger-pool-b8ec62a6-cx9q
web-2212180648-88q1c   1/1       Running   10.8.7.4   gke-migration-tutorial-larger-pool-b8ec62a6-2rhk
web-2212180648-dlmjc   1/1       Running   10.8.9.3   gke-migration-tutorial-larger-pool-b8ec62a6-cx9q
web-2212180648-hcv46   1/1       Running   10.8.5.4   gke-migration-tutorial-larger-pool-b8ec62a6-hs6p
web-2212180648-n0nht   1/1       Running   10.8.6.4   gke-migration-tutorial-larger-pool-b8ec62a6-7fl0
web-2212180648-s51jb   1/1       Running   10.8.8.4   gke-migration-tutorial-larger-pool-b8ec62a6-4bb2

5단계: 이전 노드 풀 삭제

Kubernetes가 web 배포의 모든 Pod를 larger-pool로 다시 예약한 다음에는 default-pool이 더 이상 필요하지 않으므로 안전하게 삭제할 수 있습니다. 다음 명령어를 실행하여 default-pool을 삭제합니다.

gcloud container node-pools delete default-pool --cluster migration-tutorial

이 작업이 완료되면 컨테이너 클러스터에 단일 노드 풀인 larger-pool만 있어야 합니다.

gcloud container node-pools list --cluster migration-tutorial
결과:
NAME          MACHINE_TYPE   DISK_SIZE_GB  NODE_VERSION
larger-pool   n1-highmem-2   100           1.5.7

삭제

이 가이드에서 사용한 리소스 비용이 Google Cloud Platform 계정에 청구되지 않도록 하는 방법은 다음과 같습니다.

  • 컨테이너 클러스터 삭제: 이 단계에서는 컴퓨팅 인스턴스, 디스크, 네트워크 리소스와 같이 컨테이너 클러스터를 구성하는 리소스를 삭제합니다.

    gcloud container clusters delete migration-tutorial

다음 단계