見出し画像

eksctlでEKSを構築・運用する際のTips

現時点(2019/06/28)までで得られたTipsを雑多に載せて見ようかなと思います。

・EKSをeksctlで作成する際はyamlをapplyする形で作る

$ eksctl create cluster -f cluster.yaml

コードで管理できるのでこの形に落ち着いています。以下は使用しているcluster.yamlのsampleになります。

apiVersion: eksctl.io/v1alpha5
kind: ClusterConfig

metadata:
 name: eks-cluster
 region: ap-northeast-1

vpc:
 id: "vpc-xxxxxxxx"
 cidr: "172.0.0.0/16"
 subnets:
   public:
     ap-northeast-1a:
       id: "subnet-xxxxxxxxxxxxxx"
       cidr: "172.0.144.0/22"

     ap-northeast-1c:
       id: "subnet-xxxxxxxxxxxxxx"
       cidr: "172.0.148.0/22"
   private:
     ap-northeast-1a:
       id: "subnet-xxxxxxxxxxxxxx"
       cidr: "172.0.152.0/22"

     ap-northeast-1c:
       id: "subnet-xxxxxxxxxxxxxx"
       cidr: "172.0.156.0/22"

nodeGroups:
 - name: eks-cluster
   instanceType: mixed
   labels:
     type: eks-cluster
   minSize: 1
   desiredCapacity: 2
   ssh:
     allow: true
     publicKeyName: eks-cluster-key
   maxSize: 2
   securityGroups:
     attachIDs: [sg-xxxxxxxxxxxxxx]
   privateNetworking: true
   iam:
     attachPolicyARNs:
       - arn:aws:iam::aws:policy/AmazonS3FullAccess
       - arn:aws:iam::aws:policy/CloudFrontFullAccess
       - arn:aws:iam::aws:policy/AmazonEKSWorkerNodePolicy
       - arn:aws:iam::aws:policy/AmazonEKS_CNI_Policy
     withAddonPolicies:
       autoScaler: true
       ebs: true
       albIngress: true
   instancesDistribution:
     instanceTypes: ["t3.large", "t2.large", "m5.large"]
     onDemandBaseCapacity: 0
     onDemandPercentageAboveBaseCapacity: 0

作成するEKSのネットワークなどを指定しつつ、nodeGroupsの部分でNodeのAutoscaling、sshとそのkey、追加でアタッチするセキュリティグループ、追加でアタッチするIAM Policy、Worker Nodeにスポットインスタンスを使用するのでその設定などを行っています。

・attachPolicyARNsで指定するPolicyはEKSの稼働に必要なPolicyを全て指定する

例えばEKSのWorker Nodeに新しくIAM Policyをアタッチしたい場合で、かつwithAddonPoliciesには存在しないIAM Policyを指定したい場合はattachPolicyARNsを使用して、明示的にIAM PolicyのARNを指定することで作成したWorker Nodeに指定したIAM Policyがアタッチされた状態になります。

ただし注意点があり、attachPolicyARNsを使用した場合、以下のようにデフォルトで付与されるAmazonEKSWorkerNodePolicyとAmazonEKS_CNI_Policyを明示的に指定しておかないとアタッチされなくなります。

   iam:
     attachPolicyARNs:
       - arn:aws:iam::aws:policy/AmazonS3FullAccess
       - arn:aws:iam::aws:policy/CloudFrontFullAccess
       - arn:aws:iam::aws:policy/AmazonEKSWorkerNodePolicy
       - arn:aws:iam::aws:policy/AmazonEKS_CNI_Policy

最初はこれに気づかず、後述のWorker Node入れ替え時に、CNIからのpodへのIPのアサインに失敗してpodがCreateされなくなったりして、割とハマりました。

Worker Nodeの入れ替えが結構大変

様々な理由で現在動作しているWorker Nodeのインスタンスを入れ替える機会があるかと思います。直感的にはeksctlにnodegroupのupdateコマンドのようなものがあって、いい感じにupdateしてほしいものですが、現在そういうものはありません 汗

オペレーションとしては新しいnodegroupをもう一つ追加して、その後古いnodegroupを消すような作業となります。

下記のように一旦追加するもう一つのnodegroupを用意します(Worker Nodeのインスタンス数を2 -> 4に増やすものとします)。

