kubernetesのhostPath
ボリュームは、クラスタノードのディレクトリをコンテナにマウントする機能です。
k3sなど開発環境のローカルクラスタで、コンテナ内からワーキングディレクトリにアクセスしたいケースに使えます。
基本的な設定
volumes.[].hostPath
にノードのディレクトリを指定します。
apiVersion: apps/v1
kind: StatefulSet
spec:
template:
spec:
volumes:
- name: working-dir
hostPath:
path: /opt
type: Directory
containers.[].volumeMounts
に参照設定を記述します。
mountPath
はコンテナ内のディレクトリです。
apiVersion: apps/v1
kind: StatefulSet
spec:
template:
spec:
containers:
- name: sample-container
volumeMounts:
- name: working-dir
mountPath: /root
パーミッションの考慮
ディレクトリの参照設定は、volumes
とcontainers.[].volumeMounts
で設定できます。
hostPath
は、アクセスパーミッションの不整合によりコンテナ内でファイルが開けないといったトラブルが起きやすい環境でもあります。
コンテナ内ではrootまたはイメージ作成者が追加したユーザーが実行する一方、ホストはOSがセットアップした別体系のユーザーが実行しており、相互のパーミッション体系に関連がないためです。
containers.[].securityContext
のrunAsUser
やrunAsGroup
を設定するとコンテナ内の実行ユーザーを変更できます。
ユーザーIDをホストのユーザーIDに合わせると、ファイルパーミッションをホスト環境に合わせられます。
apiVersion: apps/v1
kind: StatefulSet
spec:
template:
spec:
containers:
- name: sample-container
securityContext:
runAsUser: 5000
runAsGroup: 5000
ホストのユーザーID・グループIDはOS環境とセットアップにより異なるため、ホストのid
コマンドや/etc/passwd
などで確認します。
runAsUser
で指定したユーザーはコンテナ内に存在しないケースも多くありますが、存在しないユーザーでコンテナ実行できるケースが多々あります。
コンテナ内ユーザーの考慮
runAsUser
とrunAsGroup
を指定するとホストのファイルパーミッションに沿ったアクセスの問題は概ね解消するでしょう。
一方、非rootの独自ユーザーをセットアップしているイメージの場合、実行ユーザーが変わってしまうとコンテナ内のファイルにアクセスできなくなります。
このケースの緩和策としては、runAsUser
を指定せずrunAsGroup
のみ指定する手があります。
コンテナ内のファイルは、イメージ作成時のユーザーIDで概ねアクセスできます。
hostPath
でマウントしたファイルについては、runAsGroup
で指定したグループIDでアクセスする挙動になります。
775
や664
といった一般的なファイルパーミッションのリソースの場合、グループIDが一致すればアクセス可能です。
より込み入ったセットアップの場合、Unixアカウントとパーミッションの挙動を理解のうえ、さらに詳細な調整が必要になるでしょう。
ただし、そこまで複雑なセットアップとなると実用的とは言いにくい状況でもあります。
Chuma Takahiro