From 0dff97af3537bf4971979fdd21eff076b6a92983 Mon Sep 17 00:00:00 2001 From: Thomas von Dein Date: Thu, 21 Sep 2023 19:28:21 +0200 Subject: [PATCH] + helm chart --- charts/cm.yaml | 24 + charts/ephemerup/.helmignore | 21 + charts/ephemerup/Chart.yaml | 21 + charts/ephemerup/README.md | 121 +++++ charts/ephemerup/templates/NOTES.txt | 51 ++ charts/ephemerup/templates/_helpers.tpl | 8 + charts/ephemerup/templates/configmap.yaml | 36 ++ charts/ephemerup/templates/ingress.yaml | 63 +++ charts/ephemerup/templates/secrets.yaml | 18 + .../ephemerup/templates/service-monitor.yaml | 33 ++ charts/ephemerup/templates/service.yaml | 49 ++ charts/ephemerup/templates/statefulset.yaml | 130 +++++ charts/ephemerup/values.schema.json | 12 + charts/ephemerup/values.yaml | 480 ++++++++++++++++++ 14 files changed, 1067 insertions(+) create mode 100644 charts/cm.yaml create mode 100644 charts/ephemerup/.helmignore create mode 100644 charts/ephemerup/Chart.yaml create mode 100644 charts/ephemerup/README.md create mode 100644 charts/ephemerup/templates/NOTES.txt create mode 100644 charts/ephemerup/templates/_helpers.tpl create mode 100644 charts/ephemerup/templates/configmap.yaml create mode 100644 charts/ephemerup/templates/ingress.yaml create mode 100644 charts/ephemerup/templates/secrets.yaml create mode 100644 charts/ephemerup/templates/service-monitor.yaml create mode 100644 charts/ephemerup/templates/service.yaml create mode 100644 charts/ephemerup/templates/statefulset.yaml create mode 100644 charts/ephemerup/values.schema.json create mode 100644 charts/ephemerup/values.yaml diff --git a/charts/cm.yaml b/charts/cm.yaml new file mode 100644 index 0000000..3d62ae0 --- /dev/null +++ b/charts/cm.yaml @@ -0,0 +1,24 @@ +apiVersion: v1 +kind: ConfigMap +metadata: + name: eph-ephemerup-config + namespace: "eph" + labels: + app.kubernetes.io/name: ephemerup + helm.sh/chart: ephemerup-1.0.0 + app.kubernetes.io/instance: eph + app.kubernetes.io/managed-by: Helm + annotations: + app: ephemerup +data: + listen = "8080" + bodylimit = "1024" + super = "root" + mail = { + server = + port = + from = + password = + } + apicontexts = [ + ] diff --git a/charts/ephemerup/.helmignore b/charts/ephemerup/.helmignore new file mode 100644 index 0000000..f0c1319 --- /dev/null +++ b/charts/ephemerup/.helmignore @@ -0,0 +1,21 @@ +# 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 +*~ +# Various IDEs +.project +.idea/ +*.tmproj diff --git a/charts/ephemerup/Chart.yaml b/charts/ephemerup/Chart.yaml new file mode 100644 index 0000000..f804290 --- /dev/null +++ b/charts/ephemerup/Chart.yaml @@ -0,0 +1,21 @@ +apiVersion: v2 +name: ephemerup +description: | + A Helm chart for Ephemerup. + +type: application + +sources: + - https://github.com/tlinden/ephemerup + +version: 1.0.0 + +appVersion: "0.0.2" + +dependencies: + - name: common + repository: https://charts.bitnami.com/bitnami + tags: + - bitnami-common + version: 1.x.x +# icon: "" diff --git a/charts/ephemerup/README.md b/charts/ephemerup/README.md new file mode 100644 index 0000000..8b739af --- /dev/null +++ b/charts/ephemerup/README.md @@ -0,0 +1,121 @@ +# ephemerup + +A Helm chart for ephemerup + +## Source Code + +* + +## Requirements + +| Repository | Name | Version | +|------------|------|---------| +| https://charts.bitnami.com/bitnami | common | 1.x.x | + +## Values + +| Key | Type | Description | Default | +|---------------------------------------------------|--------|-----------------------------------------------------------|-----------------------| +| kubeVersion | string | | `""` | +| nameOverride | string | | `""` | +| fullnameOverride | string | | `""` | +| namespaceOverride | string | | `""` | +| commonLabels | object | | `{}` | +| commonAnnotations.app | string | | `"ephemerup"` | +| clusterDomain | string | | `"cluster.local"` | +| logLevel | string | | `"info"` | +| image.registry | string | | `"docker.io"` | +| image.repository | string | | `"tlinden/ephemerup"` | +| image.tag | string | | `"latest"` | +| image.pullPolicy | string | | `"IfNotPresent"` | +| image.pullSecrets | list | | `[]` | +| secrets | object | | `{}` | +| mountSecrets | list | | `[]` | +| env | list | | `[]` | +| config | object | Backup plans. For details, see [values.yaml](values.yaml) | `{}` | +| replicaCount | int | | `1` | +| sidecars | list | | `[]` | +| lifecycleHooks | object | | `{}` | +| podAnnotations | object | | `{}` | +| podLabels | object | | `{}` | +| updateStrategy.type | string | | `"RollingUpdate"` | +| podAffinityPreset | string | | `""` | +| podAntiAffinityPreset | string | | `"soft"` | +| nodeAffinityPreset.type | string | | `""` | +| nodeAffinityPreset.key | string | | `""` | +| nodeAffinityPreset.values | list | | `[]` | +| affinity | object | | `{}` | +| nodeSelector | object | | `{}` | +| tolerations | list | | `[]` | +| resources.limits.cpu | string | | `"500m"` | +| resources.limits.memory | string | | `"256Mi"` | +| resources.requests.cpu | string | | `"100m"` | +| resources.requests.memory | string | | `"128Mi"` | +| podSecurityContext.fsGroup | int | | `65534` | +| containerSecurityContext.enabled | bool | | `false` | +| containerSecurityContext.allowPrivilegeEscalation | bool | | `false` | +| containerSecurityContext.capabilities.drop[0] | string | | `"ALL"` | +| containerSecurityContext.privileged | bool | | `false` | +| containerSecurityContext.runAsUser | int | | `0` | +| containerSecurityContext.runAsNonRoot | bool | | `false` | +| livenessProbe.enabled | bool | | `true` | +| livenessProbe.initialDelaySeconds | int | | `5` | +| livenessProbe.timeoutSeconds | int | | `1` | +| livenessProbe.periodSeconds | int | | `20` | +| livenessProbe.failureThreshold | int | | `6` | +| livenessProbe.successThreshold | int | | `1` | +| readinessProbe.enabled | bool | | `true` | +| readinessProbe.initialDelaySeconds | int | | `5` | +| readinessProbe.timeoutSeconds | int | | `1` | +| readinessProbe.periodSeconds | int | | `20` | +| readinessProbe.failureThreshold | int | | `6` | +| readinessProbe.successThreshold | int | | `1` | +| startupProbe.enabled | bool | | `true` | +| startupProbe.initialDelaySeconds | int | | `10` | +| startupProbe.timeoutSeconds | int | | `1` | +| startupProbe.periodSeconds | int | | `20` | +| startupProbe.failureThreshold | int | | `6` | +| startupProbe.successThreshold | int | | `1` | +| customLivenessProbe | object | | `{}` | +| customStartupProbe | object | | `{}` | +| customReadinessProbe | object | | `{}` | +| service.type | string | | `"ClusterIP"` | +| service.ports.http | int | | `8090` | +| service.nodePorts.http | string | | `""` | +| service.clusterIP | string | | `""` | +| service.extraPorts | list | | `[]` | +| service.loadBalancerIP | string | | `""` | +| service.loadBalancerSourceRanges | list | | `[]` | +| service.externalTrafficPolicy | string | | `"Cluster"` | +| service.annotations | object | | `{}` | +| service.sessionAffinity | string | | `"None"` | +| service.sessionAffinityConfig | object | | `{}` | +| ingress.enabled | bool | | `false` | +| ingress.pathType | string | | `"Prefix"` | +| ingress.apiVersion | string | | `""` | +| ingress.hostname | string | | `"ephemerup.local"` | +| ingress.path | string | | `"/"` | +| ingress.annotations | object | | `{}` | +| ingress.tls | bool | | `false` | +| ingress.tlsSecretName | string | | `""` | +| ingress.extraPaths | list | | `[]` | +| ingress.selfSigned | bool | | `false` | +| ingress.ingressClassName | string | | `"nginx"` | +| ingress.extraHosts | list | | `[]` | +| ingress.extraTls | list | | `[]` | +| ingress.secrets | list | | `[]` | +| ingress.extraRules | list | | `[]` | +metrics.serviceMonitor.enabled | bool | `true` | | +| metrics.serviceMonitor.port | string | `"http"` | | +| metrics.serviceMonitor.namespace | string | `""` | | +| metrics.serviceMonitor.interval | string | `"30s"` | | +| metrics.serviceMonitor.scrapeTimeout | string | `"10s"` | | +| storage.longTerm | object | `{"name":"ephemerup-storage","spec":{"accessModes":["ReadWriteOnce"],"resources":{"requests":{"storage":"100Gi"}},"storageClassName":"standard"}}` | Persistent volume for backups, see `config.retention` | +| storage.tmp | object | `{"name":"ephemerup-tmp","spec":{"accessModes":["ReadWriteOnce"],"resources":{"requests":{"storage":"10Gi"}},"storageClassName":"standard"}}` | Persistent volume for temporary files | +| storage.restoreTmp.name | string | `"ephemerup-restore-tmp"` | | +| storage.restoreTmp.spec.accessModes[0] | string | `"ReadWriteOnce"` | | +| storage.restoreTmp.spec.resources.requests.storage | string | `"100Gi"` | | +| storage.restoreTmp.spec.storageClassName | string | `"standard"` | | + +---------------------------------------------- +Autogenerated from chart metadata using [helm-docs v1.11.0](https://github.com/norwoodj/helm-docs/releases/v1.11.0) diff --git a/charts/ephemerup/templates/NOTES.txt b/charts/ephemerup/templates/NOTES.txt new file mode 100644 index 0000000..2f66bb5 --- /dev/null +++ b/charts/ephemerup/templates/NOTES.txt @@ -0,0 +1,51 @@ +CHART NAME: {{ .Chart.Name }} +CHART VERSION: {{ .Chart.Version }} +APP VERSION: {{ .Chart.AppVersion }} + +** Please be patient while the chart is being deployed ** + +Application can be accessed through the following DNS name from within your cluster: + + {{ include "common.names.fullname" . }}.{{ include "common.names.namespace" . }}.svc.{{ .Values.clusterDomain }} (port {{ .Values.service.ports.http }}) + +To access Application from outside the cluster execute the following commands: + +{{- if .Values.ingress.enabled }} + +1. Get the Application URL and associate its hostname to your cluster external IP: + + export CLUSTER_IP=$(minikube ip) # On Minikube. Use: `kubectl cluster-info` on others K8s clusters + echo "Application URL: http{{ if .Values.ingress.tls }}s{{ end }}://{{ .Values.ingress.hostname }}" + echo "$CLUSTER_IP {{ .Values.ingress.hostname }}" | sudo tee -a /etc/hosts + +{{- else }} + +1. Get the Application URL by running these commands: + +{{- if contains "NodePort" .Values.service.type }} + + export NODE_PORT=$(kubectl get --namespace {{ include "common.names.namespace" . }} -o jsonpath="{.spec.ports[0].nodePort}" services {{ include "common.names.fullname" . }}) + export NODE_IP=$(kubectl get nodes --namespace {{ include "common.names.namespace" . }} -o jsonpath="{.items[0].status.addresses[0].address}") + echo "http://${NODE_IP}:${NODE_PORT}" + +{{- else if contains "LoadBalancer" .Values.service.type }} + + NOTE: It may take a few minutes for the LoadBalancer IP to be available. + You can watch the status of by running 'kubectl get --namespace {{ include "common.names.namespace" . }} svc -w {{ include "common.names.fullname" . }}' + + export SERVICE_PORT=$(kubectl get --namespace {{ include "common.names.namespace" . }} -o jsonpath="{.spec.ports[0].port}" services {{ include "common.names.fullname" . }}) + export SERVICE_IP=$(kubectl get svc --namespace {{ include "common.names.namespace" . }} {{ include "common.names.fullname" . }} -o jsonpath='{.status.loadBalancer.ingress[0].ip}') + echo "http://${SERVICE_IP}:${SERVICE_PORT}" + +{{- else if contains "ClusterIP" .Values.service.type }} + + export SERVICE_PORT=$(kubectl get --namespace {{ include "common.names.namespace" . }} -o jsonpath="{.spec.ports[0].port}" services {{ include "common.names.fullname" . }}) + kubectl port-forward --namespace {{ include "common.names.namespace" . }} svc/{{ include "common.names.fullname" . }} ${SERVICE_PORT}:${SERVICE_PORT} & + echo "http://127.0.0.1:${SERVICE_PORT}" + +{{- end }} +{{- end }} + +2. Access Application using the obtained URL. + +{{- include "common.warnings.rollingTag" .Values.image }} \ No newline at end of file diff --git a/charts/ephemerup/templates/_helpers.tpl b/charts/ephemerup/templates/_helpers.tpl new file mode 100644 index 0000000..7d2ec6f --- /dev/null +++ b/charts/ephemerup/templates/_helpers.tpl @@ -0,0 +1,8 @@ +{{/* + Return the proper image name +*/}} +{{- define "ephemerup.image" -}} +{{ include "common.images.image" (dict "imageRoot" .Values.image "global" .Values.global) }} +{{- end -}} + + diff --git a/charts/ephemerup/templates/configmap.yaml b/charts/ephemerup/templates/configmap.yaml new file mode 100644 index 0000000..6aa8831 --- /dev/null +++ b/charts/ephemerup/templates/configmap.yaml @@ -0,0 +1,36 @@ +{{- if (.Values.config) }} +apiVersion: v1 +kind: ConfigMap +metadata: + name: {{ template "common.names.fullname" . }}-config + namespace: {{ include "common.names.namespace" . | quote }} + labels: {{- include "common.labels.standard" . | nindent 4 }} + {{- if .Values.commonLabels }} + {{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }} + {{- end }} + {{- if .Values.commonAnnotations }} + annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }} + {{- end }} +data: + ephemerup.hcl: |- + listen = {{ .Values.config.listen | quote }} + bodylimit = {{ .Values.config.bodylimit | quote }} + {{- if .Values.config.url }} + url = {{ .Values.config.url | quote }} + {{- end }} + super = {{ .Values.config.super | quote }} + mail = { + server = {{ .Values.config.mail.server | quote }} + port = {{ .Values.config.mail.port | quote }} + from = {{ .Values.config.mail.from | quote }} + password = {{ .Values.config.password | quote }} + } + apicontexts = [ + {{- range $context := .Values.config.apicontexts }} + { + context = {{ $context.context | quote }} + key = {{ $context.key | quote }} + } + {{- end }} + ] +{{- end }} diff --git a/charts/ephemerup/templates/ingress.yaml b/charts/ephemerup/templates/ingress.yaml new file mode 100644 index 0000000..6164d19 --- /dev/null +++ b/charts/ephemerup/templates/ingress.yaml @@ -0,0 +1,63 @@ +{{- if .Values.ingress.enabled -}} +apiVersion: {{ include "common.capabilities.ingress.apiVersion" . }} +kind: Ingress +metadata: + name: {{ include "common.names.fullname" . }} + namespace: {{ include "common.names.namespace" . | quote }} + labels: {{- include "common.labels.standard" . | nindent 4 }} + {{- if .Values.commonLabels }} + {{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }} + {{- end }} + annotations: + {{- if .Values.ingress.certManager }} + kubernetes.io/tls-acme: "true" + {{- end }} + {{- if .Values.ingress.annotations }} + {{- include "common.tplvalues.render" ( dict "value" .Values.ingress.annotations "context" $) | nindent 4 }} + {{- end }} + {{- if .Values.commonAnnotations }} + {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }} + {{- end }} +spec: + {{- if and .Values.ingress.ingressClassName (include "common.ingress.supportsIngressClassname" .) }} + ingressClassName: {{ .Values.ingress.ingressClassName | quote }} + {{- end }} + rules: + {{- if .Values.ingress.hostname }} + - host: {{ .Values.ingress.hostname }} + http: + paths: + {{- if .Values.ingress.extraPaths }} + {{- toYaml .Values.ingress.extraPaths | nindent 10 }} + {{- end }} + - path: {{ .Values.ingress.path }} + {{- if eq "true" (include "common.ingress.supportsPathType" .) }} + pathType: {{ .Values.ingress.pathType }} + {{- end }} + backend: {{- include "common.ingress.backend" (dict "serviceName" (include "common.names.fullname" .) "servicePort" "http" "context" $) | nindent 14 }} + {{- end }} + {{- range .Values.ingress.extraHosts }} + - host: {{ .name }} + http: + paths: + - path: {{ default "/" .path }} + {{- if eq "true" (include "common.ingress.supportsPathType" $) }} + pathType: {{ default "ImplementationSpecific" .pathType }} + {{- end }} + backend: {{- include "common.ingress.backend" (dict "serviceName" (include "common.names.fullname" $) "servicePort" "http" "context" $) | nindent 14 }} + {{- end }} + {{- if .Values.ingress.extraRules }} + {{- include "common.tplvalues.render" (dict "value" .Values.ingress.extraRules "context" $) | nindent 4 }} + {{- end }} + {{- if or .Values.ingress.tls .Values.ingress.extraTls .Values.ingress.hosts }} + tls: + {{- if .Values.ingress.tls }} + - hosts: + - {{ .Values.ingress.hostname }} + secretName: {{ default (printf "%s-tls" .Values.ingress.hostname) .Values.ingress.tlsSecretName }} + {{- end }} + {{- if .Values.ingress.extraTls }} + {{- toYaml .Values.ingress.extraTls | nindent 4 }} + {{- end }} + {{- end }} +{{- end }} \ No newline at end of file diff --git a/charts/ephemerup/templates/secrets.yaml b/charts/ephemerup/templates/secrets.yaml new file mode 100644 index 0000000..c95b3a8 --- /dev/null +++ b/charts/ephemerup/templates/secrets.yaml @@ -0,0 +1,18 @@ +{{- if .Values.secrets }} +apiVersion: v1 +kind: Secret +metadata: + name: {{ template "common.names.fullname" . }}-config + namespace: {{ include "common.names.namespace" . | quote }} + labels: {{- include "common.labels.standard" . | nindent 4 }} + {{- if .Values.commonLabels }} + {{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }} + {{- end }} + {{- if .Values.commonAnnotations }} + annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }} + {{- end }} +data: +{{- with .Values.secrets }} +{{ toYaml . | nindent 2 }} +{{- end }} +{{ end }} \ No newline at end of file diff --git a/charts/ephemerup/templates/service-monitor.yaml b/charts/ephemerup/templates/service-monitor.yaml new file mode 100644 index 0000000..293112c --- /dev/null +++ b/charts/ephemerup/templates/service-monitor.yaml @@ -0,0 +1,33 @@ + +{{- if .Values.metrics.serviceMonitor.enabled }} +apiVersion: monitoring.coreos.com/v1 +kind: ServiceMonitor +metadata: + name: {{ include "common.names.fullname" . }}-sm + {{- if .Values.metrics.serviceMonitor.namespace }} + namespace: {{ .Values.metrics.serviceMonitor.namespace }} + {{- end }} + labels: {{- include "common.labels.standard" . | nindent 4 }} + {{- if .Values.commonLabels }} + {{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }} + {{- end }} + {{- if .Values.commonAnnotations }} + annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }} + {{- end }} +spec: + selector: + matchLabels: + {{- include "common.labels.standard" . | nindent 6 }} + endpoints: + - path: /metrics + port: {{ .Values.metrics.serviceMonitor.port }} + {{- if .Values.metrics.serviceMonitor.interval }} + interval: {{ .Values.metrics.serviceMonitor.interval }} + {{- end }} + {{- if .Values.metrics.serviceMonitor.scrapeTimeout }} + scrapeTimeout: {{ .Values.metrics.serviceMonitor.scrapeTimeout }} + {{- end }} + namespaceSelector: + matchNames: + - {{ .Release.Namespace }} +{{- end }} \ No newline at end of file diff --git a/charts/ephemerup/templates/service.yaml b/charts/ephemerup/templates/service.yaml new file mode 100644 index 0000000..2ae2000 --- /dev/null +++ b/charts/ephemerup/templates/service.yaml @@ -0,0 +1,49 @@ +apiVersion: v1 +kind: Service +metadata: + name: {{ include "common.names.fullname" . }} + namespace: {{ include "common.names.namespace" . | quote }} + labels: {{- include "common.labels.standard" . | nindent 4 }} + {{- if .Values.commonLabels }} + {{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }} + {{- end }} + annotations: + {{- if .Values.service.annotations }} + {{- include "common.tplvalues.render" ( dict "value" .Values.service.annotations "context" $) | nindent 4 }} + {{- end }} + {{- if .Values.commonAnnotations }} + {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }} + {{- end }} +spec: + type: {{ .Values.service.type }} + {{- if and .Values.service.clusterIP (eq .Values.service.type "ClusterIP") }} + clusterIP: {{ .Values.service.clusterIP }} + {{- end }} + {{- if and (eq .Values.service.type "LoadBalancer") (not (empty .Values.service.loadBalancerIP)) }} + loadBalancerIP: {{ .Values.service.loadBalancerIP }} + {{- end }} + {{- if and (eq .Values.service.type "LoadBalancer") (not (empty .Values.service.loadBalancerSourceRanges)) }} + loadBalancerSourceRanges: {{ .Values.service.loadBalancerSourceRanges }} + {{- end }} + {{- if or (eq .Values.service.type "LoadBalancer") (eq .Values.service.type "NodePort") }} + externalTrafficPolicy: {{ .Values.service.externalTrafficPolicy | quote }} + {{- end }} + {{- if .Values.service.sessionAffinity }} + sessionAffinity: {{ .Values.service.sessionAffinity }} + {{- end }} + {{- if .Values.service.sessionAffinityConfig }} + sessionAffinityConfig: {{- include "common.tplvalues.render" (dict "value" .Values.service.sessionAffinityConfig "context" $) | nindent 4 }} + {{- end }} + ports: + - name: http + port: {{ .Values.service.ports.http }} + targetPort: http + {{- if (and (or (eq .Values.service.type "NodePort") (eq .Values.service.type "LoadBalancer")) (not (empty .Values.service.nodePorts.http))) }} + nodePort: {{ .Values.service.nodePorts.http }} + {{- else if eq .Values.service.type "ClusterIP" }} + nodePort: null + {{- end }} + {{- if .Values.service.extraPorts }} + {{- include "common.tplvalues.render" (dict "value" .Values.service.extraPorts "context" $) | nindent 4 }} + {{- end }} + selector: {{- include "common.labels.matchLabels" . | nindent 4 }} \ No newline at end of file diff --git a/charts/ephemerup/templates/statefulset.yaml b/charts/ephemerup/templates/statefulset.yaml new file mode 100644 index 0000000..f8d4a06 --- /dev/null +++ b/charts/ephemerup/templates/statefulset.yaml @@ -0,0 +1,130 @@ +{{- $fullName := include "common.names.fullname" . -}} +apiVersion: {{ include "common.capabilities.statefulset.apiVersion" . }} +kind: StatefulSet +metadata: + name: {{ include "common.names.fullname" . }} + namespace: {{ include "common.names.namespace" . | quote }} + labels: {{- include "common.labels.standard" . | nindent 4 }} + {{- if .Values.commonLabels }} + {{- include "common.tplvalues.render" ( dict "value" .Values.commonLabels "context" $ ) | nindent 4 }} + {{- end }} + {{- if .Values.commonAnnotations }} + annotations: {{- include "common.tplvalues.render" ( dict "value" .Values.commonAnnotations "context" $ ) | nindent 4 }} + {{- end }} +spec: + serviceName: {{ include "common.names.fullname" . }} + replicas: {{ .Values.replicaCount }} + selector: + matchLabels: {{- include "common.labels.matchLabels" . | nindent 6 }} + template: + metadata: + annotations: + checksum/configMap: {{ toYaml .Values.config | sha256sum }} + {{- if .Values.podAnnotations }} + {{- include "common.tplvalues.render" (dict "value" .Values.podAnnotations "context" $) | nindent 8 }} + {{- end }} + labels: {{- include "common.labels.standard" . | nindent 8 }} + {{- if .Values.podLabels }} + {{- include "common.tplvalues.render" (dict "value" .Values.podLabels "context" $) | nindent 8 }} + {{- end }} + spec: + containers: + - name: ephemerup + image: {{ include "ephemerup.image" . }} + imagePullPolicy: {{ .Values.image.pullPolicy | quote}} + args: + - "-LogLevel={{ .Values.logLevel }}" + env: + {{- range $envVar := .Values.env }} + - name: {{ $envVar.name }} + value: {{ $envVar.value }} + {{- end }} + ports: + - name: http + containerPort: {{ .Values.service.ports.http }} + protocol: TCP + {{- if .Values.livenessProbe.enabled }} + livenessProbe: + httpGet: + port: http + path: /status + initialDelaySeconds: {{ .Values.livenessProbe.initialDelaySeconds }} + periodSeconds: {{ .Values.livenessProbe.periodSeconds }} + timeoutSeconds: {{ .Values.livenessProbe.timeoutSeconds }} + successThreshold: {{ .Values.livenessProbe.successThreshold }} + failureThreshold: {{ .Values.livenessProbe.failureThreshold }} + {{- else if .Values.customLivenessProbe }} + livenessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.customLivenessProbe "context" $) | nindent 12 }} + {{- end }} + {{- if .Values.readinessProbe.enabled }} + readinessProbe: + httpGet: + port: http + path: /status + initialDelaySeconds: {{ .Values.readinessProbe.initialDelaySeconds }} + periodSeconds: {{ .Values.readinessProbe.periodSeconds }} + timeoutSeconds: {{ .Values.readinessProbe.timeoutSeconds }} + successThreshold: {{ .Values.readinessProbe.successThreshold }} + failureThreshold: {{ .Values.readinessProbe.failureThreshold }} + {{- else if .Values.customReadinessProbe }} + readinessProbe: {{- include "common.tplvalues.render" (dict "value" .Values.customReadinessProbe "context" $) | nindent 12 }} + {{- end }} + {{- if .Values.startupProbe.enabled }} + startupProbe: + tcpSocket: + port: http + initialDelaySeconds: {{ .Values.startupProbe.initialDelaySeconds }} + periodSeconds: {{ .Values.startupProbe.periodSeconds }} + timeoutSeconds: {{ .Values.startupProbe.timeoutSeconds }} + successThreshold: {{ .Values.startupProbe.successThreshold }} + failureThreshold: {{ .Values.startupProbe.failureThreshold }} + {{- else if .Values.customStartupProbe }} + startupProbe: {{- include "common.tplvalues.render" (dict "value" .Values.customStartupProbe "context" $) | nindent 12 }} + {{- end }} + {{- if .Values.resources }} + resources: {{- toYaml .Values.resources | nindent 12 }} + {{- end }} + {{- if .Values.containerSecurityContext.enabled }} + securityContext: {{- omit .Values.containerSecurityContext "enabled" | toYaml | nindent 10 }} + {{- end }} + volumeMounts: + - name: "ephemerup-storage" + mountPath: "/storage" + - name: "ephemerup-tmp" + mountPath: "/tmp" + - name: "ephemerup-tmp" + mountPath: "/data" + - mountPath: "/config/ephemerup.hcl" + name: config + subPath: "ephemerup.hcl" + {{- range $secret := .Values.mountSecrets }} + - mountPath: "/secret/{{ $secret.name }}" + name: {{ $secret.name }} + {{- end }} + + securityContext: + {{ toYaml .Values.podSecurityContext | nindent 8 | trim }} + {{- if .Values.nodeSelector }} + nodeSelector: {{- include "common.tplvalues.render" ( dict "value" .Values.nodeSelector "context" $) | nindent 8 }} + {{- end }} + volumes: + - name: config + configMap: + name: {{ template "common.names.fullname" . }}-config + items: + - key: ephemerup.hcl + path: ephemerup.hcl + {{- range $secret := .Values.mountSecrets }} + - name: {{ $secret.name }} + secret: + secretName: {{ $secret.name }} + {{- end }} + volumeClaimTemplates: + - metadata: + name: {{ .Values.storage.longTerm.name }} + spec: + {{ toYaml .Values.storage.longTerm.spec | nindent 6 | trim }} + - metadata: + name: {{ .Values.storage.tmp.name }} + spec: + {{ toYaml .Values.storage.tmp.spec | nindent 6 | trim }} diff --git a/charts/ephemerup/values.schema.json b/charts/ephemerup/values.schema.json new file mode 100644 index 0000000..545568d --- /dev/null +++ b/charts/ephemerup/values.schema.json @@ -0,0 +1,12 @@ +{ + "$schema": "https://json-schema.org/draft-07/schema#", + "title": "Values schema", + "type": "object", + "properties": { + "replicaCount": { + "type": "integer", + "enum": [0, 1] + } + }, + "required": ["replicaCount"] +} \ No newline at end of file diff --git a/charts/ephemerup/values.yaml b/charts/ephemerup/values.yaml new file mode 100644 index 0000000..79f156f --- /dev/null +++ b/charts/ephemerup/values.yaml @@ -0,0 +1,480 @@ +## @section Common parameters +## + +## @param kubeVersion Override Kubernetes version +## +kubeVersion: "" +## @param nameOverride String to partially override aspnet-core.fullname +## +nameOverride: "" +## @param fullnameOverride String to fully override aspnet-core.fullname +## +fullnameOverride: "" +## @param namespaceOverride String to fully override common.names.namespace +## +namespaceOverride: "" +## @param commonLabels Labels to add to all deployed objects +## +commonLabels: {} +## @param commonAnnotations Annotations to add to all deployed objects +## +commonAnnotations: + app: ephemerup + +## @param clusterDomain Kubernetes cluster domain name +## +clusterDomain: cluster.local + +logLevel: info + +## +image: + registry: docker.io + repository: tlinden/ephemerup + tag: "latest" + ## Specify a imagePullPolicy + ## Defaults to 'Always' if image tag is 'latest', else set to 'IfNotPresent' + ## ref: https://kubernetes.io/docs/user-guide/images/#pre-pulling-images + ## + pullPolicy: IfNotPresent + ## Optionally specify an array of imagePullSecrets. + ## Secrets must be manually created in the namespace. + ## ref: https://kubernetes.io/docs/tasks/configure-pod-container/pull-image-private-registry/ + ## e.g: + ## pullSecrets: + ## - myRegistryKeySecretName + ## + pullSecrets: [] + +secrets: {} + +mountSecrets: [] +# - name: my-secret + +# Environment variables +env: [] +# - name: HTTPS_PROXY +# value: "http://localhost:3128" + +# Ephemerup configuration +config: + ## must be the same as in the service spec below + listen: 8080 + ## max bytes allowed to upload + bodylimit: 1024 + ## optional public visible url + #url: + ## root context which has all permissions + super: "root" + ## mail config + mail: + server: "localhost" + port: 25 + from: "root@localhost" + password: "" + ## context config, add more as needed + apicontexts: + - context: "root" + key: "0fddbff5d8010f81cd28a7d77f3e38981b13d6164c2fd6e1c3f60a4287630c37" + + +## @param replicaCount Number of application replicas to deploy +## +replicaCount: 1 + +## @param sidecars Add additional sidecar containers to the application pods +## e.g: +## sidecars: +## - name: your-image-name +## image: your-image +## imagePullPolicy: Always +## ports: +## - name: portname +## containerPort: 1234 +## +sidecars: [] + +## @param lifecycleHooks Add lifecycle hooks to the application deployment +## +lifecycleHooks: {} + +## @param podAnnotations Annotations for application pods +## ref: https://kubernetes.io/docs/concepts/overview/working-with-objects/annotations/ +## +podAnnotations: {} + +## @param podLabels Extra labels for application pods +## ref: https://kubernetes.io/docs/concepts/overview/working-with-objects/labels/ +## +podLabels: {} + +## @param updateStrategy.type Deployment strategy type +## ref: https://kubernetes.io/docs/concepts/workloads/controllers/statefulset/#update-strategies +## +updateStrategy: + ## StrategyType + ## Can be set to RollingUpdate or OnDelete + ## + type: RollingUpdate + +## @param podAffinityPreset Pod affinity preset. Ignored if `affinity` is set. Allowed values: `soft` or `hard` +## ref: https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node/#inter-pod-affinity-and-anti-affinity +## +podAffinityPreset: "" + +## @param podAntiAffinityPreset Pod anti-affinity preset. Ignored if `affinity` is set. Allowed values: `soft` or `hard` +## Ref: https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node/#inter-pod-affinity-and-anti-affinity +## +podAntiAffinityPreset: soft + +## Node affinity preset +## Ref: https://kubernetes.io/docs/concepts/scheduling-eviction/assign-pod-node/#node-affinity +## +nodeAffinityPreset: + ## @param nodeAffinityPreset.type Node affinity preset type. Ignored if `affinity` is set. Allowed values: `soft` or `hard` + ## + type: "" + ## @param nodeAffinityPreset.key Node label key to match. Ignored if `affinity` is set + ## + key: "" + ## @param nodeAffinityPreset.values Node label values to match. Ignored if `affinity` is set + ## E.g. + ## values: + ## - e2e-az1 + ## - e2e-az2 + ## + values: [] + + ## @param affinity Affinity for pod assignment +## Ref: https://kubernetes.io/docs/concepts/configuration/assign-pod-node/#affinity-and-anti-affinity +## NOTE: podAffinityPreset, podAntiAffinityPreset, and nodeAffinityPreset will be ignored when it's set +## +affinity: {} +## @param nodeSelector Node labels for pod assignment +## ref: https://kubernetes.io/docs/user-guide/node-selection/ +## + +nodeSelector: {} + +## @param tolerations Tolerations for pod assignment +## ref: https://kubernetes.io/docs/concepts/configuration/taint-and-toleration/ +## +tolerations: [] + +## application containers' resource requests and limits +## ref: https://kubernetes.io/docs/user-guide/compute-resources/ + +## @param resources.limits The resources limits for the application container +## @param resources.requests The requested resources for the application container +## +resources: + limits: + cpu: 500m + memory: 256Mi + requests: + cpu: 100m + memory: 128Mi + +## Configure Pods Security Context +## ref: https://kubernetes.io/docs/tasks/configure-pod-container/security-context/#set-the-security-context-for-a-pod +## @param podSecurityContext.fsGroup Set Security Context fsGroup +podSecurityContext: + fsGroup: 65534 + +## Configure Container Security Context (only main container) +## ref: https://kubernetes.io/docs/tasks/configure-pod-container/security-context/#set-the-security-context-for-a-container +## @param containerSecurityContext.enabled Enabled application containers' Security Context +## @param containerSecurityContext.runAsUser Set application container's Security Context runAsUser +## @param containerSecurityContext.runAsNonRoot Set container's Security Context runAsNonRoot +## +containerSecurityContext: + enabled: false + allowPrivilegeEscalation: false + capabilities: + drop: + - ALL + privileged: false + runAsUser: 0 + runAsNonRoot: false + +## Configure extra options for application containers' liveness and readiness probes +## ref: https://kubernetes.io/docs/tasks/configure-pod-container/configure-liveness-readiness-probes/#configure-probes +## @param livenessProbe.enabled Enable livenessProbe +## @param livenessProbe.initialDelaySeconds Initial delay seconds for livenessProbe +## @param livenessProbe.periodSeconds Period seconds for livenessProbe +## @param livenessProbe.timeoutSeconds Timeout seconds for livenessProbe +## @param livenessProbe.failureThreshold Failure threshold for livenessProbe +## @param livenessProbe.successThreshold Success threshold for livenessProbe +## +livenessProbe: + enabled: true + initialDelaySeconds: 5 + timeoutSeconds: 1 + periodSeconds: 20 + failureThreshold: 6 + successThreshold: 1 + +## @param readinessProbe.enabled Enable readinessProbe +## @param readinessProbe.initialDelaySeconds Initial delay seconds for readinessProbe +## @param readinessProbe.periodSeconds Period seconds for readinessProbe +## @param readinessProbe.timeoutSeconds Timeout seconds for readinessProbe +## @param readinessProbe.failureThreshold Failure threshold for readinessProbe +## @param readinessProbe.successThreshold Success threshold for readinessProbe +## +readinessProbe: + enabled: true + initialDelaySeconds: 5 + timeoutSeconds: 1 + periodSeconds: 20 + failureThreshold: 6 + successThreshold: 1 + +## Configure extra options for application containers' startup and readiness probes +## ref: https://kubernetes.io/docs/tasks/configure-pod-container/configure-startup-readiness-probes/#configure-probes +## @param startupProbe.enabled Enable startupProbe +## @param startupProbe.initialDelaySeconds Initial delay seconds for startupProbe +## @param startupProbe.periodSeconds Period seconds for startupProbe +## @param startupProbe.timeoutSeconds Timeout seconds for startupProbe +## @param startupProbe.failureThreshold Failure threshold for startupProbe +## @param startupProbe.successThreshold Success threshold for startupProbe +## +startupProbe: + enabled: true + initialDelaySeconds: 10 + timeoutSeconds: 1 + periodSeconds: 20 + failureThreshold: 6 + successThreshold: 1 + +## @param customLivenessProbe Custom livenessProbe that overrides the default one +## +customLivenessProbe: {} + +## @param customStartupProbe Custom startupProbe that overrides the default one +## +customStartupProbe: {} + +## @param customReadinessProbe Custom readinessProbe that overrides the default one +## +customReadinessProbe: {} + +## @section Traffic Exposure Parameters +## + +## application Service parameters. +## +service: + ## @param service.type application service type + ## + type: ClusterIP + ## @param service.ports.http application service HTTP port + ## + ports: + http: 8090 + ## @param service.nodePorts.http Node ports to expose + ## ref: https://kubernetes.io/docs/concepts/services-networking/service/#type-nodeport + ## + nodePorts: + http: "" + ## @param service.clusterIP application service Cluster IP + ## e.g.: + ## clusterIP: None + ## + clusterIP: "" + ## @param service.extraPorts Extra ports to expose (normally used with the `sidecar` value) + ## + extraPorts: [] + ## @param service.loadBalancerIP application service Load Balancer IP + ## ref: https://kubernetes.io/docs/concepts/services-networking/service/#type-loadbalancer + ## + loadBalancerIP: "" + ## @param service.loadBalancerSourceRanges application service Load Balancer sources + ## ref: https://kubernetes.io/docs/tasks/access-application-cluster/configure-cloud-provider-firewall/#restrict-access-for-loadbalancer-service + ## e.g: + ## loadBalancerSourceRanges: + ## - 10.10.10.0/24 + ## + loadBalancerSourceRanges: [] + ## @param service.externalTrafficPolicy application service external traffic policy + ## ref https://kubernetes.io/docs/tasks/access-application-cluster/create-external-load-balancer/#preserving-the-client-source-ip + ## + externalTrafficPolicy: Cluster + ## @param service.annotations Additional custom annotations for application service + ## + annotations: {} + ## @param service.sessionAffinity Session Affinity for Kubernetes service, can be "None" or "ClientIP" + ## If "ClientIP", consecutive client requests will be directed to the same Pod + ## ref: https://kubernetes.io/docs/concepts/services-networking/service/#virtual-ips-and-service-proxies + ## + sessionAffinity: None + ## @param service.sessionAffinityConfig Additional settings for the sessionAffinity + ## sessionAffinityConfig: + ## clientIP: + ## timeoutSeconds: 300 + ## + sessionAffinityConfig: {} + +## Configure the ingress resource that allows you to access the application app +## ref: https://kubernetes.io/docs/user-guide/ingress/ +## +ingress: + ## @param ingress.enabled Enable ingress record generation for application + ## + enabled: false + ## @param ingress.pathType Ingress path type + ## + pathType: Prefix + ## @param ingress.apiVersion Force Ingress API version (automatically detected if not set) + ## + apiVersion: "" + ## @param ingress.hostname Default host for the ingress resource, a host pointing to this will be created + ## + hostname: ephemerup.local + ## @param ingress.path Default path for the ingress record + ## + path: / + ## @param ingress.annotations Additional annotations for the Ingress resource. To enable certificate autogeneration, place here your cert-manager annotations. + ## For a full list of possible ingress annotations, please see + ## ref: https://github.com/kubernetes/ingress-nginx/blob/master/docs/user-guide/nginx-configuration/annotations.md + ## Use this parameter to set the required annotations for cert-manager, see + ## ref: https://cert-manager.io/docs/usage/ingress/#supported-annotations + ## + ## e.g: + ## annotations: + ## kubernetes.io/ingress.class: nginx + ## cert-manager.io/cluster-issuer: cluster-issuer-name + ## + annotations: {} + ## @param ingress.tls Enable TLS configuration for the host defined at `ingress.hostname` parameter + ## TLS certificates will be retrieved from a TLS secret with name: `{{- printf "%s-tls" .Values.ingress.hostname }}` + ## You can: + ## - Use the `ingress.secrets` parameter to create this TLS secret + ## - Rely on cert-manager to create it by setting the corresponding annotations + ## + tls: false + tlsSecretName: "" + ## @param ingress.extraPaths Any additional arbitrary paths that may need to be added to the ingress under the main host. + ## For example: The ALB ingress controller requires a special rule for handling SSL redirection. + ## extraPaths: + ## - path: /* + ## backend: + ## serviceName: ssl-redirect + ## servicePort: use-annotation + ## + extraPaths: [] + ## @param ingress.selfSigned Create a TLS secret for this ingress record using self-signed certificates generated by Helm + ## + selfSigned: false + ## @param ingress.ingressClassName IngressClass that will be be used to implement the Ingress (Kubernetes 1.18+) + ## This is supported in Kubernetes 1.18+ and required if you have more than one IngressClass marked as the default for your cluster . + ## ref: https://kubernetes.io/blog/2020/04/02/improvements-to-the-ingress-api-in-kubernetes-1.18/ + ## + ingressClassName: "nginx" + + ## @param ingress.extraHosts An array with additional hostname(s) to be covered with the ingress record + ## e.g: + ## extraHosts: + ## - name: aspnet-core.local + ## path: / + ## + extraHosts: [] + ## @param ingress.extraTls TLS configuration for additional hostname(s) to be covered with this ingress record + ## ref: https://kubernetes.io/docs/concepts/services-networking/ingress/#tls + ## e.g: + ## extraTls: + ## - hosts: + ## - aspnet-core.local + ## secretName: aspnet-core.local-tls + ## + extraTls: [] + ## @param ingress.secrets Custom TLS certificates as secrets + ## NOTE: 'key' and 'certificate' are expected in PEM format + ## NOTE: 'name' should line up with a 'secretName' set further up + ## If it is not set and you're using cert-manager, this is unneeded, as it will create a secret for you with valid certificates + ## If it is not set and you're NOT using cert-manager either, self-signed certificates will be created + ## It is also possible to create and manage the certificates outside of this helm chart + ## Please see README.md for more information + ## e.g: + ## secrets: + ## - name: aspnet-core.local-tls + ## key: |- + ## -----BEGIN RSA PRIVATE KEY----- + ## ... + ## -----END RSA PRIVATE KEY----- + ## certificate: |- + ## -----BEGIN CERTIFICATE----- + ## ... + ## -----END CERTIFICATE----- + ## + secrets: [] + ## @param ingress.extraRules Additional rules to be covered with this ingress record + ## ref: https://kubernetes.io/docs/concepts/services-networking/ingress/#ingress-rules + ## e.g: + ## extraRules: + ## - host: aspnet-core.local + ## http: + ## path: / + ## backend: + ## service: + ## name: aspnet-core-svc + ## port: + ## name: http + ## + extraRules: [] + +## @section RBAC parameters +## + +metrics: + serviceMonitor: + ## @param metrics.serviceMonitor.enabled Creates a Prometheus Operator ServiceMonitor (also requires `metrics.enabled` to be `true`) + ## + enabled: false + + port: "http" + ## @param metrics.serviceMonitor.namespace Namespace in which Prometheus is running + ## + namespace: "" + ## @param metrics.serviceMonitor.interval Interval at which metrics should be scraped. + ## ref: https://github.com/coreos/prometheus-operator/blob/master/Documentation/api.md#endpoint + ## e.g: + ## interval: 10s + ## + interval: "30s" + ## @param metrics.serviceMonitor.scrapeTimeout Timeout after which the scrape is ended + ## ref: https://github.com/coreos/prometheus-operator/blob/master/Documentation/api.md#endpoint + ## e.g: + ## scrapeTimeout: 10s + ## + scrapeTimeout: "10s" + +storage: + # -- Persistent volume for backups, see `config.retention` + longTerm: + name: "ephemerup-storage" + spec: + accessModes: + - ReadWriteOnce + resources: + requests: + storage: 10Gi + storageClassName: standard + # -- Persistent volume for temporary files + tmp: + name: "ephemerup-tmp" + spec: + accessModes: + - ReadWriteOnce + resources: + requests: + storage: 10Gi + storageClassName: standard + restoreTmp: + name: "ephemerup-restore-tmp" + spec: + accessModes: + - ReadWriteOnce + resources: + requests: + storage: 10Gi + storageClassName: standard