commit 8b3c549d47f264198a5264ca06b2f690ffec48c2 Author: Swordsteel Date: Mon Sep 29 07:07:02 2025 +0200 init commit diff --git a/.gitea/workflows/release.yaml b/.gitea/workflows/release.yaml new file mode 100644 index 0000000..0dced27 --- /dev/null +++ b/.gitea/workflows/release.yaml @@ -0,0 +1,11 @@ +name: Publish Helm Chart + +on: + workflow_dispatch: + +jobs: + call-helm-ci: + uses: helm/common-workflows/.gitea/workflows/release.yaml@master + secrets: + CI_BOT_USERNAME: ${{ secrets.CI_BOT_USERNAME }} + CI_BOT_TOKEN: ${{ secrets.CI_BOT_TOKEN }} diff --git a/README.md b/README.md new file mode 100644 index 0000000..cf3a521 --- /dev/null +++ b/README.md @@ -0,0 +1,25 @@ +# MongoDB + +## Basic stuff + +### Install +```shell +helm install mongo ./helm --namespace mongo --create-namespace +``` +### Update + +```shell +helm -n mongo upgrade mongo .\helm +``` + +### Check + +```shell +kubectl -n mongo get secret,cm,pvc,pod,svc +``` + +### Delete + +```shell +kubectl delete ns mongo +``` diff --git a/helm/ .helmignore b/helm/ .helmignore new file mode 100644 index 0000000..0e8a0eb --- /dev/null +++ b/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/helm/Chart.yaml b/helm/Chart.yaml new file mode 100644 index 0000000..44ad1aa --- /dev/null +++ b/helm/Chart.yaml @@ -0,0 +1,6 @@ +apiVersion: v2 +name: mongodb +description: A Helm chart for MongoDB +type: application +version: 0.1.0 +appVersion: "8.0" diff --git a/helm/templates/_helpers.tpl b/helm/templates/_helpers.tpl new file mode 100644 index 0000000..80f77fa --- /dev/null +++ b/helm/templates/_helpers.tpl @@ -0,0 +1,26 @@ +{{- define "mongo.name" -}} +{{- printf "%s" .Chart.Name | trunc 63 | trimSuffix "-" -}} +{{- end -}} + +{{- define "mongo.name.headless" -}} +{{- printf "%s-headless" .Chart.Name | trunc 54 | trimSuffix "-" -}} +{{- end -}} + +{{- define "mongo.name.config" -}} +{{- printf "%s-config" .Chart.Name | trunc 56 | trimSuffix "-" -}} +{{- end -}} + +{{- define "mongo.name.secret" -}} +{{- printf "%s-secret" .Chart.Name | trunc 56 | trimSuffix "-" -}} +{{- end -}} + +{{- define "mongo.name.initialize" -}} +{{- printf "%s-initialize" .Chart.Name | trunc 52 | trimSuffix "-" -}} +{{- end -}} + +{{- define "mongo.labels" -}} +app.kubernetes.io/name: {{ include "mongo.name" . }} +app.kubernetes.io/instance: {{ .Release.Name }} +app.kubernetes.io/version: {{ .Chart.AppVersion | quote }} +helm.sh/chart: {{ .Chart.Name }}-{{ .Chart.Version }} +{{- end -}} diff --git a/helm/templates/headless-service.yaml b/helm/templates/headless-service.yaml new file mode 100644 index 0000000..b989c0a --- /dev/null +++ b/helm/templates/headless-service.yaml @@ -0,0 +1,16 @@ +apiVersion: v1 +kind: Service +metadata: + name: {{ include "mongo.name.headless" . }} + labels: + {{- include "mongo.labels" . | nindent 4 }} +spec: + clusterIP: None + publishNotReadyAddresses: true + ports: + - port: {{ .Values.service.port }} + targetPort: {{ .Values.service.port }} + protocol: TCP + name: mongodb + selector: + app.kubernetes.io/name: {{ include "mongo.name" . }} \ No newline at end of file diff --git a/helm/templates/init-script.yaml b/helm/templates/init-script.yaml new file mode 100644 index 0000000..70448a1 --- /dev/null +++ b/helm/templates/init-script.yaml @@ -0,0 +1,16 @@ +{{- if .Values.auth.enabled }} +apiVersion: v1 +kind: ConfigMap +metadata: + name: {{ include "mongo.name.initialize" . }} + labels: + {{- include "mongo.labels" . | nindent 4 }} +data: + init.js: | + db = db.getSiblingDB(process.env.MONGO_INITDB_DATABASE); + db.createUser({ + user: process.env.MONGO_INITDB_USERNAME, + pwd: process.env.MONGO_INITDB_PASSWORD, + roles: [{ role: "readWrite", db: process.env.MONGO_INITDB_DATABASE }] + }); +{{- end }} diff --git a/helm/templates/secret.yaml b/helm/templates/secret.yaml new file mode 100644 index 0000000..45a81da --- /dev/null +++ b/helm/templates/secret.yaml @@ -0,0 +1,16 @@ +apiVersion: v1 +kind: Secret +metadata: + name: {{ include "mongo.name.secret" . }} + labels: + {{- include "mongo.labels" . | nindent 4 }} +type: Opaque +stringData: + {{- if .Values.auth.enabled }} + MONGO_INITDB_ROOT_PASSWORD: "{{ .Values.auth.rootPassword }}" + MONGO_INITDB_ROOT_USERNAME: "{{ .Values.auth.rootUsername }}" + MONGO_INITDB_DATABASE: "{{ .Values.auth.database }}" + MONGO_INITDB_PASSWORD: "{{ .Values.auth.password }}" + MONGO_INITDB_USERNAME: "{{ .Values.auth.username }}" +{{/* MONGO_AUTHSOURCE: "admin"*/}} + {{- end }} \ No newline at end of file diff --git a/helm/templates/service.yaml b/helm/templates/service.yaml new file mode 100644 index 0000000..b5c653f --- /dev/null +++ b/helm/templates/service.yaml @@ -0,0 +1,18 @@ +apiVersion: v1 +kind: Service +metadata: + name: {{ include "mongo.name" . }} + labels: + {{- include "mongo.labels" . | nindent 4 }} +spec: + type: {{ .Values.service.type }} + {{- if and .Values.service.loadBalancerIP (ne .Values.service.loadBalancerIP "") }} + loadBalancerIP: {{ .Values.service.loadBalancerIP }} + {{- end }} + ports: + - port: {{ .Values.service.port }} + targetPort: {{ .Values.service.port }} + protocol: TCP + name: mongodb + selector: + app.kubernetes.io/name: {{ include "mongo.name" . }} \ No newline at end of file diff --git a/helm/templates/statefulset.yaml b/helm/templates/statefulset.yaml new file mode 100644 index 0000000..7a953a7 --- /dev/null +++ b/helm/templates/statefulset.yaml @@ -0,0 +1,86 @@ +apiVersion: apps/v1 +kind: StatefulSet +metadata: + name: {{ include "mongo.name" . }} + labels: + {{- include "mongo.labels" . | nindent 4 }} +spec: + serviceName: {{ include "mongo.name" . }} + replicas: {{ .Values.statefulset.replicas }} + podManagementPolicy: {{ .Values.statefulset.podManagementPolicy }} + updateStrategy: + type: {{ .Values.statefulset.updateStrategy.type }} + selector: + matchLabels: + app.kubernetes.io/name: {{ include "mongo.name" . }} + template: + metadata: + labels: + app.kubernetes.io/name: {{ include "mongo.name" . }} + app.kubernetes.io/instance: {{ .Release.Name }} + spec: + {{- if .Values.securityContext.enabled }} + securityContext: + fsGroup: {{ .Values.securityContext.fsGroup }} + runAsUser: {{ .Values.securityContext.runAsUser }} + runAsNonRoot: {{ .Values.securityContext.runAsNonRoot }} + {{- end }} + containers: + - name: mongo + image: "{{ .Values.image.repository }}:{{ .Values.image.tag }}" + imagePullPolicy: {{ .Values.image.pullPolicy }} + args: + {{- if .Values.extraCommandLineArgs }} + - "{{ .Values.extraCommandLineArgs }}" + {{- end }} + ports: + - containerPort: {{ .Values.service.port }} + name: mongodb + envFrom: + - secretRef: + name: {{ include "mongo.name.secret" . }} + volumeMounts: + - name: data + mountPath: /data/db + {{- if .Values.auth.enabled }} + - name: init-script + mountPath: /docker-entrypoint-initdb.d + {{- end }} + {{- if .Values.readinessProbe.enabled }} + readinessProbe: + exec: + command: {{ toJson .Values.healthCheck.command }} + initialDelaySeconds: {{ .Values.readinessProbe.initialDelaySeconds }} + periodSeconds: {{ .Values.readinessProbe.periodSeconds }} + timeoutSeconds: {{ .Values.readinessProbe.timeoutSeconds }} + failureThreshold: {{ .Values.readinessProbe.failureThreshold }} + successThreshold: {{ .Values.readinessProbe.successThreshold }} + {{- end }} + {{- if .Values.livenessProbe.enabled }} + livenessProbe: + exec: + command: {{ toJson .Values.healthCheck.command }} + initialDelaySeconds: {{ .Values.livenessProbe.initialDelaySeconds }} + periodSeconds: {{ .Values.livenessProbe.periodSeconds }} + timeoutSeconds: {{ .Values.livenessProbe.timeoutSeconds }} + failureThreshold: {{ .Values.livenessProbe.failureThreshold }} + successThreshold: {{ .Values.livenessProbe.successThreshold }} + {{- end }} + resources: + {{- toYaml .Values.resources | nindent 10 }} + volumes: + - name: init-script + configMap: + name: {{ include "mongo.name.initialize" . }} + volumeClaimTemplates: + - metadata: + name: data + spec: + accessModes: + {{- toYaml .Values.persistence.accessModes | nindent 10 }} + resources: + requests: + storage: {{ .Values.persistence.size }} + {{- if .Values.persistence.storageClass }} + storageClassName: {{ .Values.persistence.storageClass }} + {{- end }} \ No newline at end of file diff --git a/helm/values.yaml b/helm/values.yaml new file mode 100644 index 0000000..2198e1a --- /dev/null +++ b/helm/values.yaml @@ -0,0 +1,74 @@ +image: + repository: mongo + tag: "8.0" + pullPolicy: IfNotPresent + + +statefulset: + replicas: 1 + podManagementPolicy: OrderedReady + updateStrategy: + type: RollingUpdate + + +auth: + enabled: true + rootUsername: root + rootPassword: verySecurePassword + database: user + username: user + password: securePassword + +persistence: + storageClass: + accessModes: + - ReadWriteOnce + size: 8Gi + + +service: + type: ClusterIP + port: 27017 + headless: + enabled: true + name: "{{ include \"mongo.name.headless\" . }}" + + +resources: + limits: + cpu: "1" + memory: 1Gi + requests: + cpu: 100m + memory: 256Mi + + +livenessProbe: + enabled: true + initialDelaySeconds: 30 + periodSeconds: 10 + timeoutSeconds: 5 + failureThreshold: 5 + successThreshold: 1 + +readinessProbe: + enabled: true + initialDelaySeconds: 5 + periodSeconds: 10 + timeoutSeconds: 5 + failureThreshold: 3 + successThreshold: 1 + + +securityContext: + enabled: true + fsGroup: 65534 + runAsUser: 65534 + runAsNonRoot: true + + +extraCommandLineArgs: "" + + +healthCheck: + command: ["/bin/sh", "-c", "mongosh --quiet --eval 'db.runCommand({ ping: 1 })' --username ${MONGO_INITDB_ROOT_USERNAME} --password ${MONGO_INITDB_ROOT_PASSWORD} --authenticationDatabase admin || exit 1" ]