CKA를 준비해보자 19일차 - Backup and Restore

0

CKA

목록 보기
19/43

Backup and Restore

kubernetes cluster에 배포되어 있는 pod, service, deployment 등등의 kubernetes resource들을 backup하여 저장하고 싶다면 어떻게해야할까??

이 경우 kube-apiserver에 resource configuration을 요청하는 방식이 있다.

kubectl get all --all-namesapces -o yaml > all-deploy-services.yaml

위 방식은 kubectl get all 명령어를 통해서 cluster에 배포된 resource들의 yaml file을 가져와 all-deploy-services.yaml에 저장하는 방식이다.

이러한 방식 말고도 더 좋은 방법이 있는데, etcd를 backup하는 방식이다. 왜냐하면 kubernetes cluster의 resource들이 모두 etcd에 저장되어 있기 때문이다.

일반적으로 etcd는 각 master node에 있고, 어딘가에 분산 data를 저장한다. 이 분산 data 저장 위치는 etcd.service나 pod manifest의 volume을 통해 얻을 수 있다.

  • etcd.service
ExecStart=/usr/local/bin/etcd \\
    --name ${ETCD_NAME} \\
    ...
    --data-dir=/var/lib/etcd

--data-dir에 표시된 곳이 바로 etcd가 데이터를 저장하는 곳이고, backup의 타겟이되는 위치인 것이다.

etcd pod가 있는 경우는 다음의 통해서 얻을 수 있다.

  • /etc/kubernetes/manifests/etcd.yaml
  volumes:
  ...
  - hostPath:
      path: /var/lib/etcd
      type: DirectoryOrCreate
    name: etcd-data

/var/lib/etcd가 바로 --data-dir에 해당하는 부분인 것이다.

etcd를 backup하는 가장 손쉬운 방법은 snapshot을 사용하는 것이다.

ETCDCTL_API=3 etcdctl snapshot save snapshot.db

현재의 etcd data, 즉 /var/lib/etcd에 있는 data를 snapshot.db라는 스냅샷으로 찍는 것이다.

다음의 명령어의 결과는 아래와 같다.

ls
snapshot.db

snapshot.db가 만들어진 것을 볼 수 있다.

snapshot.db 내부가 어떻게 생겼는 지를 알기위해서는 status를 사용하면 된다.

ETCDCTL_API=3 etcdctl snapshot status snapshot.db

그럼 해당 snapshot을 사용하여 data를 복구하려면 어떻게해야할까?? 먼저 kube-apiserver를 잠시 종료시켜준다.

service kube-apiserver stop

kube-apiserver를 종료시켜주냐면, etcd cluster를 재시작하는데 있어서 kube-apiserveretcd cluster에 의존하고 있어, 재시작 중 에러가 발생할 수 있기 때문이다.

이 다음 etcdctl을 이용하여 data를 복구하도록 한다.

ETCDCTL_API=3 etcdctl snapshot restore snapshot.db --data-dir /var/lib/etcd-from-backup

snapshot.db의 내용을 /var/lib/etcd-from-backup에 복구하도록 한 것이다. 왜 이전 data path가 아니라 새로운 data path를 지정했냐면, 기존의 남아있던 data path와 현재의 복구한 내용이 충돌을 발생시킬 수 있기 때문이다.

위와 같이 --data-dir을 바꾸는 경우는 etcd pod에서 volume에 대한 정의를 --data-dir에서 지시한 곳으로 변경해야한다.

systemctl에서의 etcd.service를 수정하면 된다.

vi /etc/systemd/system/etcd.service

[Service]
User=etcd
Type=notify
ExecStart=/usr/local/bin/etcd \
  --name etcd-server \
  --data-dir=/var/lib/etcd-data \

/var/lib/etcd-data/var/lib/etcd-from-backup으로 바꾸면 된다.

[Service]
User=etcd
Type=notify
ExecStart=/usr/local/bin/etcd \
  --name etcd-server \
  --data-dir=/var/lib/etcd-data-new \

다음과 같이 바꾸고 저장하면 된다.

이제 service daemon을 재시작하고 etcd service를 재시작해주도록 하자.

systemctl daemon-reload
systemctl restart etcd

마지막으로 kube-apiserver를 다시 실행시켜준다.

systemctl kube-apiserver start

이제 우리의 cluster가 정상 작동하면서, 이전의 data를 가지고 있게 된다.

참고로, 위의 방식은 etcd가 외부 설치되었을 때 설정하는 방법이다. 만약 kubernetes master node에 etcd가 설치되었다면, 바로 etcdctl을 통해서 snapshot restore 후에 etcd pod의 volume을 --data-dir로만 바꿔주면 된다. 즉 굳이 service 명령어를 쓸 필요가 없다.

