Amazon EKS クラスターの Kubernetes バージョンの更新 - Amazon EKS

Amazon EKS クラスターの Kubernetes バージョンの更新

新しい Kubernetes バージョンが Amazon EKS で利用できるようになると、クラスターを最新バージョンに更新することができます。

重要

新しい Kubernetes バージョンに更新する前に、「Amazon EKS Kubernetes バージョン」とこのトピックの更新ステップの情報を確認することをお勧めします。

新しいバージョンの Kubernetes では大幅な変更が加えられているため、本稼働用クラスターで更新を実行する前に、新しいバージョンの Kubernetes に対してアプリケーションの動作をテストすることをお勧めします。そのためには、継続的な統合ワークフローを作成し、新しい Kubernetes バージョンに移行する前にアプリケーションの動作をエンドツーエンドでテストします。

更新プロセスは、更新された Kubernetes バージョンで新しい API サーバーを起動して既存のバージョンを置き換える Amazon EKS で構成されます。Amazon EKS は、これらの新しいノードでネットワークトラフィックの標準インフラストラクチャと準備状況のヘルスチェックを実行し、予期どおりに動作していることを確認します。これらのヘルスチェックが失敗すると、Amazon EKS はインフラストラクチャのデプロイを元に戻します。クラスターは前の Kubernetes バージョンのままになります。実行中のアプリケーションは影響を受けません。また、クラスターが非決定的または回復不可能な状態のままになることはありません。Amazon EKS は定期的にすべてのマネージド型クラスターをバックアップします。また、必要に応じてクラスターを復元するメカニズムが存在します。Kubernetes インフラストラクチャの管理プロセスは、継続的に評価、改善されています。

クラスターをアップグレードするためには、クラスターの作成時に指定したサブネットから、2~3 の空き IP アドレスが Amazon EKS に必要です。これらのサブネットに使用可能な IP アドレスがない場合、アップグレードが失敗することがあります。さらに、クラスターの作成時に指定されたいずれかのサブネットやセキュリティグループが削除された場合、クラスターのアップグレードが失敗することがあります。

注記

Amazon EKS は可用性の高いコントロールプレーンが実行されますが、更新時にサービスが短時間中断することがあります。たとえば、終了直前または終了直後に新しいバージョンの Kubernetes を実行している新しい API サーバーに接続しようとすると、API コールエラーや接続の問題が発生する可能性があります。この場合は、成功するまで API オペレーションを繰り返し実行します。

Amazon EKS は、クラスターの更新時に Kubernetes アドオンを変更しません。クラスターの更新後、更新後の新しいバージョンの Kubernetes 用に、アドオンを次の表に記載のバージョンに更新することをお勧めします。これを実行するためのステップは、更新手順に含まれています。

Kubernetes バージョン 1.17 1.16 1.15 1.14
Amazon VPC CNI プラグイン 1.6.3 1.6.3 1.6.3 1.6.3
DNS (CoreDNS) 1.6.6 1.6.6 1.6.6 1.6.6
KubeProxy 1.17.7 1.16.12 1.15.11 1.14.9

上記の表に記載されていない追加のアドオンをクラスターに使用する場合は、クラスターの更新後にそれらを最新の互換バージョンに更新します。

既存のクラスターの更新

クラスターと Kubnernetes アドオンを更新します。

