Kubernetes に democratic-csi を入れて、TrueNAS に自動的にPVを作ってもらうようにした
democratic-csi とは
GitHub - democratic-csi/democratic-csi: csi storage for container orchestration systems より
democratic-csi implements the csi (container storage interface) spec providing storage for various container orchestration systems (ie: Kubernetes).
The current focus is providing storage via iscsi/nfs from zfs-based storage systems, predominantly FreeNAS / TrueNAS and ZoL on Ubuntu.
The current drivers implement the depth and breadth of the csi spec, so you have access to resizing, snapshots, clones, etc functionality.
意訳) democratic-csi とは、Kubernetes の中で PersistentVolume リソースを要求する PersistentVolumeClaim を定義されたときに、自動的に TrueNAS や FreeNAS 等の NAS 上で対応するボリュームを作成して iSCSI や NFS 経由で Export & Mount して、Pod に引き渡してくれるところまでを、CSI (Container Storage Interface) の仕様に基づいて自動的に行ってくれるドライバー(仕組み)を提供してくれるものです。
実際に利用してみる
TrueNAS 上で ZFS Dataset を切り出しておく
今回は家に転がっていた TrueNAS 13.0 (Intel NUC に NVMe M.2 SSD を挿したもの) 上の ZFS に あらかじめ Dataset を作っておきます。
TrueNAS のサービスを自動起動にしておく
SSH と実際にストレージアクセスに用いるプロトコル (iSCSI/NFS) のサービスを自動起動にしておきます。なお SSH アクセスで root ユーザーを指定した場合は Actions の設定ボタンから Permit Root Login も設定しておきます。
Helm で democratic-csi のリポジトリを追加する
Kubernetes の kubectl が動くマシン上で helm コマンドを使って democratic-csi の導入の準備をしておきます。
$ helm repo add democratic-csi https://democratic-csi.github.io/charts/
$ helm repo update
$ helm search repo democratic-csi/
設定ファイルを作成する
TrueNAS に対して、Kubernetes 上の trunas-iscsi-democratic-csi-controller が実際に指示を出すために必要となる SSH / HTTP / ZFS 等のパラメータを YAML ファイルに組み立てていきます。
csiDriver:
name: "org.democratic-csi.iscsi"
storageClasses:
- name: truenas-iscsi-csi
defaultClass: true
reclaimPolicy: Delete
volumeBindingMode: Immediate
allowVolumeExpansion: true
parameters:
fsType: ext4
mountOptions: []
secrets:
provisioner-secret:
controller-publish-secret:
node-stage-secret:
node-publish-secret:
controller-expand-secret:
driver:
config:
driver: freenas-iscsi #TrueNAS Coreを使っているときでも driver 名は freenas-* になる
httpConnection:
protocol: http
host: 192.168.1.xxx
port: 80
username: root
password: PASSWORD
sshConnection:
host: 192.168.1.xxx
port: 22
username: root
password: PASSWORD
zfs:
datasetParentName: main/k8s-pvs # PV を生やす ZFS Dataset 名を指定する
detachedSnapshotsDatasetParentName: main/k8s-snaps # ZFS Snapshot を生やす場所を指定する (省略不可)
iscsi:
targetPortal: 192.168.1.xxx:3260
namePrefix: csi-
targetGroups:
- targetGroupPortalGroup: 1
targetGroupInitiatorGroup: 1
targetGroupAuthType: None
targetGroupAuthGroup:
extentInsecureTpc: true
extentXenCompat: false
extentDisablePhysicalBlocksize: true
extentBlocksize: 4096
extentRpm: "SSD"
extentAvailThreshold: 0
TrueNAS で 設定ファイルに合わせて iSCSI Portal と Initiator Group を作る
Portal
Initiator Group
democratic-csi をデプロイする
先ほど作成した設定ファイルを引き渡して、実際に trunas-iscsi-democratic-csi-controller をデプロイしていきます。
$ helm upgrade --install --values truenas-iscsi.yml --create-namespace --namespace democratic-csi trunas-iscsi democratic-csi/democratic-csi
成功すると controller と node が起動してきます。
$ kubectl get pod -n democratic-csi
democratic-csi の中でどのような処理がされているのかは、deployment のログを追いかけるとわかりやすいと思います。
$ kubectl logs -n democratic-csi deployments/trunas-iscsi-democratic-csi-controller
StatefulSet で実際に PVC/PV が作られるか見てみる
テスト用の StatefulSet 定義
とりあえずのテスト用に Ubuntu の Pod を 3個 起動して、それぞれに PersistentVolume を付けるような StatefulSet を定義してみました。
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: ubuntu
labels:
app: ubuntu
spec:
replicas: 3
selector:
matchLabels:
app: ubuntu
template:
metadata:
labels:
app: ubuntu
spec:
containers:
- image: ubuntu:latest
name: ubuntu
command: [ 'sleep', 'infinity']
volumeMounts:
- name: test-claim-iscsi
mountPath: /pv-test
volumeClaimTemplates:
- metadata:
name: test-claim-iscsi
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 30Gi
Apply してみる
適用してみると、Pod が 3個起動して、PVCとPVもそれぞれに合わせて、自動的に作成されています。
$ kubectl apply -f statefulset-test.yml
statefulset.apps/ubuntu created
$ kubectl get pod
NAME READY STATUS RESTARTS AGE
ubuntu-0 1/1 Running 0 34s
ubuntu-1 1/1 Running 0 24s
ubuntu-2 1/1 Running 0 13s
$ kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
test-claim-iscsi-ubuntu-0 Bound pvc-1c9d1a85-5b5a-4c1c-a806-05384226c254 30Gi RWO truenas-iscsi-csi 54s
test-claim-iscsi-ubuntu-1 Bound pvc-8037a743-afec-4e3e-bc45-7b7053a78dc1 30Gi RWO truenas-iscsi-csi 44s
test-claim-iscsi-ubuntu-2 Bound pvc-d206a88e-4c4f-4780-a69b-0ceb47367b46 30Gi RWO truenas-iscsi-csi 33s
$ kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
pvc-1c9d1a85-5b5a-4c1c-a806-05384226c254 30Gi RWO Delete Bound default/test-claim-iscsi-ubuntu-0 truenas-iscsi-csi 64s
pvc-8037a743-afec-4e3e-bc45-7b7053a78dc1 30Gi RWO Delete Bound default/test-claim-iscsi-ubuntu-1 truenas-iscsi-csi 54s
pvc-d206a88e-4c4f-4780-a69b-0ceb47367b46 30Gi RWO Delete Bound default/test-claim-iscsi-ubuntu-2 truenas-iscsi-csi 43s
TrueNAS 上でも PVC の名前に合わせた ZVol が自動的に切り出されて、iSCSI ボリュームとして共有されています。
Pod の中に入って確認してみる
kubectl exec して、実際に Pod の中に入って df コマンドを実行すると、指定したとおり 30Gi のボリューム (表示上は29 Gですが) をマウントしていることが分かります。
$ kubectl exec -it ubuntu-0 -- bash
root@ubuntu-0:/#
root@ubuntu-0:/#
root@ubuntu-0:/# df -h
Filesystem Size Used Avail Use% Mounted on
overlay 29G 7.7G 20G 29% /
tmpfs 64M 0 64M 0% /dev
/dev/sda 30G 24K 28G 1% /pv-test
/dev/mapper/ubuntu--vg-ubuntu--lv 29G 7.7G 20G 29% /etc/hosts
shm 64M 0 64M 0% /dev/shm
tmpfs 16G 12K 16G 1% /run/secrets/kubernetes.io/serviceaccount
tmpfs 7.9G 0 7.9G 0% /proc/acpi
tmpfs 7.9G 0 7.9G 0% /proc/scsi
tmpfs 7.9G 0 7.9G 0% /sys/firmware
この後は、通常の PersistentVolume として、ファイルの読み書きや Pod の停止→起動後もきちんとデータが永続化されて利用可能になっています。
最後に
PV を地味にポチポチ作ったり、Localに置いててあれ?どこに行ったがなくなると、気が楽になりますから、
お家に CSI 準拠のストレージがあると何かと捗りますよ (ぇ
Discussion