Amazon EKS에서 영구 스토리지를 사용하려면 어떻게 해야 합니까?

최종 업데이트 날짜: 2021년 7월 19일

Amazon Elastic Kubernetes Service(Amazon EKS)에서 영구 스토리지를 사용하고 싶습니다.

간략한 설명

다음 옵션 중 하나를 사용하여 Amazon EKS에서 영구 스토리지를 설정할 수 있습니다.

이러한 옵션 중 하나를 사용하려면 다음 단원 중 하나의 단계를 완료하세요.

  • 옵션 A: Amazon EBS CSI 드라이버 배포 및 테스트
  • 옵션 B: Amazon EFS CSI 드라이버 배포 및 테스트

참고: 이 문서의 명령에는 kubectl 버전 1.14 이상이 필요합니다. 사용 중인 kubectl의 버전을 확인하려면 다음 명령을 실행하세요.

kubectl version --client --short

참고: AWS Command Line Interface(AWS CLI) 명령을 실행할 때 오류가 발생하는 경우 최신 버전의 AWS CLI를 사용하고 있는지 확인하세요.

해결 방법

두 섹션 중 하나의 단계를 완료하기 전에 다음을 수행해야 합니다.

1.    AWS CLI를 설치합니다.

2.    정책을 생성하여 Amazon EKS 작업자 노드 역할 CSI Driver Role에 연결하기 위한 AWS Identity and Access Management(IAM) 권한을 설정합니다.

3.    Amazon EKS 클러스터를 생성하고 작업자 노드를 클러스터에 조인합니다.

참고: 작업자 노드가 클러스터에 연결되어 있는지 확인하려면 kubectl get nodes 명령을 실행합니다.

옵션 A: Amazon EBS CSI 드라이버 배포 및 테스트

Amazon EBS CSI 드라이버 배포:

1.    작업자 노드가 Amazon EBS 볼륨을 생성 및 수정할 수 있도록 허용하는 권한이 있는 예제 IAM 정책을 다운로드합니다.

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

2.    Amazon_EBS_CSI_Driver라는 IAM 정책을 생성합니다.

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

3.    클러스터의 OIDC 공급자 URL을 확인합니다.

aws eks describe-cluster --name your_cluster_name --query "cluster.identity.oidc.issuer" --output text

참고: 3단계에서 your_cluster_name을 클러스터 이름으로 바꿉니다.

4.    다음 IAM 신뢰 정책 파일을 생성합니다.

cat <<EOF > trust-policy.json
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {
        "Federated": "arn:aws:iam::YOUR_AWS_ACCOUNT_ID:oidc-provider/oidc.eks.YOUR_AWS_REGION.amazonaws.com/id/<XXXXXXXXXX45D83924220DC4815XXXXX>"
      },
      "Action": "sts:AssumeRoleWithWebIdentity",
      "Condition": {
        "StringEquals": {
          "oidc.eks.YOUR_AWS_REGION.amazonaws.com/id/<XXXXXXXXXX45D83924220DC4815XXXXX>:sub": "system:serviceaccount:kube-system:ebs-csi-controller-sa"
        }
      }
    }
  ]
}
EOF

참고: 4단계에서 YOUR_AWS_ACCOUNT_ID를 계정 ID로 바꿉니다. YOUR_AWS_REGION을 해당 AWS 리전으로 대체합니다. XXXXXXXXXX45D83924220DC4815XXXXX를 3단계에서 반환된 값으로 바꿉니다.

5.    IAM 역할을 생성합니다.

aws iam create-role \
  --role-name AmazonEKS_EBS_CSI_DriverRole \
  --assume-role-policy-document file://"trust-policy.json"

6.    새 IAM 정책을 역할에 연결합니다.

aws iam attach-role-policy \
--policy-arn arn:aws:iam::111122223333:policy/AmazonEKS_EBS_CSI_Driver_Policy \
--role-name AmazonEKS_EBS_CSI_DriverRole

7.    Amazon EBS CSI 드라이버를 배포하려면 리전에 따라 다음 명령 중 하나를 실행합니다.

중국 리전을 제외한 모든 리전:

kubectl apply -k "github.com/kubernetes-sigs/aws-ebs-csi-driver/deploy/kubernetes/overlays/stable/?ref=master"

베이징 및 닝샤 중국 리전:

kubectl apply -k "github.com/kubernetes-sigs/aws-ebs-csi-driver/deploy/kubernetes/overlays/stable-cn/?ref=master"

