非推奨の Kubernetes API

Kubernetes は API ドリブンなシステムであり、API は問題領域の進化する理解を反映して時間とともに進化します。これは、システムとその API 全体で一般的なプラクティスです。進化する API の重要な部分は、API の変更がどのように実装されるかをユーザーに知らせるための適切な非推奨ポリシーとプロセスです。つまり、API の利用者は、API が削除または変更されるリリースを事前に知っておく必要があります。これにより、サプライズや利用者への破壊的な変更がなくなります。

Kubernetes の非推奨ポリシーは、Kubernetes が API バージョンの変更をどのように処理するかを説明しています。非推奨に関するポリシーでは、非推奨の発表後、API バージョンがサポートされる期間が規定されています。したがって、非推奨の発表を認識し、API バージョンが削除される時期を把握して、影響を最小限に抑えることが重要です。

これは、Kubernetes 1.16 で非推奨の API バージョンが削除されることについての発表の例であり、リリースの数ヶ月前に告知されました。これらの API バージョンは、これも事前に非推奨として発表されていたはずです。これは、API バージョンサポートについて利用者に知らせるための適切なポリシーが整備されていることを示しています。

Helm テンプレートは、Kubernetes マニフェストファイルと同様に、Kubernetes オブジェクトを定義する際にKubernetes API グループを指定します。これは、テンプレートのapiVersionフィールドに指定され、Kubernetes オブジェクトのAPI バージョンを識別します。つまり、Helm ユーザーとチャートメンテナーは、Kubernetes API バージョンが非推奨になり、どの Kubernetes バージョンで削除されるかを認識する必要があります。

チャートメンテナー

Kubernetes のバージョンで非推奨または削除される Kubernetes API バージョンをチェックして、チャートを監査する必要があります。サポート対象外またはサポート対象外になることが判明した API バージョンは、サポートされているバージョンに更新し、チャートの新しいバージョンをリリースする必要があります。API バージョンは、kindapiVersionフィールドで定義されます。たとえば、Kubernetes 1.16 で削除されたDeploymentオブジェクトのAPI バージョンを以下に示します。

apiVersion: apps/v1beta1
kind: Deployment

Helm ユーザー

使用するチャート(チャートメンテナーと同様)を監査し、Kubernetes のバージョンで非推奨または削除される API バージョンを含むチャートを特定する必要があります。特定されたチャートについては、サポートされている API バージョンを含むチャートの最新バージョンを確認するか、自分でチャートを更新する必要があります。

さらに、展開されたチャート(つまり、Helm リリース)を監査し、非推奨または削除された API バージョンがないか再度確認する必要があります。これは、helm get manifestコマンドを使用してリリースの詳細を取得することで実行できます。

サポートされている API に Helm リリースを更新する方法は、以下の調査結果によって異なります。

  1. 非推奨の API バージョンのみが見つかった場合
  • サポートされている Kubernetes API バージョンを含むチャートのバージョンでhelm upgradeを実行します。
  • アップグレードの説明を追加します。この現在のバージョンより前の Helm バージョンにはロールバックしないようにするなどの記述を追加します。
  1. Kubernetes のバージョンで削除された API バージョンが見つかった場合
  • API バージョンがまだ使用可能な Kubernetes バージョンを実行している場合(たとえば、Kubernetes 1.15 を実行していて、Kubernetes 1.16 で削除される API を使用していることがわかった場合)
    • 手順1の手順に従います。
  • それ以外の場合(たとえば、helm get manifestによって報告された一部のAPIバージョンが既に使用できないKubernetesバージョンを実行している場合)

注:サポートされている API を使用して Helm リリースを更新する場合は、サポートされている API を含むリリースバージョンより前のバージョンにリリースをロールバックしないでください。

推奨事項:ベストプラクティスは、それらの API バージョンを削除する Kubernetes クラスタにアップグレードする前に、非推奨の API バージョンを使用するリリースをサポートされている API バージョンにアップグレードすることです。