既存のクラスターを更新するには

  1. Kubernetes バージョンのクラスターコントロールプレーンと Kubernetes バージョンのノードを比較します。

    • 次のコマンドで、Kubernetes バージョンのクラスターコントロールプレーンを取得します。

      kubectl version --short
    • 以下のコマンドで、Kubernetes バージョンのノードを取得します。

      kubectl get nodes

    ノードがコントロールプレーンよりも古い複数の Kubernetes マイナーバージョンの場合は、クラスターの Kubernetes バージョンを更新する前に、ノードを新しい Kubernetes マイナーバージョンにアップグレードする必要があります。詳細については、Kubernetes ドキュメントの「Kubernetes のバージョンおよびバージョンスキューのサポートポリシー」を参照してください。

    クラスターを更新する前に、ノードをクラスターの現在の更新前の Kubernetes マイナーバージョンに更新することをお勧めします。コントロールプレーンより新しい Kubernetes バージョンをノードで実行しないでください。たとえば、コントロールプレーンでバージョン 1.16 を実行し、ノードでバージョン 1.14 を実行している場合は、クラスターの Kubernetes バージョンを 1.17 に更新する前に、ノードをバージョン 1.15 または 1.16 (推奨) に更新します。詳細については、「セルフマネージド型ワーカーノードの更新」を参照してください。

  2. ポッドセキュリティポリシーのアドミッションコントローラーは、Kubernetes バージョン 1.13 以降を実行している Amazon EKS クラスターに対して有効になります。クラスターを Kubernetes バージョン 1.13 以降にアップグレードする場合は、問題を回避するために、適切なポッドセキュリティポリシーが設定されていることを確認してから、その更新を行います。以下のコマンドを使用して、デフォルトのポリシーを表示できます。

    kubectl get psp eks.privileged

    以下のエラーが表示された場合は、先に進む前に「デフォルトのポッドセキュリティポリシーをインストールまたは復元するには」を参照してください。

    Error from server (NotFound): podsecuritypolicies.extensions "eks.privileged" not found
  3. クラスターを更新します。手順については、クラスターの更新に使用するツールの名前が付いているタブを選択します。

    eksctl

    この手順には、eksctl バージョン 0.24.0 以降が必要です。お使いのバージョンは、以下のコマンドを使用して確認できます。

    eksctl version

    eksctl のインストールまたはアップグレードの詳細については、eksctl のインストールまたはアップグレード を参照してください。

    注記

    この手順は、eksctl で作成されたクラスターに対してのみ機能します。

    以下のコマンドを使用して、Amazon EKS クラスターの Kubernetes バージョンを現在より 1 マイナーバージョン後のバージョンに更新します。dev は実際のクラスター名に置き換えてください。Amazon EKS は可用性の高いコントロールプレーンを実行しているため、一度に更新できるのは 1 マイナーバージョンのみです。この背後にある論理的根拠については、「Kubernetes Version and Version Skew Support Policy (Kubernetes のバージョンおよびバージョンスキューのサポートポリシー)」を参照してください。

    重要

    1.16 に更新するには、事前にデプロイ済みのリソースの一部を更新する必要があります。詳細については、「Kubernetes 1.16 にアップグレードにするための前提条件」を参照してください。いずれかの AWS Fargate ポッドに 1.16 より前の kubelet マイナーバージョンがある場合、1.16 から 1.17 へのクラスターのアップグレードは失敗します。クラスターを 1.16 から 1.17 にアップグレードする場合、クラスターを 1.17 にアップグレードする前に、その kubelet が 1.16 になるように Fargate ポッドをリサイクルする必要があります。

    eksctl upgrade cluster --name dev --approve

    このプロセスが完了するまでに数分かかります。

    AWS マネジメントコンソール
    1. Open the Amazon EKS console at https://console.aws.amazon.com/eks/home#/clusters.

    2. 更新するクラスターの名前を選択し、[Update cluster version (クラスターバージョンの更新)] を選択します。

    3. [Kubernetes version] で、バージョンを選択してクラスターを更新し、[更新] を選択します。

      重要
      • いずれかの AWS Fargate ポッドに 1.16 より前の kubelet マイナーバージョンがある場合、1.16 から 1.17 へのクラスターのアップグレードは失敗します。クラスターを 1.16 から 1.17 にアップグレードする場合、クラスターを 1.17 にアップグレードする前に、Fargate ポッドをリサイクルし、kubelet ポッドを 1.16 にする必要があります。

      • 1.16 に更新するには、事前にデプロイ済みのリソースの一部を更新する必要があります。詳細については、「Kubernetes 1.16 にアップグレードにするための前提条件」を参照してください。

      重要

      Amazon EKS は可用性の高いコントロールプレーンを実行しているため、一度に更新できるのは 1 マイナーバージョンのみです。この背後にある論理的根拠については、「Kubernetes Version and Version Skew Support Policy (Kubernetes のバージョンおよびバージョンスキューのサポートポリシー)」を参照してください。したがって、現在のバージョンが 1.15 で、1.17 にアップグレードする場合は、最初にクラスターを 1.16 にアップグレードし、その後 1.16 から 1.17 にアップグレードする必要があります。1.15 から 1.17 に直接アップデートしようとすると、バージョン更新コマンドからエラーがスローされます。

    4. [クラスター名] にクラスターの名前を入力し、[確認] を選択します。

      注記

      クラスターの更新は、数分で終了します。

    AWS CLI
    1. 次の AWS CLI コマンドを使用して、クラスターを作成します。クラスター名と目的の Kubernetes マイナーバージョンを置き換えます。

      重要

      1.16 に更新するには、事前にデプロイ済みのリソースの一部を更新する必要があります。詳細については、「Kubernetes 1.16 にアップグレードにするための前提条件」を参照してください。いずれかの AWS Fargate ポッドに 1.16 より前の kubelet マイナーバージョンがある場合、1.16 から 1.17 へのクラスターのアップグレードは失敗します。クラスターを 1.16 から 1.17 にアップグレードする場合、クラスターを 1.17 にアップグレードする前に、その kubelet が 1.16 になるように Fargate ポッドをリサイクルする必要があります。

      重要

      Amazon EKS は可用性の高いコントロールプレーンを実行しているため、一度に更新できるのは 1 マイナーバージョンのみです。この背後にある論理的根拠については、「Kubernetes Version and Version Skew Support Policy (Kubernetes のバージョンおよびバージョンスキューのサポートポリシー)」を参照してください。したがって、現在のバージョンが 1.15 で、1.17 にアップグレードする場合は、最初にクラスターを 1.16 にアップグレードし、その後 1.16 から 1.17 にアップグレードする必要があります。1.15 から 1.17 に直接アップデートしようとすると、バージョン更新コマンドからエラーがスローされます。

      aws eks --region region-code update-cluster-version --name prod --kubernetes-version 1.17

      出力:

      { "update": { "id": "b5f0ba18-9a87-4450-b5a0-825e6e84496f", "status": "InProgress", "type": "VersionUpdate", "params": [ { "type": "Version", "value": "1.17" }, { "type": "PlatformVersion", "value": "eks.1" } ], ... "errors": [] } }
    2. 次のコマンドでクラスター更新のステータスをモニタリングします。その際、以前のコマンドで返されたクラスター名と更新 ID を使用します。ステータスが Successful となったら、更新は完了です。

      注記

      クラスターの更新は、数分で終了します。

      aws eks --region region-code describe-update --name prod --update-id b5f0ba18-9a87-4450-b5a0-825e6e84496f

      出力:

      { "update": { "id": "b5f0ba18-9a87-4450-b5a0-825e6e84496f", "status": "Successful", "type": "VersionUpdate", "params": [ { "type": "Version", "value": "1.17" }, { "type": "PlatformVersion", "value": "eks.1" } ], ... "errors": [] } }
  4. クラスターのリージョンと現在の Kubernetes バージョン (この例では 1.17.7) に対応するイメージを使用するには、kube-proxy デーモンセットにパッチを適用します。

    Kubernetes バージョン 1.17 1.16 1.15 1.14
    KubeProxy 1.17.7 1.16.12 1.15.11 1.14.9

    まず、現在の kube-proxy イメージを取得します。

    kubectl get daemonset kube-proxy --namespace kube-system -o=jsonpath='{$.spec.template.spec.containers[:1].image}'

    kube-proxy を推奨バージョンに更新します。これには、前のステップの出力を取得し、バージョンタグを、クラスターに対して推奨される kube-proxy バージョンに置き換えます。

    kubectl set image daemonset.apps/kube-proxy \ -n kube-system \ kube-proxy=602401143452.dkr.ecr.us-west-2.amazonaws.com/eks/kube-proxy:v1.17.7

    アカウント ID とリージョンは、上記の例と異なる場合があります。

  5. クラスターの DNS プロバイダーを確認します。Kubernetes バージョン 1.10 で作成されたクラスターは、デフォルトの DNS およびサービス検出プロバイダーとして kube-dns に付属していました。1.10 クラスターをそれ以降のバージョンに更新し、DNS とサービス検出に CoreDNS を使用する場合は、CoreDNS をインストールして、kube-dns を削除する必要があります。

    クラスターですでに CoreDNS が実行されているかどうかを確認するには、次のコマンドを使用します。

    kubectl get pod -n kube-system -l k8s-app=kube-dns

    出力のポッド名に coredns と示されている場合、CoreDNS はすでにクラスターで実行されています。そうでない場合は、「CoreDNS のインストールまたはアップグレード」を参照してクラスターに CoreDNS をインストールし、推奨バージョンに更新します。次に、ここに戻ってステップ 6~8 をスキップします。

  6. クラスターの coredns デプロイの現在のバージョンを確認します。

    kubectl describe deployment coredns --namespace kube-system | grep Image | cut -d "/" -f 3

    出力:

    coredns:v1.1.3

    対応する Kubernetes バージョンに対して推奨される coredns のバージョンは以下のとおりです。

    Kubernetes バージョン 1.17 1.16 1.15 1.14
    CoreDNS 1.6.6 1.6.6 1.6.6 1.6.6
  7. coredns の現在のバージョンが 1.5.0 以降かつ推奨バージョンより前の場合、このステップをスキップしてください。現在のバージョンが 1.5.0 より前の場合、proxy プラグインではなく forward プラグインを使用するように coredns の設定マップを変更する必要があります。

    1. 次のコマンドを使用して設定マップを開きます。

      kubectl edit configmap coredns -n kube-system
    2. 次の行の proxyforward に置き換えます。ファイルを保存し、エディタを終了します。

      proxy . /etc/resolv.conf
  8. 現在の coredns イメージを取得します。

    kubectl get deployment coredns --namespace kube-system -o=jsonpath='{$.spec.template.spec.containers[:1].image}'
  9. coredns を推奨バージョンに更新します。これには、前のステップの出力を取得し、バージョンタグを、クラスターに対して推奨される coredns バージョンに置き換えます。

    kubectl set image --namespace kube-system deployment.apps/coredns \ coredns=602401143452.dkr.ecr.us-west-2.amazonaws.com/eks/coredns:v1.6.6
  10. クラスターの Amazon VPC CNI Plugin for Kubernetes のバージョンを確認します。次のコマンドを使用して、クラスターの CNI バージョンを出力します。

    kubectl describe daemonset aws-node --namespace kube-system | grep Image | cut -d "/" -f 2

    出力:

    amazon-k8s-cni:1.6.2

    CNI が 1.6.3 より前のバージョンである場合は、以下のうち適切なコマンドを使用して、CNI バージョンを最新の推奨バージョンに更新します。

    • 米国西部 (オレゴン) (us-west-2)

      kubectl apply -f https://raw.githubusercontent.com/aws/amazon-vpc-cni-k8s/release-1.6/config/v1.6/aws-k8s-cni.yaml
    • 中国 (北京) (cn-north-1) または 中国 (寧夏) (cn-northwest-1)

      kubectl apply -f https://raw.githubusercontent.com/aws/amazon-vpc-cni-k8s/release-1.6/config/v1.6/aws-k8s-cni-cn.yaml
    • AWS GovCloud (米国東部) (us-gov-east-1)

      kubectl apply -f https://raw.githubusercontent.com/aws/amazon-vpc-cni-k8s/release-1.6/config/v1.6/aws-k8s-cni-us-gov-east-1.yaml
    • AWS GovCloud (US-West) (us-gov-west-1)

      kubectl apply -f https://raw.githubusercontent.com/aws/amazon-vpc-cni-k8s/release-1.6/config/v1.6/aws-k8s-cni-us-gov-west-1.yaml
    • その他のすべてのリージョンの場合

      • マニフェストファイルをダウンロードします。

        curl -o aws-k8s-cni.yaml https://raw.githubusercontent.com/aws/amazon-vpc-cni-k8s/release-1.6/config/v1.6/aws-k8s-cni.yaml
      • 次のコマンドの region-code をクラスターがあるリージョンに置き換え、変更したコマンドを実行して、ファイル内のリージョンコードを置き換えます (現在 us-west-2)。

        sed -i -e 's/us-west-2/region-code/' aws-k8s-cni.yaml
      • 変更したマニフェストファイルをクラスターに適用します。

        kubectl apply -f aws-k8s-cni.yaml
  11. (オプション) クラスターをアップグレードする前にクラスターに Kubernetes Cluster Autoscaler をデプロイ済みである場合は、アップグレードした Kubernetes メジャーバージョンとマイナーバージョンに一致する最新バージョンに Cluster Autoscaler を更新します。

    1. ウェブブラウザで Cluster Autoscaler リリースページを開き、クラスターの Kubernetes メジャーバージョンとマイナーバージョンに一致する最新の Cluster Autoscaler バージョンを見つけます。たとえば、クラスターの Kubernetes バージョンが 1.17 である場合、1.17 で始まる最新の Cluster Autoscaler リリースを見つけます。次のステップで使用するために、そのリリースのセマンティックバージョン番号 (1.17.n) を書き留めます。

    2. 次のコマンドを使用して、Cluster Autoscaler イメージタグを、前のステップで書き留めたバージョンに設定します。1.17.n は、独自の値に置き換えます。us は、asia または eu に置き換えることができます。

      kubectl -n kube-system set image deployment.apps/cluster-autoscaler cluster-autoscaler=us.gcr.io/k8s-artifacts-prod/autoscaling/cluster-autoscaler:v1.17.n
      注記

      必要とするバージョンによっては、以前のアドレスを gcr.io/google-containers/cluster-autoscaler:v1.n.n に変更する必要があります。イメージアドレスは、リリースページに一覧表示されています。

  12. (GPU ワーカーを含むクラスターのみ) クラスターに GPU 対応のワーカーノードグループ (p3.2xlarge など) がある場合は、以下のコマンドを使用してクラスターの NVIDIA device plugin for Kubernetes デーモンセットを更新する必要があります。

    kubectl apply -f https://raw.githubusercontent.com/NVIDIA/k8s-device-plugin/1.0.0-beta6/nvidia-device-plugin.yml
  13. クラスターの更新が完了したら、同じ Kubernetes バージョンの更新したクラスターにワーカーノードを更新する必要があります。詳細については、「セルフマネージド型ワーカーノードの更新」または「マネージド型ノードグループの更新」を参照してください。Fargate で起動される新しいポッドには、クラスターのバージョンと一致する kubelet バージョンがあります。既存の Fargate ポッドは変更されません。

Kubernetes 1.16 にアップグレードにするための前提条件

Kubernetes 1.15 の変更ログ」と「Deprecated APIs Removed In 1.16: Here’s What You Need To Know」に記述されているように、既存のクラスターがある場合、クラスターを 1.16 にアップグレードする前に、以下のデプロイ済みリソースで API を変更する必要があります。

警告

1.16 にアップグレードする前にこれらの API を変更しないと、アップグレードの完了後にワークロードが失敗します。

  • v1.16 では、NetworkPolicy リソースが extensions/v1beta1 から提供されなくなります。v1.8 以降で利用可能な networking.k8s.io/v1 API に移行してください。既存の永続化データは、networking.k8s.io/v1 API を介して取得できます。

  • v1.16 では、PodSecurityPolicy リソースが extensions/v1beta1 から提供されなくなります。v1.10 以降で利用可能な policy/v1beta1 API に移行してください。既存の永続化データは、policy/v1beta1 API を介して取得できます。

  • v1.16 では、DaemonSet、Deployment、StatefulSet、および ReplicaSet の各リソースが extensions/v1beta1apps/v1beta1、または apps/v1beta2 から提供されなくなります。v1.9 以降で利用可能な apps/v1 APIに移行してください。既存の永続化データは、apps/v1 API を介して取得できます。たとえば、apps/v1beta1 を現在使用している Deployment を変換するには、次のコマンドを入力します。

    kubectl convert -f ./my-deployment.yaml --output-version apps/v1
    注記

    上のコマンドで使用しているデフォルト値は、現在のマニフェストファイルに設定されているデフォルト値とは異なる場合があります。特定のリソースの詳細については、Kubernetes API リファレンスを参照してください。

最初に Kubernetes バージョン 1.11 以前で Amazon EKS クラスターを作成し、kube-proxy DaemonSet から --resource-container フラグを削除していない場合、Kubernetes 1.16 にアップデートすると kube-proxy エラーが発生します。このフラグは Kubernetes 1.16 で廃止されました。詳細については、「Kubernetes 1.16 Deprecations and removals」の「kube-proxy」を参照してください。Kubernetes 1.16 にアップデートする前に、このフラグを削除する必要があります。

1.16 にアップグレードする前に行う必要があること

  • 新しい API を参照するように YAML ファイルを変更します。

  • 新しい API を呼び出すようにカスタムインテグレーションとコントローラーを更新します。

  • 新しい API を呼び出すためのサードパーティー製ツール (イングレスコントローラー、継続的配信システムなど) の最新バージョンを使用していることを確認します。

    クラスターで非推奨の API が使用されているかどうかを簡単に確認するには、audit コントロールプレーンログが有効になっていることを確認し、イベントのフィルターとして v1beta を指定します。すべての代替 API は、Kubernetes バージョン 1.10 より後のバージョンにあります。すべてのサポートされているバージョンの Amazon EKS に搭載されているアプリケーションで、更新済み API を使用できます。

  • クラスターが最初に Kubernetes 1.11 以前を使用してデプロイされていた場合は、kube-proxy DaemonSet から --resource-container="" フラグを削除するか、kube-proxy 設定ファイルを使用します (推奨)。現在のバージョンの kube-proxy にフラグがあるかどうかを確認するには、次のコマンドを入力します。

    kubectl get daemonset kube-proxy --namespace kube-system -o yaml | grep 'resource-container='

    出力がない場合は、何も削除する必要はありません。--resource-container="" のような出力があった場合は、フラグを削除する必要があります。次のコマンドを入力して、現在の kube-proxy 設定を編集します。

    kubectl edit daemonset kube-proxy --namespace kube-system

    エディタを開いた状態で --resource-container="" 行を削除し、ファイルを保存します。代わりに、kube-proxy 設定ファイルの使用を開始することをお勧めします。これを行うには、次のマニフェストをダウンロードします。

    curl -o kube-proxy-daemonset.yaml https://amazon-eks.s3-us-west-2.amazonaws.com/cloudformation/2020-06-10/kube-proxy-daemonset.yaml

    次のコマンドを使用して、クラスターのエンドポイントを特定します。

    aws eks describe-cluster \ --name cluster-name \ --region region-code \ --query 'cluster.endpoint' \ --output text

    出力

    https://A89DBB2140C8AC0C2F920A36CCC6E18C.sk1.region-code.eks.amazonaws.com

    ダウンロードした kube-proxy-daemonset.yaml ファイルを編集します。エディタで、MASTER_ENDPOINT を前のコマンドの出力に置き換えます。REGION をクラスターのリージョンに置き換えます。同じ行で、必要に応じてバージョンをクラスターのバージョンに置き換えます。次のコマンドを使用してファイルを適用します。

    kubectl apply -f kube-proxy-daemonset.yaml