8.    ebs-csi-controller-sa Kubernetes 서비스 계정에 이전에 생성한 IAM 역할의 Amazon 리소스 이름(ARN)으로 주석을 답니다.

kubectl annotate serviceaccount ebs-csi-controller-sa \
  -n kube-system \
  eks.amazonaws.com/role-arn=arn:aws:iam::YOUR_AWS_ACCOUNT_ID:role/AmazonEKS_EBS_CSI_DriverRole

참고: YOUR_AWS_ACCOUNT_ID를 계정 ID로 바꿉니다.

9.    드라이버 Pod를 삭제합니다.

kubectl delete pods \
  -n kube-system \
  -l=app=ebs-csi-controller

참고: 역할에 할당된 IAM 정책의 IAM 권한으로 드라이버 Pod가 자동으로 재배포됩니다. 자세한 내용은 Amazon EBS CSI 드라이버를 참조하세요.

Amazon EBS CSI 드라이버를 테스트합니다.

동적 프로비저닝을 사용하는 애플리케이션으로 Amazon EBS CSI 드라이버를 테스트할 수 있습니다. Amazon EBS 볼륨은 온디맨드로 프로비저닝됩니다.

1.    AWS GitHub에서 aws-ebs-csi-driver 리포지토리를 복제합니다.

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

2.    작업 디렉터리를 Amazon EBS 드라이버 테스트 파일이 포함된 폴더로 변경합니다.

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

3.    테스트에 필요한 Kubernetes 리소스를 생성합니다.

kubectl apply -f specs/

참고: kubectl 명령은 StorageClass(Kubernetes 웹 사이트 출처), PersistentVolumeClaim (PVC)(Kubernetes 웹 사이트 출처) 및 Pod를 생성합니다. Pod는 PVC를 참조합니다. Amazon EBS 볼륨은 Pod가 생성될 때만 프로비저닝됩니다.

4.    ebs-sc 스토리지 클래스를 설명합니다.

kubectl describe storageclass ebs-sc

5.    기본 네임 스페이스에서 Pod를 보고 app Pod의 상태가 Running으로 변경될 때까지 기다립니다. 예를 들면 다음과 같습니다.

kubectl get pods --watch

6.    PVC를 참조하는 Pod로 인해 생성된 영구 볼륨을 확인합니다.

kubectl get pv

7.    영구 볼륨에 대한 정보를 확인합니다.

kubectl describe pv your_pv_name

참고: your_pv_name을 이전 6단계에서 반환된 영구 볼륨의 이름으로 바꿉니다. 출력에서 Source.VolumeHandle 속성의 값은 계정에 생성된 물리적 Amazon EBS 볼륨의 ID입니다.

8.    Pod가 볼륨에 데이터를 쓰고 있는지 확인합니다.

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

참고: 명령 출력은 /data/out.txt 파일에 저장된 현재 날짜와 시간을 표시합니다. 파일에는 일, 월, 날짜 및 시간이 포함됩니다.

옵션 B: Amazon EFS CSI 드라이버 배포 및 테스트

CSI 드라이버를 배포하기 전에 CSI 드라이버의 서비스 계정이 사용자를 대신하여 AWS API를 호출할 수 있도록 허용하는 IAM 역할을 생성합니다.

1.    GitHub에서 IAM 정책 문서를 다운로드합니다.

curl -o iam-policy-example.json https://raw.githubusercontent.com/kubernetes-sigs/aws-efs-csi-driver/v1.2.0/docs/iam-policy-example.json

2.    IAM 정책을 생성합니다.

aws iam create-policy \
    --policy-name AmazonEKS_EFS_CSI_Driver_Policy \
    --policy-document file://iam-policy-example.json

3.    Kubernetes 서비스 계정에 IAM 역할 ARN으로, IAM 역할에 Kubernetes 서비스 계정 이름으로 주석으로 답니다. 예를 들면 다음과 같습니다.

aws eks describe-cluster --name your_cluster_name --query "cluster.identity.oidc.issuer" --output text

참고: 3단계에서 your_cluster_name을 클러스터 이름으로 바꿉니다.

4.    다음 IAM 신뢰 정책을 생성한 다음 Kubernetes 서비스 계정에 AssumeRoleWithWebIdentity 작업을 부여합니다. 예를 들면 다음과 같습니다.

cat <<EOF > trust-policy.json
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": {
        "Federated": "arn:aws:iam::YOUR_AWS_ACCOUNT_ID:oidc-provider/oidc.eks.YOUR_AWS_REGION.amazonaws.com/id/<XXXXXXXXXX45D83924220DC4815XXXXX>"
      },
      "Action": "sts:AssumeRoleWithWebIdentity",
      "Condition": {
        "StringEquals": {
          "oidc.eks.YOUR_AWS_REGION.amazonaws.com/id/<XXXXXXXXXX45D83924220DC4815XXXXX>:sub": "system:serviceaccount:kube-system:efs-csi-controller-sa"
        }
      }
    }
  ]
}
EOF

참고: 4단계에서 YOUR_AWS_ACCOUNT_ID를 계정 ID로 바꿉니다. YOUR_AWS_REGION을 해당 AWS 리전으로 바꿉니다. XXXXXXXXXX45D83924220DC4815XXXXX를 3단계에서 반환된 값으로 바꿉니다.

5.    IAM 역할을 생성합니다.

aws iam create-role \
  --role-name AmazonEKS_EFS_CSI_DriverRole \
  --assume-role-policy-document file://"trust-policy.json"

6.    새 IAM 정책을 역할에 연결합니다.

aws iam attach-role-policy \
  --policy-arn arn:aws:iam::<AWS_ACCOUNT_ID>:policy/AmazonEKS_EFS_CSI_Driver_Policy \
  --role-name AmazonEKS_EFS_CSI_DriverRole

7.    생성한 IAM 역할의 ARN으로 주석이 추가된 Kubernetes 서비스 계정을 생성합니다. 예를 들면 다음과 같습니다.

cat << EOF > efs-service-account.yaml
---
apiVersion: v1
kind: ServiceAccount
metadata:
  name: efs-csi-controller-sa
  namespace: kube-system
  labels:
    app.kubernetes.io/name: aws-efs-csi-driver
  annotations:
    eks.amazonaws.com/role-arn: arn:aws:iam::YOUR_AWS_ACCOUNT_ID:role/AmazonEKS_EFS_CSI_DriverRole
EOF

참고: YOUR_AWS_ACCOUNT_ID를 계정 ID로 바꿉니다.

8.    매니페스트를 적용합니다.

kubectl apply -f efs-service-account.yaml

Amazon EFS CSI 드라이버를 배포합니다.

Amazon EFS CSI 드라이버를 사용하면 ReadWriteMany 모드를 사용하여 여러 Pod를 동시에 볼륨에 쓸 수 있습니다.

1.    Amazon EFS CSI 드라이버를 배포하려면 리전 또는 클러스터 유형에 따라 다음 명령 중 하나를 실행합니다.

중국 리전을 제외한 모든 리전:

kubectl apply -k "github.com/kubernetes-sigs/aws-efs-csi-driver/deploy/kubernetes/overlays/stable/ecr/?ref=release-1.1"

베이징 및 닝샤 중국 리전:

kubectl apply -k "github.com/kubernetes-sigs/aws-efs-csi-driver/deploy/kubernetes/overlays/stable/?ref=release-1.1"

클러스터에 AWS Fargate Pod만 포함된 경우(노드 없음) 다음 명령(모든 리전)을 사용하여 드라이버를 배포합니다.

kubectl apply -f https://raw.githubusercontent.com/kubernetes-sigs/aws-efs-csi-driver/master/deploy/kubernetes/base/csidriver.yaml

2.    Amazon EKS 클러스터에 대한 VPC ID를 가져옵니다.

aws eks describe-cluster --name your_cluster_name --query "cluster.resourcesVpcConfig.vpcId" --output text

참고: 2단계에서 your_cluster_name을 클러스터 이름으로 바꿉니다.

3.    VPC 클러스터에 대한 CIDR 범위를 가져옵니다.

aws ec2 describe-vpcs --vpc-ids YOUR_VPC_ID --query "Vpcs[].CidrBlock" --output text

참고: 3단계에서, YOUR_VPC_ID를 이전 2단계의 VPC ID로 바꿉니다.

4.    Amazon EFS 탑재 지점에 대한 인바운드 네트워크 파일 시스템(NFS) 트래픽을 허용하는 보안 그룹을 생성합니다.

aws ec2 create-security-group --description efs-test-sg --group-name efs-sg --vpc-id YOUR_VPC_ID

