brunch

You can make anything
by writing

C.S.Lewis

by Master Seo Sep 28. 2021

EKS 4탄-16. EKS에서 EBS 사용 실습

실습 4탄 =  16/17

Pod가 종료되면 데이터가 모두 사라진다.

Pod가 종료되더라도 데이터가 모두 남아 있게 해보자~

Mysql처럼 컨테이너로 배포가 필요하면 데이터 보존이 필요하다.

Worker node의 로컬볼륨(hostPath)에 보존하면 되나, 경로가 없으면 안된다. 

다른 Node에 배포가 되면, 서비스가 안되므로 퍼시스텐트 볼륨이 필요하다. 

PV - 어느 노드에서도 연결 가능한 볼륨. NFS , EBS 등이 있다.


이미지 출처 : 김태민님 기술 블로그
https://kubetm.github.io/k8s/03-beginner-basic-resource/volume/



<1> Pod에 EBS 연결하기

<2> EBS CSI(PV)와 Statefulsets 사용하기

<3> 실습 1 - EBS CSI 드라이버 설치하기?

<4> Sample app 배포

<5> Reclaim Policy:Retain 실습

<6> 삭제 

<10> 다음~ EKS에서 EFS사용하기




<1> Pod에 EBS 연결하기



1

퍼시스턴트 볼륨 ( Persistent Volume, PV)?

어느 노드에서나 연결이 가능하다.



2

구성?

Pod------PVC(Persistent Volume Claim) -------------Persistent Volume ---------- Volume Local 



3

CSI 드라이버 (Container Storage interface) ?

EKS를 계속 업데이트 못하므로 , 공통의 인터페이스를 만들어 사용한다.



4

스테이트 풀 셋(Stateful Sets)?

쿠버 네티스에서는 상태가 없는 Pod는 가축

특정한 이름을 짓지 않는다.

상태가 있는 Pod는 애완동물로 비유한다.


동작?

Stateful Sets으로 애플리케이션 배포했었다.

Stateful Sets 애플리케이션이 1개 다운 시 , 동일 이름의 애플리케이션이 동일 볼륨에 연결되어 서비스된다.



5

Stateless Application ?

Apache, NGINX, IIS

App1, App2 , App3, App 4  ---------- 모두 Volume 1개 연결



6

Stateful Application?

Database

mongoDB , redis


App1 ---------- Volume1

App2 ---------- Volume2

App3 ---------- Volume3

에서   App3 다운시,  다른 App3에서 Volume3을 연동함.

App3(복제본) ---------- Volume3


스테이트풀셋으로 배포된 Pod는 파드별로 PV(PVC)가 생성 및 연동됨.


이미지 출처 : 김태민님 기술 블로그

https://kubetm.github.io/k8s/03-beginner-basic-resource/volume/




<2> EBS CSI(PV)와 Statefulsets 사용하기


App파드를 1개 배포할때  EBS 사용하고 싶다고 하자.

App파드가 EBS볼륨 gp3에 연결됨.


ebs-csi-controller (pod)에 볼륨 생성한다.

ebs-csi-node(파드)로 연결한다.






<3> 실습 1 - EBS CSI 드라이버 설치하기?


IRSA 필요


1

IRSA가 CSI 드라이버 사용에 필요한  정책 만들기

curl -sSL -o ebs-csi-policy.json https://raw.githubusercontent.com/kubernetes-sigs/aws-ebs-csi-driver/master/docs/example-iam-policy.json


aws iam create-policy --policy-name AmazonEKS_EBS_CSI_Driver_Policy --policy-document file://ebs-csi-policy.json


aws iam delete-policy --policy-arn  xxxxxxxx   

// AmazonEKS_EBS_CSI_Driver_Policy   arn



2

# IRSA 만들고

ACCOUNT_ID=`aws sts get-caller-identity --query 'Account' --output text`

echo $ACCOUNT_ID

echo $CLUSTER_NAME


eksctl create iamserviceaccount --name ebs-csi-controller-irsa --namespace kube-system --cluster $CLUSTER_NAME --attach-policy-arn arn:aws:iam::$ACCOUNT_ID:policy/AmazonEKS_EBS_CSI_Driver_Policy --approve


2021-09-28 08:20:08 [ℹ]  waiting for CloudFormation stack "eksctl-myeks-addon-iamserviceaccount-kube-system-ebs-csi-controller-irsa"

2021-09-28 08:20:24 [ℹ]  waiting for CloudFormation stack "eksctl-myeks-addon-iamserviceaccount-kube-system-ebs-csi-controller-irsa"

