Создать PV в S3 для кластера k8s
В этой статье опишем процесс подключения персистентного хранилища на базе S3 к поду кластера Kubernetes.
Хранилище S3 медленне аналогичного устройства на базе диска, но дешевле по стоимсости и потенциально не ограничено. Есть квоты, но их легко можно увеличить в большую сторону.
Для подключения бакета необходимо:
1. Установить и настроить утилиты yc, jq, git, kubectl.
2. Создать бакет. У меня это будет cam-kuber-s3.
3. Иметь SA с соответствующими правами для записи в данный бакет (например, editor) и сгенерированным авторизованным ключом.
Создадим Secret, в котором укажем ключи SA для доступа к бакету.
cat <<EOF | kubectl apply -f - apiVersion: v1 kind: Secret metadata: namespace: kube-system name: csi-s3-secret stringData: accessKeyID: YCAJ11kn7y11112g111111hMv secretAccessKey: YCO1111GH8114It111116RP01111EY11117Zi11P endpoint: https://storage.yandexcloud.net EOF
kubectl get secret -A | grep csi-s3-secret kube-system csi-s3-secret Opaque 3 55s
Создадим StorageClass, который будет хранить информацию о типе хранилища.
cat <<EOF | kubectl apply -f - apiVersion: storage.k8s.io/v1 kind: StorageClass metadata: name: csi-s3 provisioner: ru.yandex.s3.csi parameters: mounter: geesefs options: "--memory-limit=1000 --dir-mode=0777 --file-mode=0666" bucket: cam-kuber-s3 csi.storage.k8s.io/provisioner-secret-name: csi-s3-secret csi.storage.k8s.io/provisioner-secret-namespace: kube-system csi.storage.k8s.io/controller-publish-secret-name: csi-s3-secret csi.storage.k8s.io/controller-publish-secret-namespace: kube-system csi.storage.k8s.io/node-stage-secret-name: csi-s3-secret csi.storage.k8s.io/node-stage-secret-namespace: kube-system csi.storage.k8s.io/node-publish-secret-name: csi-s3-secret csi.storage.k8s.io/node-publish-secret-namespace: kube-system EOF
kubectl get sc NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE ALLOWVOLUMEEXPANSION AGE csi-s3 ru.yandex.s3.csi Delete Immediate false 9s yc-network-hdd (default) disk-csi-driver.mks.ycloud.io Delete WaitForFirstConsumer true 4d1h yc-network-nvme disk-csi-driver.mks.ycloud.io Delete WaitForFirstConsumer true 4d1h yc-network-ssd disk-csi-driver.mks.ycloud.io Delete WaitForFirstConsumer true 4d1h yc-network-ssd-nonreplicated disk-csi-driver.mks.ycloud.io Delete WaitForFirstConsumer true 4d1h
В предыдущем пункте мы указали информацию о том какой драйвер использовать (ru.yandex.s3.csi) и программу, которая будет использоваться для монтирования бакета (geesefs).
Теперь нам надо скачать сам драйвер, программу и установить их.
git clone https://github.com/yandex-cloud/k8s-csi-s3.git
Установим драйвер и программу.
kubectl create -f k8s-csi-s3/deploy/kubernetes/provisioner.yaml && \ kubectl create -f k8s-csi-s3/deploy/kubernetes/attacher.yaml && \ kubectl create -f k8s-csi-s3/deploy/kubernetes/csi-s3.yaml
cat <<EOF | kubectl apply -f -
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: csi-s3-pvc-dynamic
namespace: default
spec:
accessModes:
- ReadWriteMany
resources:
requests:
storage: 5Gi
storageClassName: csi-s3
EOFkubectl get pvc NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE csi-s3-pvc-dynamic Bound pvc-afd588b3-b10d-490f-8cc2-07d9457bb3e0 5Gi RWX csi-s3 7s
cat <<EOF | kubectl apply -f -
apiVersion: apps/v1
kind: Deployment
metadata:
name: cam-nginx
labels:
app: nginx-prod
environment: prod
spec:
replicas: 2
selector:
matchLabels:
app: nginx
strategy:
rollingUpdate:
maxSurge: 1
maxUnavailable: 1
type: RollingUpdate
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx:latest
imagePullPolicy: IfNotPresent
ports:
- name: http
containerPort: 80
resources:
requests:
cpu: 300m
memory: 300Mi
limits:
cpu: 400m
memory: 400Mi
volumeMounts:
- mountPath: /mnt/s3
name: cameda-volume
restartPolicy: Always
volumes:
- name: cameda-volume
persistentVolumeClaim:
claimName: csi-s3-pvc-dynamic
EOFkubectl get po NAME READY STATUS RESTARTS AGE cam-nginx-59798c8884-f9shd 1/1 Running 0 3m54s cam-nginx-59798c8884-psbvt 1/1 Running 0 3m54s
kubectl exec --stdin --tty cam-nginx-59798c8884-f9shd -- /bin/bash cd /mnt/s3 touch fule echo -n "Hello, World!" > fule cat fule Hello, World!
kubectl exec --stdin --tty cam-nginx-59798c8884-psbvt -- /bin/bash cd /mnt/s3 cat fule Hello, World! echo -n "Hello, Alex!!!" >> fule cat fule Hello, World! Hello, Alex!!!
kubectl exec --stdin --tty cam-nginx-59798c8884-f9shd -- /bin/bash cd /mnt/s3 cat fule Hello, World! Hello, Alex!!!