단, mastert node와 etcd가 같이 설치된 경우에는 다음과 같이 pod의 yaml 명세를 바꾸어야 한다.
가령 아래는 etcd pod yaml파일이다. 보통 /etc/kubernetes/manifests/etcd.yaml에 있기 때문에, 이 파일을 직접 바꾸면 반영이 된다.

  volumes:
  ...
  - hostPath:
      path: /var/lib/etcd
      type: DirectoryOrCreate
    name: etcd-data

/var/lib/etcd 이 부분을 --data-dir이 명시하고 있는 /var/lib/etcd-from-backup으로 바꾸어야 한다는 것이다.

  volumes:
  ...
  - hostPath:
      path: /var/lib/etcd-from-backup
      type: DirectoryOrCreate
    name: etcd-data

이렇게 바꾸면 된다.

한 가지 명심할 것은 etcdctlsave를 사용할 때는 etcd에 접근해야하므로 다음과 같이 endpoint와 cert를 설정해주어야 한다.

ETCDCTL_API=3 etcdctl snapshot save snapshot.db \
--endpoints=https://127.0.0.1:2379 \
--cacert=/etc/etcd/ca.crt \
--cert=/etc/etcd/etcd-server.crt \
--key=/etc/etcd/etcd-server.key

만약 위처럼 endpoint, cacert, cery, key를 안써주면 다음과 같은 error가 발생한다.

Error: rpc error: code = Unavailable desc = transport is closing

또한 backup과 restore 기능을 사용하기 위해서 etcdctl은 반드시 3이상의 version을 사용해야하기 때문에 ETCDCTL_API=3을 써주는 것이다.

가령 kubectl describe을 통해 etcd pod의 flag들을 가져와서 다음을 얻었다고 하자.

    Command:
      etcd
      ..
      --cert-file=/etc/kubernetes/pki/etcd/server.crt
      --client-cert-auth=true
      --data-dir=/var/lib/etcd
      ...
      --key-file=/etc/kubernetes/pki/etcd/server.key
      --listen-client-urls=https://127.0.0.1:2379,https://192.30.39.9:2379
      ...
      --trusted-ca-file=/etc/kubernetes/pki/etcd/ca.crt

cert-file, key-file, trusted-ca-file에 해당하는 값들을 etcdctl의 flag에 써주면 된다.

ETCDCTL_API=3 etcdctl snapshot save /opt/snapshot-pre-boot.db \ --endpoints=https://127.0.0.1:2379  \
--cacert=/etc/kubernetes/pki/etcd/ca.crt \ 
--cert=/etc/kubernetes/pki/etcd/server.crt \ 
--key=/etc/kubernetes/pki/etcd/server.key

참고로 --endpointslisten-client-urls의 값으로 생각하면 된다.

마지막으로 etcdctl을 통해서 etcd cluster의 구성을 볼 수 있는데, etcdctl member를 사용하면 된다.

etcdctl member list
 13:54:06 up 56 min,  1 user,  load average: 11.46, 9.75, 9.31
USER     TTY      FROM             LOGIN@   IDLE   JCPU   PCPU WHAT
root     pts/0    192.28.177.9     13:50    6.00s  0.08s  0.00s w

1개의 member로만 이루어진 것을 알 수 있다.

정리하자면 master node에 etcd가 있으면 해당 master node에서 etcdctl을 통해 snapshotsave하는 backup부분과 restore를 모두 할 수 있다. 이후 etcd pod manifest를 수정하여 data path를 변경해주면 자동으로 설정된다.

만약 master node에 etcd가 없으면 외부etcd와 연결된 것이기 때문에, master node에서 etcdctl을 통해서 backup은 가능하지만, restore은 직접 etcd가 있는 외부 서버에 접근하여 etcdctlrestore를 해주어야 한다. 또한, restore 이후에는 systemctletcd.service를 수정하여 data path를 변경해주고 재시작해주어야 한다.

kubectl config

kubernetes cluster는 하나의 host에 여러 개 있을 수 있다. 현재 cluster가 몇 개 있는 지는 다음의 명령어를 통해서 알 수 있다.

kubectl config get-clusters
NAME
cluster1
cluster2

현재 host에 두 개의 cluster가 있는 것을 알 수 있다.

참고로, context 변경을 통해서 kubectl의 타겟이 되는 각 cluster를 변경할 수 있다.

cluster1으로 context를 변경하기 위해서는 다음의 명령어를 사용하면 된다.

kubectl config use-context cluster1
Switched to context "cluster1".

0개의 댓글