2021-09-28 08:20:41 [ℹ]  waiting for CloudFormation stack "eksctl-myeks-addon-iamserviceaccount-kube-system-ebs-csi-controller-irsa"

2021-09-28 08:20:41 [ℹ]  created serviceaccount "kube-system/ebs-csi-controller-irsa"



3

ebs-csi-controller는 디플로이먼트로 배포되어 EBS 볼륨 생성/삭제를 제어

ebs-csi-node는 데몬 셋으로 배포되어 EBS 볼륨을 파드에 탈부착을 제어



4

helm repo에 추가

helm repo add aws-ebs-csi-driver https://kubernetes-sigs.github.io/aws-ebs-csi-driver


업데이트

helm repo update

helm search  repo aws-ebs-csi-driver



5

배포

helm upgrade -install aws-ebs-csi-driver aws-ebs-csi-driver/aws-ebs-csi-driver --namespace kube-system --set image.repository=602401143452.dkr.ecr.$AWS_DEFAULT_REGION.amazonaws.com/eks/aws-ebs-csi-driver --set enableVolumeResizing=true --set enableVolumeSnapshot=true --set controller.serviceAccount.create=false --set controller.serviceAccount.name=ebs-csi-controller-irsa


아래 경고는 무시 해도 된다.

 controller and CRDs will no longer be installed as part of this chart and moving forward will be a prerequisite of using the snap shotting functionality.



6

리전별로 배포 주소가 틀리니 참고

602401143452.dkr.ecr.ap-south-1.amazonaws.com/

https://docs.aws.amazon.com/eks/latest/userguide/add-ons-images.html



7

확인

kubectl get pod -n kube-system -l "app.kubernetes.io/name=aws-ebs-csi-driver,app.kubernetes.io/instance=aws-ebs-csi-driver" -w


NAME                                  READY   STATUS    RESTARTS   AGE

ebs-csi-controller-577c4f47c9-8685h   5/5     Running   0          43s

ebs-csi-controller-577c4f47c9-qzlp9   5/5     Running   0          43s

ebs-csi-node-cb4rv                    3/3     Running   0          43s

ebs-csi-node-d6mwx                    3/3     Running   0          43s

ebs-csi-node-dtfh8                    3/3     Running   0          43s

ebs-csi-node-lbtjt                    3/3     Running   0          43s




<4> Sample app 배포



1

watch -d kubectl get pods,pv,pvc



2

# 배포

git clone https://github.com/kubernetes-sigs/aws-ebs-csi-driver.git


cd aws-ebs-csi-driver/examples/kubernetes/dynamic-provisioning/

tree


[root@eksctl-host dynamic-provisioning]# tree

├── README.md

└── specs

    ├── claim.yaml

    ├── pod.yaml

    └── storageclass.yaml


스토리지클래스,  PVC ,Pod  3 개를 모두 배포 한다.

kubectl apply -f specs/



3

# 확인

kubectl get pvc

(seo-sing-admin@myeks:default) [root@myeks-host dynamic-provisioning]# kubectl get pvc

NAME        STATUS   VOLUME            CAPACITY   ACCESS MODES   STORAGECLASS   AGE

ebs-claim   Bound    pvc-769de143-56f7-4be6-ab70-fede5fb598e5   4Gi        RWO  ebs-sc         19s


kubectl get pods,pv,pvc

kubectl describe storageclass ebs-sc

kubectl get pv | egrep -o pvc-[a-zA-Z0-9-]+

kubectl get pvc ebs-claim 


MyPVC=$(kubectl get pvc ebs-claim -o jsonpath='{.spec.volumeName}')

kubectl describe pv $MyPVC

me:              pvc-769de143-56f7-4be6-ab70-fede5fb598e5

Labels:            <none>

Annotations:       pv.kubernetes.io/provisioned-by: ebs.csi.aws.com

Finalizers:        [kubernetes.io/pv-protection external-attacher/ebs-csi-aws-com]

StorageClass:      ebs-sc

Status:            Bound

Claim:             default/ebs-claim

Reclaim Policy:    Delete

Access Modes:      RWO

VolumeMode:        Filesystem

Capacity:          4Gi

Node Affinity:

  Required Terms:

    Term 0:        topology.ebs.csi.aws.com/zone in [ap-southeast-1c]

Message:

Source:

    Type:              CSI (a Container Storage Interface (CSI) volume source)

    Driver:            ebs.csi.aws.com

    FSType:            ext4

    VolumeHandle:      vol-0562bcca5f3df17b1

    ReadOnly:          false

    VolumeAttributes:      storage.kubernetes.io/csiProvisionerIdentity=1632784924922-8081-ebs.csi.aws.com

Events:                <none>


//

    Term 0:        topology.ebs.csi.aws.com/zone in [ap-southeast-1c]

// Pod가 AZ a에 생성되면  볼륨이 AZ a에 생겨 맞춰주는 옵션?   topology.ebs 토폴로지 옵션 

// Pod가 AZ-a에 생성되면, AZ-a번에서 연결된다로 사전에 설정한다.



4

Pod에 있는 정보를 확인  ?

kubectl get pod app -o json


pod에 data라는 디렉토리에 마운트 된것임

volumes 부분에 persistent-storage라고 나옴.


                "volumeMounts": [

                    {

                        "mountPath": "/data",

                        "name": "persistent-storage"

:

        "volumes": [

            {

                "name": "persistent-storage",

                "persistentVolumeClaim": {

                    "claimName": "ebs-claim"

                }

            },



4

콘솔에서 확인 ?


EC2 > EBS

gp3  - 4 GiB  

연결 인스턴스 확인.  

work node에 연결되어 있음을 확인

i-01105855728ed20c4 (myeks-ng-a8d19dc2-Node):/dev/xvdba (attached)



5

# kubectl get pv -o jsonpath="{.items[*].spec.csi.volumeHandle}"

kubectl get pv -o jsonpath="{.items[0].spec.csi.volumeHandle}" 

MyEbsId=$(kubectl get pv -o jsonpath="{.items[0].spec.csi.volumeHandle}")

aws ec2 describe-volumes --volume-ids $MyEbsId


...

"AvailabilityZone": "ap-northeast-2a",

"Iops": 3000,

"VolumeType": "gp3",

...



6

aws ec2 describe-volume-status --volume-ids $MyEbsId



7

pod에서 실행해보자~

# Verify that the pod is successfully writing data to the volume.

kubectl exec -it app -- cat /data/out.txt

kubectl exec -it app -- sh -c 'mount |grep data'


kubectl exec -it app -- sh -c 'df -hT --type=ext4'

Filesystem     Type  Size  Used Avail Use% Mounted on

/dev/nvme1n1   ext4  3.9G   16M  3.8G   1% /data



8

# 삭제 >> EBS 볼륨은 어떻게 될까? (현재 Reclaim Policy:Delete) 이다

kubectl delete -f specs/

pv, pod 삭제

EBS 볼륩을 삭제하는 옵션이 delete라   EBS 볼륨도 삭제 된다.



9

볼륨을 삭제하는 옵션중 retain으로 하면 EBS 볼륨이 남아 있다.

제약 조건 ?

EBS는 AZ 내에서만 동작한다.

같은 AZ만 동작한다. 

Pod가 다른 AZ에서 생성하면  EBS볼륨이 연결되지 못한다.



10

Pod가 AZ a에 생성되면  볼륨이 AZ a에 생겨 맞춰주는 옵션?

topology.ebs 토폴로지 옵션 

Pod가 AZ-a에 생성되면, AZ-a번에서 연결된다로 사전에 설정한다.




<5>  Reclaim Policy:Retain 실습



1

# 다시 배포

kubectl apply -f specs/



2

MyPVC=$(kubectl get pvc ebs-claim -o jsonpath='{.spec.volumeName}')



3

# Reclaim Policy:Retain 업데이트

kubectl patch pv $MyPVC -p '{"spec":{"persistentVolumeReclaimPolicy": "Retain"}}'

persistentvolume/pvc-aa155928 patched


4

# 다시 삭제 >> EBS 볼륨은 어떻게 될까? (현재 Reclaim Policy:Retain) 이다

kubectl delete -f specs/


볼륨은 남아 있다~



5

콘솔에서 확인하자

EC2 > EBS 




<6> 삭제 


1

드라이버 삭제

helm -n kube-system uninstall aws-ebs-csi-driver



2

iam서비스 어카운트 삭제

eksctl delete iamserviceaccount --cluster $CLUSTER_NAME --namespace kube-system --name ebs-csi-controller-irsa --wait





<10> 다음 = EKS에서 EFS사용하기


https://brunch.co.kr/@topasvga/1902



감사합니다.


매거진의 이전글 EKS 4탄-15. EKS-Fargate 실습
브런치는 최신 브라우저에 최적화 되어있습니다. IE chrome safari