上記のようにリリースを更新しないと、Kubernetes のバージョンでその API バージョンが削除されているリリースをアップグレードしようとすると、次のエラーが発生します。

Error: UPGRADE FAILED: current release manifest contains removed kubernetes api(s)
for this kubernetes version and it is therefore unable to build the kubernetes
objects for performing the diff. error from kubernetes: unable to recognize "":
no matches for kind "Deployment" in version "apps/v1beta1"

このシナリオでは、Helm は現在の展開済みリリース(この Kubernetes バージョンで削除された Kubernetes API を含む)と、更新/サポートされた API バージョンを含むチャートとの間の差分パッチを作成しようとするときに失敗します。失敗の根本的な理由は、Kubernetes が API バージョンを削除すると、Kubernetes Go クライアントライブラリは非推奨のオブジェクトを解析できなくなり、したがって、ライブラリを呼び出すときに Helm が失敗することです。残念ながら、Helm はこの状況から回復できず、そのようなリリースを管理できなくなります。リリースマニフェストのAPIバージョンの更新で、このシナリオからの回復方法の詳細を参照してください。

リリースマニフェストの API バージョンの更新

マニフェストは、クラスタの Secret(デフォルト)または ConfigMap の data フィールドに格納されている Helm リリースオブジェクトのプロパティです。data フィールドには、base64 エンコードされた gzip 圧縮オブジェクトが含まれています(Secret の場合は、追加の base64 エンコードがあります)。リリースのネームスペースには、リリースバージョン/リビジョンごとに Secret/ConfigMap があります。

Helm のmapkubeapisプラグインを使用して、サポートされている API にリリースの更新を実行できます。詳細については、README を確認してください。

または、次の手動手順に従って、リリースマニフェストの API バージョンの更新を実行できます。構成によっては、Secret または ConfigMap バックエンドの手順に従います。

  • 最新に展開されたリリースに関連付けられた Secret または ConfigMap の名前を取得します。
    • Secrets バックエンド:kubectl get secret -l owner=helm,status=deployed,name=<release_name> --namespace <release_namespace> | awk '{print $1}' | grep -v NAME
    • ConfigMap バックエンド:kubectl get configmap -l owner=helm,status=deployed,name=<release_name> --namespace <release_namespace> | awk '{print $1}' | grep -v NAME
  • 最新に展開されたリリースの詳細を取得します。
    • Secrets バックエンド:kubectl get secret <release_secret_name> -n <release_namespace> -o yaml > release.yaml
    • ConfigMap バックエンド:kubectl get configmap <release_configmap_name> -n <release_namespace> -o yaml > release.yaml
  • 何か問題が発生した場合に復元するために、リリースをバックアップしてください。
    • cp release.yaml release.bak
    • 緊急時における復元: kubectl apply -f release.bak -n <release_namespace>
  • リリースオブジェクトのデコード
    • Secrets バックエンド: cat release.yaml | grep -oP '(?<=release: ).*' | base64 -d | base64 -d | gzip -d > release.data.decoded
    • ConfigMap バックエンド: cat release.yaml | grep -oP '(?<=release: ).*' | base64 -d | gzip -d > release.data.decoded
  • マニフェストのAPIバージョンの変更。変更を行うには、任意のツール(例:エディタ)を使用できます。これは、デコードされたリリースオブジェクト(release.data.decoded)のmanifestフィールドにあります。
  • リリースオブジェクトのエンコード
    • Secrets バックエンド: cat release.data.decoded | gzip | base64 | base64
    • ConfigMap バックエンド: cat release.data.decoded | gzip | base64
  • デプロイされたリリースファイル(release.yaml)内のdata.releaseプロパティの値を、新しいエンコードされたリリースオブジェクトに置き換えます。
  • ネームスペースへのファイル適用: kubectl apply -f release.yaml -n <release_namespace>
  • サポートされている Kubernetes API バージョンを含むチャートのバージョンでhelm upgradeを実行します。
  • アップグレードの説明を追加します。この現在のバージョンより前の Helm バージョンにはロールバックしないようにするなどの記述を追加します。