diff --git a/deploy/helm/.helmignore b/deploy/helm/.helmignore new file mode 100644 index 0000000..0e8a0eb --- /dev/null +++ b/deploy/helm/.helmignore @@ -0,0 +1,23 @@ +# Patterns to ignore when building packages. +# This supports shell glob matching, relative path matching, and +# negation (prefixed with !). Only one pattern per line. +.DS_Store +# Common VCS dirs +.git/ +.gitignore +.bzr/ +.bzrignore +.hg/ +.hgignore +.svn/ +# Common backup files +*.swp +*.bak +*.tmp +*.orig +*~ +# Various IDEs +.project +.idea/ +*.tmproj +.vscode/ diff --git a/deploy/helm/Chart.yaml b/deploy/helm/Chart.yaml new file mode 100644 index 0000000..0339e48 --- /dev/null +++ b/deploy/helm/Chart.yaml @@ -0,0 +1,12 @@ +apiVersion: v2 +name: csi-s3 +description: A Container Storage Interface for S3 +type: application +version: 0.1.0 +appVersion: "1.1.1" +keywords: + - s3 + - csi +home: https://github.com/ctrox/csi-s3 +sources: + - https://github.com/ctrox/csi-s3/deploy/helm diff --git a/deploy/helm/README.md b/deploy/helm/README.md new file mode 100644 index 0000000..7d8db93 --- /dev/null +++ b/deploy/helm/README.md @@ -0,0 +1,38 @@ +# Helm chart for csi-s3 + +This chart adds S3 volume support to your cluster. + +## Install chart + +```shell +helm install --namespace kube-system csi-s3 . +``` + +After installation succeeds, you can get a status of Chart: `helm status csi-s3`. + +## Delete Chart + +```shell +helm uninstall csi-s3 --namespace kube-system` +``` + +## Configuration + +By default, this chart creates a secret and a storage class. + +The following table lists all configuration parameters and their default values. + +| Parameter | Description | Default | +| ---------------------------- | ---------------------------------------------------------------------- | ------------------------------------------------------ | +| `storageClass.create` | Specifies whether the storage class should be created | true | +| `storageClass.name` | Storage class name | csi-s3 | +| `storageClass.bucket` | Existing bucket name to use, or leave blank to create | | +| `storageClass.usePrefix` | Enable the prefix feature to avoid the removal of the prefix or bucket | false | +| `storageClass.prefix` | can be empty (mounts bucket root), an existing prefix or a new one. | | +| `storageClass.reclaimPolicy` | Volume reclaim policy | Delete | +| `storageClass.annotations` | Annotations for the storage class | | +| `secret.create` | Specifies whether the secret should be created | true | +| `secret.name` | Name of the secret | csi-s3-secret | +| `secret.accessKey` | S3 Access Key | | +| `secret.secretKey` | S3 Secret Key | | +| `secret.endpoint` | Endpoint | https://storage.yandexcloud.net | diff --git a/deploy/helm/templates/NOTES.txt b/deploy/helm/templates/NOTES.txt new file mode 100644 index 0000000..50dd488 --- /dev/null +++ b/deploy/helm/templates/NOTES.txt @@ -0,0 +1 @@ +The csi-s3 driver has been successfully installed. diff --git a/deploy/helm/templates/_helpers.tpl b/deploy/helm/templates/_helpers.tpl new file mode 100644 index 0000000..ce466cc --- /dev/null +++ b/deploy/helm/templates/_helpers.tpl @@ -0,0 +1,51 @@ +{{/* +Expand the name of the chart. +*/}} +{{- define "csi-s3.name" -}} +{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }} +{{- end }} + +{{/* +Create a default fully qualified app name. +We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec). +If release name contains chart name it will be used as a full name. +*/}} +{{- define "csi-s3.fullname" -}} +{{- if .Values.fullnameOverride }} +{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }} +{{- else }} +{{- $name := default .Chart.Name .Values.nameOverride }} +{{- if contains $name .Release.Name }} +{{- .Release.Name | trunc 63 | trimSuffix "-" }} +{{- else }} +{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" }} +{{- end }} +{{- end }} +{{- end }} + +{{/* +Create chart name and version as used by the chart label. +*/}} +{{- define "csi-s3.chart" -}} +{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }} +{{- end }} + +{{/* +Common labels +*/}} +{{- define "csi-s3.labels" -}} +helm.sh/chart: {{ include "csi-s3.chart" . }} +{{ include "csi-s3.selectorLabels" . }} +{{- if .Chart.AppVersion }} +app.kubernetes.io/version: {{ .Chart.AppVersion | quote }} +{{- end }} +app.kubernetes.io/managed-by: {{ .Release.Service }} +{{- end }} + +{{/* +Selector labels +*/}} +{{- define "csi-s3.selectorLabels" -}} +app.kubernetes.io/name: {{ include "csi-s3.name" . }} +app.kubernetes.io/instance: {{ .Release.Name }} +{{- end }} diff --git a/deploy/helm/templates/attacher.yaml b/deploy/helm/templates/attacher.yaml new file mode 100644 index 0000000..5f5b4e5 --- /dev/null +++ b/deploy/helm/templates/attacher.yaml @@ -0,0 +1,106 @@ +apiVersion: v1 +kind: ServiceAccount +metadata: + name: csi-attacher-sa + labels: + {{- include "csi-s3.labels" . | nindent 4 }} + {{- with .Values.serviceAccount.annotations }} + annotations: + {{- toYaml . | nindent 4 }} + {{- end }} +--- +kind: ClusterRole +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: external-attacher-runner + labels: + {{- include "csi-s3.labels" . | nindent 4 }} +rules: + - apiGroups: [""] + resources: ["secrets"] + verbs: ["get", "list"] + - apiGroups: [""] + resources: ["events"] + verbs: ["get", "list", "watch", "update"] + - apiGroups: [""] + resources: ["persistentvolumes"] + verbs: ["get", "list", "watch", "update"] + - apiGroups: [""] + resources: ["nodes"] + verbs: ["get", "list", "watch"] + - apiGroups: ["storage.k8s.io"] + resources: ["volumeattachments"] + verbs: ["get", "list", "watch", "update", "patch"] +--- +kind: ClusterRoleBinding +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: csi-attacher-role + labels: + {{- include "csi-s3.labels" . | nindent 4 }} +subjects: + - kind: ServiceAccount + name: csi-attacher-sa + namespace: "{{ .Release.Namespace }}" +roleRef: + kind: ClusterRole + name: external-attacher-runner + apiGroup: rbac.authorization.k8s.io +--- +# needed for StatefulSet +apiVersion: v1 +kind: Service +metadata: + name: csi-attacher-s3 + labels: + {{- include "csi-s3.labels" . | nindent 4 }} + app: csi-attacher-s3 +spec: + selector: + {{- include "csi-s3.selectorLabels" . | nindent 4 }} + app: csi-attacher-s3 + ports: + - name: csi-s3-dummy + port: 65535 +--- +kind: StatefulSet +apiVersion: apps/v1 +metadata: + name: csi-attacher-s3 + labels: + {{- include "csi-s3.labels" . | nindent 4 }} +spec: + serviceName: csi-attacher-s3 + replicas: 1 + selector: + matchLabels: + {{- include "csi-s3.selectorLabels" . | nindent 6 }} + app: csi-attacher-s3 + template: + metadata: + labels: + {{- include "csi-s3.selectorLabels" . | nindent 8 }} + app: csi-attacher-s3 + spec: + serviceAccountName: csi-attacher-sa + containers: + - name: csi-attacher + image: "{{ .Values.attacher.image.repository }}:{{ .Values.attacher.image.tag | default .Chart.AppVersion }}" + imagePullPolicy: "{{ .Values.attacher.image.pullPolicy }}" + args: + - "--v=4" + - "--csi-address=$(ADDRESS)" + env: + - name: ADDRESS + value: /var/lib/kubelet/plugins/ch.ctrox.csi.s3-driver/csi.sock + volumeMounts: + - name: socket-dir + mountPath: /var/lib/kubelet/plugins/ch.ctrox.csi.s3-driver + volumes: + - name: socket-dir + hostPath: + path: /var/lib/kubelet/plugins/ch.ctrox.csi.s3-driver + type: DirectoryOrCreate + tolerations: + - key: node-role.kubernetes.io/master + operator: "Exists" diff --git a/deploy/helm/templates/csi-s3.yaml b/deploy/helm/templates/csi-s3.yaml new file mode 100644 index 0000000..5512361 --- /dev/null +++ b/deploy/helm/templates/csi-s3.yaml @@ -0,0 +1,133 @@ +apiVersion: v1 +kind: ServiceAccount +metadata: + name: csi-s3 + labels: + {{- include "csi-s3.labels" . | nindent 4 }} + {{- with .Values.serviceAccount.annotations }} + annotations: + {{- toYaml . | nindent 4 }} + {{- end }} +--- +kind: ClusterRole +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: csi-s3 + labels: + {{- include "csi-s3.labels" . | nindent 4 }} +rules: + - apiGroups: [""] + resources: ["secrets"] + verbs: ["get", "list"] + - apiGroups: [""] + resources: ["nodes"] + verbs: ["get", "list", "update"] + - apiGroups: [""] + resources: ["namespaces"] + verbs: ["get", "list"] + - apiGroups: [""] + resources: ["persistentvolumes"] + verbs: ["get", "list", "watch", "update"] + - apiGroups: ["storage.k8s.io"] + resources: ["volumeattachments"] + verbs: ["get", "list", "watch", "update"] +--- +kind: ClusterRoleBinding +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: csi-s3 + labels: + {{- include "csi-s3.labels" . | nindent 4 }} +subjects: + - kind: ServiceAccount + name: csi-s3 + namespace: "{{ .Release.Namespace }}" +roleRef: + kind: ClusterRole + name: csi-s3 + apiGroup: rbac.authorization.k8s.io +--- +kind: DaemonSet +apiVersion: apps/v1 +metadata: + name: csi-s3 + labels: + {{- include "csi-s3.labels" . | nindent 4 }} +spec: + selector: + matchLabels: + {{- include "csi-s3.selectorLabels" . | nindent 6 }} + app: csi-s3 + template: + metadata: + labels: + {{- include "csi-s3.selectorLabels" . | nindent 8 }} + app: csi-s3 + spec: + serviceAccountName: csi-s3 + hostNetwork: true + containers: + - name: driver-registrar + image: "{{ .Values.registrar.image.repository }}:{{ .Values.registrar.image.tag | default .Chart.AppVersion }}" + imagePullPolicy: "{{ .Values.registrar.image.pullPolicy }}" + args: + - "--kubelet-registration-path=$(DRIVER_REG_SOCK_PATH)" + - "--v=4" + - "--csi-address=$(ADDRESS)" + env: + - name: ADDRESS + value: /csi/csi.sock + - name: DRIVER_REG_SOCK_PATH + value: /var/lib/kubelet/plugins/ch.ctrox.csi.s3-driver/csi.sock + - name: KUBE_NODE_NAME + valueFrom: + fieldRef: + fieldPath: spec.nodeName + volumeMounts: + - name: plugin-dir + mountPath: /csi + - name: registration-dir + mountPath: /registration/ + - name: csi-s3 + image: "{{ .Values.csi.image.repository }}:{{ .Values.csi.image.tag | default .Chart.AppVersion }}" + imagePullPolicy: "{{ .Values.csi.image.pullPolicy }}" + securityContext: + privileged: true + capabilities: + add: ["SYS_ADMIN"] + allowPrivilegeEscalation: true + args: + - "--endpoint=$(CSI_ENDPOINT)" + - "--nodeid=$(NODE_ID)" + - "--v=4" + env: + - name: CSI_ENDPOINT + value: unix:///csi/csi.sock + - name: NODE_ID + valueFrom: + fieldRef: + fieldPath: spec.nodeName + volumeMounts: + - name: plugin-dir + mountPath: /csi + - name: pods-mount-dir + mountPath: /var/lib/kubelet/pods + mountPropagation: "Bidirectional" + - name: fuse-device + mountPath: /dev/fuse + volumes: + - name: registration-dir + hostPath: + path: /var/lib/kubelet/plugins_registry/ + type: DirectoryOrCreate + - name: plugin-dir + hostPath: + path: /var/lib/kubelet/plugins/ch.ctrox.csi.s3-driver + type: DirectoryOrCreate + - name: pods-mount-dir + hostPath: + path: /var/lib/kubelet/pods + type: Directory + - name: fuse-device + hostPath: + path: /dev/fuse diff --git a/deploy/helm/templates/provisioner.yaml b/deploy/helm/templates/provisioner.yaml new file mode 100644 index 0000000..aaeb6ff --- /dev/null +++ b/deploy/helm/templates/provisioner.yaml @@ -0,0 +1,120 @@ +apiVersion: v1 +kind: ServiceAccount +metadata: + name: csi-provisioner-sa + labels: + {{- include "csi-s3.labels" . | nindent 4 }} + {{- with .Values.serviceAccount.annotations }} + annotations: + {{- toYaml . | nindent 4 }} + {{- end }} +--- +kind: ClusterRole +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: external-provisioner-runner + labels: + {{- include "csi-s3.labels" . | nindent 4 }} +rules: + - apiGroups: [""] + resources: ["secrets"] + verbs: ["get", "list"] + - apiGroups: [""] + resources: ["persistentvolumes"] + verbs: ["get", "list", "watch", "create", "delete"] + - apiGroups: [""] + resources: ["persistentvolumeclaims"] + verbs: ["get", "list", "watch", "update"] + - apiGroups: ["storage.k8s.io"] + resources: ["storageclasses"] + verbs: ["get", "list", "watch"] + - apiGroups: [""] + resources: ["events"] + verbs: ["list", "watch", "create", "update", "patch"] +--- +kind: ClusterRoleBinding +apiVersion: rbac.authorization.k8s.io/v1 +metadata: + name: csi-provisioner-role + labels: + {{- include "csi-s3.labels" . | nindent 4 }} +subjects: + - kind: ServiceAccount + name: csi-provisioner-sa + namespace: "{{ .Release.Namespace }}" +roleRef: + kind: ClusterRole + name: external-provisioner-runner + apiGroup: rbac.authorization.k8s.io +--- +kind: Service +apiVersion: v1 +metadata: + name: csi-provisioner-s3 + labels: + {{- include "csi-s3.labels" . | nindent 4 }} + app: csi-provisioner-s3 +spec: + selector: + {{- include "csi-s3.selectorLabels" . | nindent 4 }} + app: csi-provisioner-s3 + ports: + - name: csi-s3-dummy + port: 65535 +--- +kind: StatefulSet +apiVersion: apps/v1 +metadata: + name: csi-provisioner-s3 + labels: + {{- include "csi-s3.labels" . | nindent 4 }} +spec: + serviceName: "csi-provisioner-s3" + replicas: 1 + selector: + matchLabels: + {{- include "csi-s3.selectorLabels" . | nindent 6 }} + app: csi-provisioner-s3 + template: + metadata: + labels: + {{- include "csi-s3.selectorLabels" . | nindent 8 }} + app: csi-provisioner-s3 + spec: + serviceAccountName: csi-provisioner-sa + tolerations: + - key: node-role.kubernetes.io/master + operator: "Exists" + containers: + - name: csi-provisioner + image: "{{ .Values.provisioner.image.repository }}:{{ .Values.provisioner.image.tag | default .Chart.AppVersion }}" + imagePullPolicy: "{{ .Values.provisioner.image.pullPolicy }}" + args: + - "--csi-address=$(ADDRESS)" + - "--v=4" + env: + - name: ADDRESS + value: /var/lib/kubelet/plugins/ch.ctrox.csi.s3-driver/csi.sock + volumeMounts: + - name: socket-dir + mountPath: /var/lib/kubelet/plugins/ch.ctrox.csi.s3-driver + - name: csi-s3 + image: "{{ .Values.csi.image.repository }}:{{ .Values.csi.image.tag | default .Chart.AppVersion }}" + imagePullPolicy: "{{ .Values.csi.image.pullPolicy }}" + args: + - "--endpoint=$(CSI_ENDPOINT)" + - "--nodeid=$(NODE_ID)" + - "--v=4" + env: + - name: CSI_ENDPOINT + value: unix:///var/lib/kubelet/plugins/ch.ctrox.csi.s3-driver/csi.sock + - name: NODE_ID + valueFrom: + fieldRef: + fieldPath: spec.nodeName + volumeMounts: + - name: socket-dir + mountPath: /var/lib/kubelet/plugins/ch.ctrox.csi.s3-driver + volumes: + - name: socket-dir + emptyDir: {} diff --git a/deploy/helm/templates/secret.yaml b/deploy/helm/templates/secret.yaml new file mode 100644 index 0000000..be7ac7d --- /dev/null +++ b/deploy/helm/templates/secret.yaml @@ -0,0 +1,15 @@ +{{- if .Values.secret.create -}} +apiVersion: v1 +kind: Secret +metadata: + namespace: {{ .Release.Namespace }} + name: {{ .Values.secret.name }} +stringData: +{{- if .Values.secret.accessKey }} + accessKeyID: {{ .Values.secret.accessKey }} +{{- end }} +{{- if .Values.secret.secretKey }} + secretAccessKey: {{ .Values.secret.secretKey }} +{{- end }} + endpoint: {{ .Values.secret.endpoint }} +{{- end -}} diff --git a/deploy/helm/templates/storageclass.yaml b/deploy/helm/templates/storageclass.yaml new file mode 100644 index 0000000..78ee7c1 --- /dev/null +++ b/deploy/helm/templates/storageclass.yaml @@ -0,0 +1,29 @@ +{{- if .Values.storageClass.create -}} +kind: StorageClass +apiVersion: storage.k8s.io/v1 +metadata: + name: "{{ .Values.storageClass.name }}" +{{- if .Values.storageClass.annotations }} + annotations: +{{ toYaml .Values.storageClass.annotations | indent 4 }} +{{- end }} +provisioner: ch.ctrox.csi.s3-driver +reclaimPolicy: "{{ .Values.storageClass.reclaimPolicy }}" +parameters: + mounter: "{{ .Values.storageClass.mounter }}" +{{- if .Values.storageClass.bucket }} + bucket: "{{ .Values.storageClass.bucket }}" +{{- end }} +{{- if .Values.secret.usePrefix }} + usePrefix: "true" +{{- end }} + prefix: "{{ .Values.secret.prefix }}" + csi.storage.k8s.io/provisioner-secret-name: {{ .Values.secret.name }} + csi.storage.k8s.io/provisioner-secret-namespace: {{ .Release.Namespace }} + csi.storage.k8s.io/controller-publish-secret-name: {{ .Values.secret.name }} + csi.storage.k8s.io/controller-publish-secret-namespace: {{ .Release.Namespace }} + csi.storage.k8s.io/node-stage-secret-name: {{ .Values.secret.name }} + csi.storage.k8s.io/node-stage-secret-namespace: {{ .Release.Namespace }} + csi.storage.k8s.io/node-publish-secret-name: {{ .Values.secret.name }} + csi.storage.k8s.io/node-publish-secret-namespace: {{ .Release.Namespace }} +{{- end -}} diff --git a/deploy/helm/values.yaml b/deploy/helm/values.yaml new file mode 100644 index 0000000..2b7dc6b --- /dev/null +++ b/deploy/helm/values.yaml @@ -0,0 +1,76 @@ +# Default values for csi-s3. +# This is a YAML-formatted file. +# Declare variables to be passed into your templates. + +attacher: + image: + repository: quay.io/k8scsi/csi-attacher + pullPolicy: IfNotPresent + # Overrides the image tag whose default is the chart appVersion. + tag: v2.2.0 + +provisioner: + image: + repository: quay.io/k8scsi/csi-provisioner + pullPolicy: IfNotPresent + # Overrides the image tag whose default is the chart appVersion. + tag: v2.1.0 + +registrar: + image: + repository: quay.io/k8scsi/csi-node-driver-registrar + pullPolicy: IfNotPresent + # Overrides the image tag whose default is the chart appVersion. + tag: v1.2.0 + +csi: + image: + repository: ctrox/csi-s3 + pullPolicy: Always + # Overrides the image tag whose default is the chart appVersion. + tag: v1.2.0-rc.2 + +nameOverride: "" +fullnameOverride: "" + +serviceAccount: + # Specifies whether a service account should be created + create: true + # Annotations to add to the service account + annotations: {} + # The name of the service account to use. + # If not set and create is true, a name is generated using the fullname template + name: "" + +secret: + # Specifies whether the secret should be created + create: true + # Name of the secret + name: csi-s3-secret + # S3 Access Key + accessKey: "" + # S3 Secret Key + secretKey: "" + # Endpoint + endpoint: https://s3.amazonaws.com + +storageClass: + # Specifies whether the storage class should be created + create: true + # Name + name: csi-s3 + # Either s3fs, rclone, goofys or s3backer + mounter: s3fs + # An existing bucket or leave blank to create + bucket: "" + # Volume reclaim policy + reclaimPolicy: Delete + # Annotations for the storage class + # Example: + # annotations: + # storageclass.kubernetes.io/is-default-class: "true" + annotations: {} + # 'usePrefix' must be true in order to enable the prefix feature and to avoid the removal of the prefix or bucket + usePrefix: + # 'prefix' can be empty (it will mount on the root of the bucket), an existing prefix or a new one. + prefix: