メニュー

Kubernetesボリューム5種とその運用方法

 : Kubernetesのボリュームとは

目次

このページを共有

Yifat Perry
Yifat Perry

Kubernetes のボリュームは、Kubernetes の Pod 内でコンテナーがアクセスできるデータ用ディレクトリです。ディレクトリの場所、基盤となるストレージ媒体、および内容は、ボリュームの種類によって異なります。

Pod 内のコンテナーで実行されるプロセスは、次の要素で構成されるファイルシステムを参照します。

  • コンテナー イメージの内容に一致する ルート ファイルシステム
  • (定義されていれば)コンテナーにマウントされた ボリューム。各ボリュームは、コンテナーのファイルシステム内の特定のパスにマウントされます。

ボリュームは Pod テンプレートの .spec.containers[*].volumeMounts で定義します。各 Pod とその中の各コンテナー イメージについて、どのボリュームをどのパスにマウントするか(パスはコンテナーごとに異なって構いません)を指定する必要があります。

Kubernetes にはさまざまなボリュームの種類があります。主なものは、Kubernetes ノード上にローカル保存され Pod の再起動で削除される「一時(エフェメラル)ボリューム」 と、Pod の停止後もデータを保持する「永続ボリューム(PV)」 です。

Kubernetes ボリュームの 5 種類

Kubernetes は複数種のボリュームをサポートしており、各 Pod は同時に複数のボリューム タイプを利用できます。エフェメラル(短命)ボリュームは Pod のライフサイクルに連動し、永続ボリュームはそのライフサイクルを超えて存続します。つまり、Pod が消滅すると一時ボリュームは破棄されますが、永続ボリュームのデータは保持されます。

永続ボリューム

Kubernetes には、ストレージのプロビジョニングと利用を抽象化する PersistentVolume(永続ボリューム)サブシステム があり、API として PersistentVolume(PV)PersistentVolumeClaim(PVC) の 2 つのリソースで構成されています。

PersistentVolume(PV)

PV はクラスター内のストレージ リソースです。管理者が手動で用意することも、Kubernetes が StorageClass を用いて動的にプロビジョニングすることもできます。PV はボリュームと同様に「プラグイン」ですが、そのライフサイクルはそれを利用する Pod から独立しています。

 PV は API オブジェクトとして、iSCSINFS、クラウド ベンダーのストレージ システムなど、ストレージ実装の詳細を保持します。ノードに似た概念ですが、提供するのは計算資源ではなくストレージ資源です。

PersistentVolumeClaim(PVC)

PVC はユーザーによるストレージ要求です。Pod がノード資源を消費するのと同様に、PVC は PV 資源を消費します。PVC では、必要なストレージ特性を指定でき、サイズやアクセス モード(ReadWriteOnce / ReadWriteMany / ReadOnlyMany)を明示できます。

 PVC により、ユーザーは抽象化されたストレージ資源を利用できますが、ユースケースごとに異なる特性の PV が求められることが一般的です。そこでクラスター管理者は、サイズやアクセス モードだけでなく特性の異なる複数の PV を用意する必要があります。これは、ユーザーに実装詳細を意識させることなく、StorageClass リソースを通じて実現できます。

関連コンテンツ: Kubernetes PVC ガイド

一時(エフェメラル)ボリューム

一時(エフェメラル)ボリュームは、再起動をまたいでデータを恒久的に保持しません。これらのボリュームは Pod のライフサイクルに連動しており、Pod と同時に作成・削除されます。これにより、永続ボリュームの可用性に制約されることなく、Pod を停止して再起動できます。

一時ボリュームは、プロビジョニングと管理が容易で、Pod の仕様内にインラインで指定できます。永続ストレージを必要としないアプリケーション(例:キャッシュ サービス)に最適です。

EmptyDir ボリューム

EmptyDir ボリュームは、Kubernetes が Pod をノードに割り当てたときに作成されます。このボリュームの存続期間は、その特定ノード上で動作する Pod のライフサイクルに連動します。コンテナーが再起動したりクラッシュした場合、EmptyDir ボリューム自体は再作成されますが、Pod がノードから削除・クラッシュ・障害で失われると、このボリューム内のデータは消去され、失われます。

EmptyDir ボリュームを作成した後は、Pod マニフェストでボリューム種別名をフィールドとして宣言できます。ボリュームのプロパティ セクションで、値が空の中括弧 {} として表示されます。EmptyDir ボリュームは主に一時的なデータ保存に適しており、たとえばディスクベースのマージ処理などの一時作業領域として利用できます。

EmptyDir ボリュームは、そのノードの基盤ストレージ上(例:ネットワーク ストレージや SSD)に保存できます。あるいは、emptyDir.medium フィールドで "memory" を指定することも可能です。この場合、Kubernetes は RAM を裏付けとするファイルシステム(tmpfs)をマウントします。なお、ノードが再起動されると Kubernetes は tmpfs を消去する点に注意してください。

Kubernetes hostPath ボリューム

hostPath ボリュームは、ホスト ノードのファイルシステム上のディレクトリまたはファイルを Pod にマウントします。

主なユースケース

  • コンテナーから Docker の内部情報へアクセスする必要がある場合、/var/lib/docker の hostPath を使用する。
  • コンテナー内で cAdvisor を実行するために、/sys の hostPath を使用する。
  • Pod 実行前に特定のホスト パスの存在要件や、自動作成の可否を定義できるよう、Pod に hostPath を指定する。
  • hostPath ボリュームにタイプを指定する(必須のパス指定に加えて設定可能)。

hostPath ボリュームのセキュリティ

hostPath は多くのセキュリティ リスクを伴います。可能な限り使用を避け、やむを得ず使用する場合は、必要最小限のディレクトリ/ファイルのみに限定し、読み取り専用 でマウントしてください。

主なリスク:

  • 認証情報の露出: hostPath により、特権的なシステム認証情報や特権 API が露出する可能性があります。攻撃者に悪用されると、クラスターの他領域への攻撃やコンテナーからの脱出につながり得ます。
  • root 権限の問題: 基盤ホスト上で作成されるディレクトリやファイルは、書き込み可能なのが通常 root のみです。hostPath ボリュームに書き込むには、ホスト側のファイル権限を変更するか、特権コンテナー内でプロセスを root として実行する必要があります。

AdmissionPolicy を用いて、hostPath のアクセス先を特定ディレクトリに制限できます。ただし、このポリシーは、VolumeMounts に読み取り専用マウントの使用を求める 場合にのみ有効性が高まります。

Kubernetes の ConfigMap ボリューム

ConfigMap は、Pod に設定データを挿入するための仕組みです。ConfigMap に保存したデータは ConfigMap ボリューム タイプ で参照でき、Pod 内で動作するコンテナー化アプリケーションから利用できます。ConfigMap を参照する際は、ボリューム定義内でその ConfigMap 名 を指定する必要があります。Kubernetes では、ConfigMap 内の特定エントリに対して マウント先パスをカスタマイズ することも可能です。

Kubernetes ボリューム用ストレージ プラグイン

Kubernetes には、クラスター内で提供されるストレージ デバイスへアクセスするための複数のストレージ プラグインが用意されており、これらは StorageClass オブジェクトを用いて実装されます。

 現在 Kubernetes がサポートする代表的なプラグインには、GCEPersistentDisk、AWSElasticBlockStore、AzureDisk、GlusterFS、NFS、iSCSI などがあります。各プラグインの詳細は StorageClass のドキュメント を参照してください。

ここでは、注目すべき 2 つのストレージ プラグインを詳しく見ていきます。


NFS

Network File System (NFS) は、ストレージ デバイスをローカル ドライブとしてマウントするための標準プロトコルです。Kubernetes では、NFS ボリュームをコンテナー内のローカル ドライブとしてマウントできます。レガシー コードが NFS 経由でデータへアクセスするケースが多いため、レガシー ワークロードを Kubernetes へ移行する際に非常に有用なプラグインです。

NFS と Kubernetes でデータへアクセスする方法は主に 2 つあります。

  • 一時的 NFS ボリューム — 既存の NFS ストレージにアタッチして使用。
  • NFS を用いた PersistentVolume — クラスター上に NFS でアクセスする管理対象リソースを設定可能。

 

CSI

Container Storage Interface (CSI) は、コンテナー オーケストレーターが管理下のコンテナーに対してストレージ システムを利用可能にするための標準インターフェースです。CSI により、ストレージ ベンダーは「アウト・オブ・ツリー」のプラグインを作成できます。これは、プラグインを Kubernetes のコード リポジトリに組み込む必要がなく、Kubernetes 本体に同梱されないことを意味します。

CSI に基づくアウト・オブ・ツリー プラグインは数多く存在し、ストレージ ベンダーから直接提供されています。CSI の導入により、ストレージ技術による Kubernetes への対応は大幅に容易になりました。

関連コンテンツ: Container Storage Interface ガイド

Kubernetes の volumeMounts とは何ですか?

ボリュームを作成し、Pod から利用可能にするには、次の 2 つの手順が必要です。

  1. Pod テンプレートの spec: volumes プロパティで宣言し、Pod をいずれかのノードにデプロイする。
  2. コンテナーの volumeMounts プロパティを用いて、特定のコンテナーにボリュームをマウントする。

これらの手順は常にセットで行います。ボリュームを作成したら、必ずコンテナーにマウントする必要があります。逆に、Pod テンプレートで宣言せずにボリュームをマウントすることはできません。

以下は、Pod テンプレートの YAML 構成で、ボリュームの作成とマウントの両方を示す例です。

spec:   containers:  —name: my-app     image: nginx     volumeMounts:    —name: my-volume       mountPath: /app/config   volumes:  —name: my-volume

このコードでは次のとおりです。

  • volumes(下部)は my-volume という名前のボリュームを作成し、Pod にアタッチします。
  • volumeMounts は、ボリュームをどのパスに・どのようにマウントするか(コンテナー内での利用パスを含む)を定義します。

重要点:ボリューム名は、volumes の宣言と volumeMounts の指定で同一にする必要があります。

Pod をデプロイして Kubernetes ボリュームを作成する

Kubernetes のボリュームを作成するには、そのボリュームを宣言した 1 つ以上の Pod をデプロイします。一般的な方法として、Deployment オブジェクトを使用します。以下は、次の内容を実行する Deployment マニフェストの例です。

  • NGINX コンテナーを持つ Pod を 3 つ デプロイする
  • emptyDir ボリューム を宣言する
  • そのボリュームを 3 つの各コンテナーのルート ディレクトリ にマウントする
     

apiVersion: apps/v1 kind: Deployment metadata:   name: pods-with-volumes spec:   replicas: 3   selector:     matchLabels:       app: demo   template:     metadata:       labels:         app: demo     spec:       containers:      —name: my-container         image: nginx:1.14.2         volumeMounts:        —mountPath: /           name: my-volume       volumes:        —name: my-volume           emptyDir: {}

 

このデプロイメントの名前は「Pods mit Volumes」として定義されています。Kubernetes 環境ではこの名称で参照されます。

前節で見たとおり、この Deployment オブジェクトはボリューム作成に必要な 2 つの処理を行います。

  • spec: template: volumes プロパティでボリュームを宣言する。
  • spec: containers: volumeMounts プロパティでボリュームをコンテナーにマウントする。

この YAML ファイルを my-deployment.yaml という名前で保存したとします。次のコマンドで、Kubernetes クラスターにデプロイメントを作成できます。

kubectl apply -f my-deployment.yaml

デプロイメントが期待どおりのボリューム構成で正常に動作しているか確認するには、次のコマンドを実行します。


kubectl describe pods pods-with-volumes

すべてが正しく機能していれば、出力には各 Pod に my-container という名前のコンテナーが存在し、指定したマウントポイントが設定されていることが示されます。


Mounts:   / from my-volume (rw)

出力には、各 Pod で使用中のボリュームも表示されます。


Volumes:   my-volume:     Type:    EmptyDir (a temporary directory that shares a pod's lifetime)

NetApp Cloud Volumes ONTAP による Kubernetes ボリューム管理

NetApp Cloud Volumes ONTAP は、エンタープライズ向けのリーディング ストレージ管理ソリューションであり、AWS、Azure、Google Cloud 上で安全かつ実績あるストレージ管理サービスを提供します。容量はペタバイト級までスケール可能で、ファイル サービス、データベース、DevOps、その他のエンタープライズ ワークロードなど幅広いユースケースをサポートします。さらに、高可用性、データ保護、ストレージ効率化、Kubernetes 連携など強力な機能を備えています。

特に Cloud Volumes ONTAP は、コンテナ化ワークロード向けの Kubernetes Persistent Volume のプロビジョニングおよび管理要件 をサポートします。

また、Cloud Volumes ONTAP を活用した Kubernetes ワークロードの事例研究 では、コンテナ化アプリケーションの課題解決に Cloud Volumes ONTAP がどのように貢献するかを詳しく紹介しています。

Drift chat loading