nodeGroups:
 - name: eks-cluster
   instanceType: mixed
   labels:
     type: eks-cluster
   minSize: 1
   desiredCapacity: 2
   ssh:
     allow: true
     publicKeyName: eks-cluster-key
   maxSize: 2
   securityGroups:
     attachIDs: [sg-xxxxxxxxxxxxxx]
   privateNetworking: true
   iam:
     attachPolicyARNs:
       - arn:aws:iam::aws:policy/AmazonS3FullAccess
       - arn:aws:iam::aws:policy/CloudFrontFullAccess
       - arn:aws:iam::aws:policy/AmazonEKSWorkerNodePolicy
       - arn:aws:iam::aws:policy/AmazonEKS_CNI_Policy
     withAddonPolicies:
       autoScaler: true
       ebs: true
       albIngress: true
   instancesDistribution:
     instanceTypes: ["t3.large", "t2.large", "m5.large"]
     onDemandBaseCapacity: 0
     onDemandPercentageAboveBaseCapacity: 0
 - name: eks-cluster1
   instanceType: mixed
   labels:
     type: eks-cluster1
   minSize: 2
   desiredCapacity: 4
   ssh:
     allow: true
     publicKeyName: eks-cluster-key
   maxSize: 4
   securityGroups:
     attachIDs: [sg-xxxxxxxxxxxxxx]
   privateNetworking: true
   iam:
     attachPolicyARNs:
       - arn:aws:iam::aws:policy/AmazonS3FullAccess
       - arn:aws:iam::aws:policy/CloudFrontFullAccess
       - arn:aws:iam::aws:policy/AmazonEKSWorkerNodePolicy
       - arn:aws:iam::aws:policy/AmazonEKS_CNI_Policy
     withAddonPolicies:
       autoScaler: true
       ebs: true
       albIngress: true
   instancesDistribution:
     instanceTypes: ["t3.large", "t2.large", "m5.large"]
     onDemandBaseCapacity: 0
     onDemandPercentageAboveBaseCapacity: 0

nodegroupをcreateします

eksctl create nodegroup --config-file=cluster.yaml

そうするとeks-clusterとeks-cluster1という2つのnodegroupがEKSクラスタにアタッチされた状態になります。

この後古いnodegroupを削除したいですが、podが古いnodegroupのインスタンス上に載ったままなので、このまま削除すると全てのpodが再作成されて新しいNode上で作成されるまでのダウンタイムが発生します。

これを許容できないようであれば、以下のように1台ずつNodeのdrainを行っていきます。

kubectl drain --ignore-daemonsets --delete-local-data ip-172-xx-xxx-xxx.ap-northeast-1.compute.internal
kubectl drain --ignore-daemonsets --delete-local-data ip-172-xx-xxx-xx.ap-northeast-1.compute.internal

drain時のポイントは、もちろん1台ずつ実行していくということと、kubectl get pod -o wide などを使用してpodが新しく作成したNodeに移動することを確認しながら行うことです。

また当然ですが、このオペレーションはpodが2台以上で冗長化されていることが前提です。1台でのみ動作しているpodは再作成されてサービスインするまでのダウンタイムが発生します。

drainが完了し、必要なpodが新しく作成したNodeに移動したことを確認できたら、以下のように古いnodegroupの設定を削除し、新しいnodegroupの設定のみ残します。

nodeGroups:
 - name: eks-cluster1
   instanceType: mixed
   labels:
     type: eks-cluster1
   minSize: 2
   desiredCapacity: 4
   ssh:
     allow: true
     publicKeyName: eks-cluster-key
   maxSize: 4
   securityGroups:
     attachIDs: [sg-xxxxxxxxxxxxxx]
   privateNetworking: true
   iam:
     attachPolicyARNs:
       - arn:aws:iam::aws:policy/AmazonS3FullAccess
       - arn:aws:iam::aws:policy/CloudFrontFullAccess
       - arn:aws:iam::aws:policy/AmazonEKSWorkerNodePolicy
       - arn:aws:iam::aws:policy/AmazonEKS_CNI_Policy
     withAddonPolicies:
       autoScaler: true
       ebs: true
       albIngress: true
   instancesDistribution:
     instanceTypes: ["t3.large", "t2.large", "m5.large"]
     onDemandBaseCapacity: 0
     onDemandPercentageAboveBaseCapacity: 0

以下で削除前の確認を行います。

eksctl delete nodegroup --config-file=cluster.yaml --only-missing

この場合eks-clusterというnodegroupが削除される旨がサジェストされるとおもうので、問題なければ以下で削除を実行します。

eksctl delete nodegroup --config-file=cluster.yaml --only-missing --approve

正直現在のWorker Nodeの入れ替えのオペレーションはかなり手間がかかるものなので、eksctlの新しい機能などで改善されてほしい部分です。

また、よりよい方法があれば教えてほしいです。

以上、特に苦労した部分を記載したつもりですが、eksctlでEKSを構築・運用する際のTipsでした。


この記事が気に入ったらサポートをしてみませんか?