참고: YOUR_VPC_ID를 이전 2단계의 출력으로 바꿉니다. 나중에 사용하기 위해 GroupId를 저장합니다.

5.    VPC의 리소스가 Amazon EFS 파일 시스템과 통신할 수 있도록 NFS 인바운드 규칙을 추가합니다.

aws ec2 authorize-security-group-ingress --group-id sg-xxx --protocol tcp --port 2049 --cidr YOUR_VPC_CIDR

참고: YOUR_VPC_CIDR을 이전 3단계의 출력으로 바꿉니다. sg-xxx를 이전 4단계의 보안 그룹 ID로 바꿉니다.

6.    Amazon EKS 클러스터에 대한 Amazon EFS 파일 시스템을 생성합니다.

aws efs create-file-system --creation-token eks-efs

참고: 나중에 사용하기 위해 FileSystemId를 저장합니다.

7.    Amazon EFS용 탑재 대상을 생성하려면 다음 명령을 실행합니다.

aws efs create-mount-target --file-system-id FileSystemId --subnet-id SubnetID --security-group sg-xxx

중요: 작업자 노드가 실행 중인 가용 영역에서 SubnetID를 사용하여 모든 가용 영역에 대해 다음 명령을 실행해야 합니다. FileSystemId를 Amazon EFS 파일 시스템을 생성했던 이전 6단계의 출력으로 바꿉니다. sg-xxx를 보안 그룹을 생성했던 이전 4단계의 출력으로 바꿉니다. SubnetID를 작업자 노드에서 사용하는 서브넷으로 바꿉니다. 여러 서브넷에 탑재 대상을 생성하려면 각 서브넷 ID에 대해 7단계의 명령을 별도로 실행해야 합니다. 작업자 노드가 실행 중인 각 가용 영역에 탑재 대상을 생성하는 것이 가장 좋습니다.

참고: 작업자 노드가 시작되는 모든 가용 영역에 대해 탑재 대상을 생성할 수 있습니다. 그러면 탑재 대상이 있는 가용 영역의 모든 Amazon Elastic Compute Cloud(Amazon EC2) 인스턴스가 파일 시스템을 사용할 수 있습니다.

이제 Amazon EFS 파일 시스템 및 그 탑재 대상이 실행 중이며 클러스터의 Pod에서 사용할 준비가 되었습니다.

Amazon EFS CSI 드라이버 테스트:

동일한 파일에 쓰는 두 개의 Pod를 배포하여 Amazon EFS CSI 드라이버를 테스트할 수 있습니다.

1.    AWS GitHub에서 aws-efs-csi-driver 리포지토리를 복제합니다.

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

2.    작업 디렉터리를 Amazon EFS CSI 드라이버 테스트 파일이 포함된 폴더로 변경합니다.

cd aws-efs-csi-driver/examples/kubernetes/multiple_pods/

3.    이전에 생성한 Amazon EFS 파일 시스템 ID를 검색합니다.

aws efs describe-file-systems --query "FileSystems[*].FileSystemId" --output text

참고: 3단계 명령에서 두 개 이상의 결과가 반환될 경우 이전에 저장한 Amazon EFS 파일 시스템 ID를 사용할 수 있습니다.

4.    specs/pv.yaml 파일에서 spec.csi.volumeHandle 값을 이전 단계의 Amazon EFS FileSystemId로 바꿉니다.

5.    테스트에 필요한 Kubernetes 리소스를 생성합니다.

kubectl apply -f specs/

참고: 이전 5단계의 kubectl 명령은 Amazon EFS 스토리지 클래스, PVC, 영구 볼륨 및 두 개의 Pod(app1app2)를 생성합니다.

6.    기본 네임 스페이스에 영구 볼륨을 나열하고 default/efs-claim 클레임이 있는 영구 볼륨을 찾습니다.

kubectl get pv -w

7.    영구 볼륨을 설명합니다.

kubectl describe pv efs-pv

8.    두 개의 Pod가 파일에 데이터를 쓰고 있는지 테스트합니다.

kubectl exec -it app1 -- tail /data/out1.txt 
kubectl exec -it app2 -- tail /data/out1.txt

1분 정도 기다리세요. 출력은 두 개의 Pod에서 /data/out1.txt에 작성된 현재 날짜를 보여 줍니다.


이 문서가 도움이 되었나요?


결제 또는 기술 지원이 필요하세요?