diff --git a/CHANGELOG.md b/CHANGELOG.md index 23b0e04119..21ef48b5be 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,6 +9,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Added +- Secrets consistency for the chart. Bugfixing [#1016](https://github.com/grafana/oncall/pull/1016) - Make it possible to completely delete a rotation oncall ([#1505](https://github.com/grafana/oncall/issues/1505)) - Polish rotation modal form oncall ([#1506](https://github.com/grafana/oncall/issues/1506)) - Quick actions when editing a schedule oncall ([#1507](https://github.com/grafana/oncall/issues/1507)) diff --git a/helm/oncall/README.md b/helm/oncall/README.md index e8d7917f4f..e55bc6faed 100644 --- a/helm/oncall/README.md +++ b/helm/oncall/README.md @@ -86,6 +86,112 @@ helm upgrade \ grafana/oncall ``` +### Passwords and external secrets + +As OnCall subcharts are Bitname charts, there is a common approach to secrets. Bundled charts allow specifying passwords +in values.yaml explicitly or as K8s secret value. OnCall chart refers either to secret created in sub-chart or +to specified external secret. +Similarly, if component chart is disabled, the password(s) can be supplied in `external` value +(e.g. externalMysql) explicitly or as K8s secret value. In the first case, the secret is created with the specified +value. In the second case the external secret is used. + +- If `.auth.existingSecret` is non-empty, then this secret is used. Secret keys are pre-defined by chart. +- If subchart supports password files and `.customPasswordFiles` dictionary is non-empty, then password files + are used. Dictionary keys are pre-defined per sub-chart. Password files are not supported by OnCall chart and should + not be used with bundled sub-charts. +- Passwords are specified via `auth` section values, e.g. `auth.password`. K8s secret is created. + - If `.auth.forcePassword` is `true`, then passwords MUST be specified. Otherwise, missing passwords + are generated. + +If external component is used instead of the bundled one: + +- If existingSecret within appropriate external component values is non-empty (e.g. `externalMysql.existingSecret`) then + it is used together with corresponding key names, e.g. `externalMysql.passwordKey`. +- Otherwise, corresponding password values are used, e.g. `externalMysql.password`. K8s secret is created by OnCall chart. + +Below is the summary for the dependent charts. + +MySQL/MariaDB: + +```yaml +database: + type: "mysql" # This is default +mariaDB: + enabled: true # Default + auth: + existingSecret: "" + forcePassword: false + # Secret name: `-mariadb` + rootPassword: "" # Secret key: mariadb-root-password + password: "" # Secret key: mariadb-password + replicationPassword: "" # Secret key: mariadb-replication-password +externalMysql: + password: "" + existingSecret: "" + passwordKey: "" +``` + +Postgres: + +```yaml +database: + type: postgresql +mariadb: + enabled: false # Must be set to false for Postgres +postgresql: + enabled: true # Must be set to true for bundled Postgres + auth: + existingSecret: "" + secretKeys: + adminPasswordKey: "" + userPasswordKey: "" # Not needed + replicationPasswordKey: "" # Not needed with disabled replication + # Secret name: `-postgresql` + postgresPassword: "" # password for admin user postgres. As non-admin user is not created, only this one is relevant. + password: "" # Not needed + replicationPassword: "" # Not needed with disabled replication +externalPostgresql: + user: "" + password: "" + existingSecret: "" + passwordKey: "" +``` + +Rabbitmq: + +```yaml +rabbitmq: + enabled: true + auth: + existingPasswordSecret: "" # Must contain `rabbitmq-password` key + existingErlangSecret: "" # Must contain `rabbitmq-erlang-cookie` key + # Secret name: `-rabbitmq` + password: "" + erlangCookie: "" +externalRabbitmq: + user: "" + password: "" + existingSecret: "" + passwordKey: "" + usernameKey: "" +``` + +Redis: + +```yaml +redis: + enabled: true + auth: + existingSecret: "" + existingSecretPasswordKey: "" + # Secret name: `-redis` + password: "" +externalRedis: + password: "" + existingSecret: "" + passwordKey: "" +``` + ### Set up Slack and Telegram You can set up Slack connection via following variables: diff --git a/helm/oncall/templates/_env.tpl b/helm/oncall/templates/_env.tpl index 895d374a44..49b3094c46 100644 --- a/helm/oncall/templates/_env.tpl +++ b/helm/oncall/templates/_env.tpl @@ -4,65 +4,65 @@ - name: SECRET_KEY valueFrom: secretKeyRef: - name: {{ template "snippet.oncall.secret.name" . }} - key: {{ template "snippet.oncall.secret.secretKey" . }} + name: {{ include "snippet.oncall.secret.name" . }} + key: {{ include "snippet.oncall.secret.secretKey" . | quote }} - name: MIRAGE_SECRET_KEY valueFrom: secretKeyRef: - name: {{ template "snippet.oncall.secret.name" . }} - key: {{ template "snippet.oncall.secret.mirageSecretKey" . }} + name: {{ include "snippet.oncall.secret.name" . }} + key: {{ include "snippet.oncall.secret.mirageSecretKey" . | quote }} - name: MIRAGE_CIPHER_IV - value: "{{ .Values.oncall.mirageCipherIV | default "1234567890abcdef" }}" + value: {{ .Values.oncall.mirageCipherIV | default "1234567890abcdef" | quote }} - name: DJANGO_SETTINGS_MODULE value: "settings.helm" - name: AMIXR_DJANGO_ADMIN_PATH value: "admin" - name: OSS value: "True" -{{- template "snippet.oncall.uwsgi" . }} +{{- include "snippet.oncall.uwsgi" . }} - name: BROKER_TYPE value: {{ .Values.broker.type | default "rabbitmq" }} - name: GRAFANA_API_URL - value: {{ include "snippet.grafana.url" . }} -{{- end -}} + value: {{ include "snippet.grafana.url" . | quote }} +{{- end }} {{- define "snippet.oncall.secret.name" -}} -{{- if .Values.oncall.secrets.existingSecret -}} -{{ .Values.oncall.secrets.existingSecret }} +{{ if .Values.oncall.secrets.existingSecret -}} + {{ .Values.oncall.secrets.existingSecret }} {{- else -}} -{{ template "oncall.fullname" . }} -{{- end -}} -{{- end -}} + {{ include "oncall.fullname" . }} +{{- end }} +{{- end }} {{- define "snippet.oncall.secret.secretKey" -}} -{{- if .Values.oncall.secrets.existingSecret -}} -{{ required "oncall.secrets.secretKey is required if oncall.secret.existingSecret is not empty" .Values.oncall.secrets.secretKey }} +{{ if .Values.oncall.secrets.existingSecret -}} + {{ required "oncall.secrets.secretKey is required if oncall.secret.existingSecret is not empty" .Values.oncall.secrets.secretKey }} {{- else -}} -SECRET_KEY -{{- end -}} -{{- end -}} + SECRET_KEY +{{- end }} +{{- end }} {{- define "snippet.oncall.secret.mirageSecretKey" -}} -{{- if .Values.oncall.secrets.existingSecret -}} -{{ required "oncall.secrets.mirageSecretKey is required if oncall.secret.existingSecret is not empty" .Values.oncall.secrets.mirageSecretKey }} +{{ if .Values.oncall.secrets.existingSecret -}} + {{ required "oncall.secrets.mirageSecretKey is required if oncall.secret.existingSecret is not empty" .Values.oncall.secrets.mirageSecretKey }} {{- else -}} -MIRAGE_SECRET_KEY -{{- end -}} -{{- end -}} + MIRAGE_SECRET_KEY +{{- end }} +{{- end }} {{- define "snippet.oncall.uwsgi" -}} -{{- if .Values.uwsgi -}} +{{- if .Values.uwsgi }} {{- range $key, $value := .Values.uwsgi }} - name: UWSGI_{{ $key | upper | replace "-" "_" }} value: {{ $value | quote }} - {{- end -}} -{{- end -}} -{{- end -}} + {{- end }} +{{- end }} +{{- end }} {{- define "snippet.oncall.slack.env" -}} -{{- if .Values.oncall.slack.enabled -}} - name: FEATURE_SLACK_INTEGRATION_ENABLED value: {{ .Values.oncall.slack.enabled | toString | title | quote }} +{{- if .Values.oncall.slack.enabled }} - name: SLACK_SLASH_COMMAND_NAME value: "/{{ .Values.oncall.slack.commandName | default "oncall" }}" {{- if .Values.oncall.slack.existingSecret }} @@ -70,17 +70,17 @@ MIRAGE_SECRET_KEY valueFrom: secretKeyRef: name: {{ .Values.oncall.slack.existingSecret }} - key: {{ required "oncall.slack.clientIdKey is required if oncall.slack.existingSecret is not empty" .Values.oncall.slack.clientIdKey }} + key: {{ required "oncall.slack.clientIdKey is required if oncall.slack.existingSecret is not empty" .Values.oncall.slack.clientIdKey | quote }} - name: SLACK_CLIENT_OAUTH_SECRET valueFrom: secretKeyRef: name: {{ .Values.oncall.slack.existingSecret }} - key: {{ required "oncall.slack.clientSecretKey is required if oncall.slack.existingSecret is not empty" .Values.oncall.slack.clientSecretKey }} + key: {{ required "oncall.slack.clientSecretKey is required if oncall.slack.existingSecret is not empty" .Values.oncall.slack.clientSecretKey | quote }} - name: SLACK_SIGNING_SECRET valueFrom: secretKeyRef: name: {{ .Values.oncall.slack.existingSecret }} - key: {{ required "oncall.slack.signingSecretKey is required if oncall.slack.existingSecret is not empty" .Values.oncall.slack.signingSecretKey }} + key: {{ required "oncall.slack.signingSecretKey is required if oncall.slack.existingSecret is not empty" .Values.oncall.slack.signingSecretKey | quote }} {{- else }} - name: SLACK_CLIENT_OAUTH_ID value: {{ .Values.oncall.slack.clientId | default "" | quote }} @@ -91,16 +91,13 @@ MIRAGE_SECRET_KEY {{- end }} - name: SLACK_INSTALL_RETURN_REDIRECT_HOST value: {{ .Values.oncall.slack.redirectHost | default (printf "https://%s" .Values.base_url) | quote }} -{{- else -}} -- name: FEATURE_SLACK_INTEGRATION_ENABLED - value: {{ .Values.oncall.slack.enabled | toString | title | quote }} -{{- end -}} -{{- end -}} +{{- end }} +{{- end }} {{- define "snippet.oncall.telegram.env" -}} -{{- if .Values.oncall.telegram.enabled -}} - name: FEATURE_TELEGRAM_INTEGRATION_ENABLED value: {{ .Values.oncall.telegram.enabled | toString | title | quote }} +{{- if .Values.oncall.telegram.enabled }} - name: TELEGRAM_WEBHOOK_HOST value: {{ .Values.oncall.telegram.webhookUrl | default "" | quote }} {{- if .Values.oncall.telegram.existingSecret }} @@ -108,366 +105,400 @@ MIRAGE_SECRET_KEY valueFrom: secretKeyRef: name: {{ .Values.oncall.telegram.existingSecret }} - key: {{ required "oncall.telegram.tokenKey is required if oncall.telegram.existingSecret is not empty" .Values.oncall.telegram.tokenKey }} + key: {{ required "oncall.telegram.tokenKey is required if oncall.telegram.existingSecret is not empty" .Values.oncall.telegram.tokenKey | quote }} {{- else }} - name: TELEGRAM_TOKEN value: {{ .Values.oncall.telegram.token | default "" | quote }} {{- end }} -{{- else -}} -- name: FEATURE_TELEGRAM_INTEGRATION_ENABLED - value: {{ .Values.oncall.telegram.enabled | toString | title | quote }} -{{- end -}} -{{- end -}} +{{- end }} +{{- end }} -{{- define "snippet.oncall.twilio.env" -}} -{{- with .Values.oncall.twilio -}} -{{- if .accountSid }} -- name: TWILIO_ACCOUNT_SID - value: {{ .accountSid | quote }} -{{- end -}} +{{- define "snippet.oncall.twilio.env" }} +{{- with .Values.oncall.twilio }} {{- if .existingSecret }} +- name: TWILIO_ACCOUNT_SID + valueFrom: + secretKeyRef: + name: {{ .existingSecret }} + key: {{ required "oncall.twilio.accountSid is required if oncall.twilio.existingSecret is not empty" .accountSid | quote }} - name: TWILIO_AUTH_TOKEN valueFrom: secretKeyRef: name: {{ .existingSecret }} - key: {{ required ".authTokenKey is required if .existingSecret is not empty" .authTokenKey }} + key: {{ required "oncall.twilio.authTokenKey is required if oncall.twilio.existingSecret is not empty" .authTokenKey | quote }} - name: TWILIO_NUMBER valueFrom: secretKeyRef: name: {{ .existingSecret }} - key: {{ required ".phoneNumberKey is required if .existingSecret is not empty" .phoneNumberKey }} + key: {{ required "oncall.twilio.phoneNumberKey is required if oncall.twilio.existingSecret is not empty" .phoneNumberKey | quote }} - name: TWILIO_VERIFY_SERVICE_SID valueFrom: secretKeyRef: name: {{ .existingSecret }} - key: {{ required ".verifySidKey is required if .existingSecret is not empty" .verifySidKey }} + key: {{ required "oncall.twilio.verifySidKey is required if oncall.twilio.existingSecret is not empty" .verifySidKey | quote }} - name: TWILIO_API_KEY_SID valueFrom: secretKeyRef: name: {{ .existingSecret }} - key: {{ required ".apiKeySidKey is required if .existingSecret is not empty" .apiKeySidKey }} + key: {{ required "oncall.twilio.apiKeySidKey is required if oncall.twilio.existingSecret is not empty" .apiKeySidKey | quote }} - name: TWILIO_API_KEY_SECRET valueFrom: secretKeyRef: name: {{ .existingSecret }} - key: {{ required ".apiKeySecretKey is required if .existingSecret is not empty" .apiKeySecretKey }} + key: {{ required "oncall.twilio.apiKeySecretKey is required if oncall.twilio.existingSecret is not empty" .apiKeySecretKey | quote }} {{- else }} +{{- if .accountSid }} +- name: TWILIO_ACCOUNT_SID + value: {{ .accountSid | quote }} +{{- end }} {{- if .authToken }} - name: TWILIO_AUTH_TOKEN value: {{ .authToken | quote }} -{{- end -}} +{{- end }} {{- if .phoneNumber }} - name: TWILIO_NUMBER value: {{ .phoneNumber | quote }} -{{- end -}} +{{- end }} {{- if .verifySid }} - name: TWILIO_VERIFY_SERVICE_SID value: {{ .verifySid | quote }} -{{- end -}} +{{- end }} {{- if .apiKeySid }} - name: TWILIO_API_KEY_SID value: {{ .apiKeySid | quote }} -{{- end -}} +{{- end }} {{- if .apiKeySecret }} - name: TWILIO_API_KEY_SECRET value: {{ .apiKeySecret | quote }} -{{- end -}} +{{- end }} +{{- end }} {{- if .limitPhone }} - name: PHONE_NOTIFICATIONS_LIMIT value: {{ .limitPhone | quote }} -{{- end -}} -{{- end -}} -{{- end -}} -{{- end -}} +{{- end }} +{{- end }} +{{- end }} -{{- define "snippet.celery.env" -}} +{{- define "snippet.celery.env" }} {{- if .Values.celery.worker_queue }} - name: CELERY_WORKER_QUEUE - value: {{ .Values.celery.worker_queue }} -{{- end -}} + value: {{ .Values.celery.worker_queue | quote }} +{{- end }} {{- if .Values.celery.worker_concurrency }} - name: CELERY_WORKER_CONCURRENCY value: {{ .Values.celery.worker_concurrency | quote }} -{{- end -}} +{{- end }} {{- if .Values.celery.worker_max_tasks_per_child }} - name: CELERY_WORKER_MAX_TASKS_PER_CHILD value: {{ .Values.celery.worker_max_tasks_per_child | quote }} -{{- end -}} +{{- end }} {{- if .Values.celery.worker_beat_enabled }} - name: CELERY_WORKER_BEAT_ENABLED value: {{ .Values.celery.worker_beat_enabled | quote }} -{{- end -}} +{{- end }} {{- if .Values.celery.worker_shutdown_interval }} - name: CELERY_WORKER_SHUTDOWN_INTERVAL - value: {{ .Values.celery.worker_shutdown_interval }} -{{- end -}} -{{- end -}} + value: {{ .Values.celery.worker_shutdown_interval | quote }} +{{- end }} +{{- end }} {{- define "snippet.grafana.url" -}} -{{- if .Values.externalGrafana.url -}} -{{- .Values.externalGrafana.url | quote }} -{{- else if .Values.grafana.enabled -}} -http://{{ include "oncall.grafana.fullname" . }} +{{ if .Values.grafana.enabled -}} + http://{{ include "oncall.grafana.fullname" . }} {{- else -}} -{{- required "externalGrafana.url is required when not grafana.enabled" .Values.externalGrafana.url | quote }} -{{- end -}} -{{- end -}} + {{ required "externalGrafana.url is required when not grafana.enabled" .Values.externalGrafana.url }} +{{- end }} +{{- end }} {{- define "snippet.mysql.env" -}} - name: MYSQL_HOST - value: {{ include "snippet.mysql.host" . }} + value: {{ include "snippet.mysql.host" . | quote }} - name: MYSQL_PORT - value: {{ include "snippet.mysql.port" . }} + value: {{ include "snippet.mysql.port" . | quote }} - name: MYSQL_DB_NAME - value: {{ include "snippet.mysql.db" . }} -{{- if and (not .Values.mariadb.enabled) .Values.externalMysql.existingSecret .Values.externalMysql.usernameKey (not .Values.externalMysql.user) }} + value: {{ include "snippet.mysql.db" . | quote }} - name: MYSQL_USER +{{- if and (not .Values.mariadb.enabled) .Values.externalMysql.existingSecret .Values.externalMysql.usernameKey (not .Values.externalMysql.user) }} valueFrom: secretKeyRef: name: {{ include "snippet.mysql.password.secret.name" . }} - key: {{ .Values.externalMysql.usernameKey }} + key: {{ .Values.externalMysql.usernameKey | quote }} {{- else }} -- name: MYSQL_USER - value: {{ include "snippet.mysql.user" . }} + value: {{ include "snippet.mysql.user" . | quote }} {{- end }} - name: MYSQL_PASSWORD valueFrom: secretKeyRef: name: {{ include "snippet.mysql.password.secret.name" . }} - key: {{ include "snippet.mysql.password.secret.key" . }} + key: {{ include "snippet.mysql.password.secret.key" . | quote }} {{- end }} {{- define "snippet.mysql.password.secret.name" -}} -{{- if and (not .Values.mariadb.enabled) .Values.externalMysql.password -}} -{{ include "oncall.fullname" . }}-mysql-external -{{- else if and (not .Values.mariadb.enabled) .Values.externalMysql.existingSecret -}} -{{ .Values.externalMysql.existingSecret }} +{{ if .Values.mariadb.enabled -}} + {{ if .Values.mariadb.auth.existingSecret -}} + {{ .Values.mariadb.auth.existingSecret }} + {{- else -}} + {{ include "oncall.mariadb.fullname" . }} + {{- end }} {{- else -}} -{{ include "oncall.mariadb.fullname" . }} -{{- end -}} -{{- end -}} + {{ if .Values.externalMysql.existingSecret -}} + {{ .Values.externalMysql.existingSecret }} + {{- else -}} + {{ include "oncall.fullname" . }}-mysql-external + {{- end }} +{{- end }} +{{- end }} {{- define "snippet.mysql.password.secret.key" -}} -{{- if and (not .Values.mariadb.enabled) .Values.externalMysql.passwordKey -}} -{{ .Values.externalMysql.passwordKey }} +{{ if and (not .Values.mariadb.enabled) .Values.externalMysql.existingSecret .Values.externalMysql.passwordKey -}} + {{ .Values.externalMysql.passwordKey }} {{- else -}} -mariadb-root-password -{{- end -}} -{{- end -}} + mariadb-root-password +{{- end }} +{{- end }} {{- define "snippet.mysql.host" -}} -{{- if and (not .Values.mariadb.enabled) .Values.externalMysql.host -}} -{{- required "externalMysql.host is required if not mariadb.enabled" .Values.externalMysql.host | quote }} +{{ if and (not .Values.mariadb.enabled) .Values.externalMysql.host -}} + {{ .Values.externalMysql.host }} {{- else -}} -{{ include "oncall.mariadb.fullname" . }} -{{- end -}} -{{- end -}} + {{ include "oncall.mariadb.fullname" . }} +{{- end }} +{{- end }} {{- define "snippet.mysql.port" -}} -{{- if and (not .Values.mariadb.enabled) .Values.externalMysql.port -}} -{{- required "externalMysql.port is required if not mariadb.enabled" .Values.externalMysql.port | quote }} +{{ if and (not .Values.mariadb.enabled) .Values.externalMysql.port -}} + {{ .Values.externalMysql.port }} {{- else -}} -"3306" -{{- end -}} -{{- end -}} + 3306 +{{- end }} +{{- end }} {{- define "snippet.mysql.db" -}} -{{- if and (not .Values.mariadb.enabled) .Values.externalMysql.db_name -}} -{{- required "externalMysql.db_name is required if not mariadb.enabled" .Values.externalMysql.db_name | quote}} +{{ if and (not .Values.mariadb.enabled) .Values.externalMysql.db_name -}} + {{ .Values.externalMysql.db_name }} {{- else -}} -{{- .Values.mariadb.auth.database | default "oncall" | quote -}} -{{- end -}} -{{- end -}} + {{ .Values.mariadb.auth.database | default "oncall" }} +{{- end }} +{{- end }} {{- define "snippet.mysql.user" -}} -{{- if and (not .Values.mariadb.enabled) .Values.externalMysql.user -}} -{{- .Values.externalMysql.user | quote }} +{{ if and (not .Values.mariadb.enabled) .Values.externalMysql.user -}} + {{ .Values.externalMysql.user }} {{- else -}} -{{- .Values.mariadb.auth.username | default "root" | quote -}} -{{- end -}} -{{- end -}} + {{ .Values.mariadb.auth.username | default "root" }} +{{- end }} +{{- end }} {{- define "snippet.postgresql.env" -}} - name: DATABASE_TYPE - value: {{ .Values.database.type }} + value: {{ .Values.database.type | quote }} - name: DATABASE_HOST - value: {{ include "snippet.postgresql.host" . }} + value: {{ include "snippet.postgresql.host" . | quote }} - name: DATABASE_PORT - value: {{ include "snippet.postgresql.port" . }} + value: {{ include "snippet.postgresql.port" . | quote }} - name: DATABASE_NAME - value: {{ include "snippet.postgresql.db" . }} + value: {{ include "snippet.postgresql.db" . | quote }} - name: DATABASE_USER - value: {{ include "snippet.postgresql.user" . }} + value: {{ include "snippet.postgresql.user" . | quote }} - name: DATABASE_PASSWORD valueFrom: secretKeyRef: name: {{ include "snippet.postgresql.password.secret.name" . }} - key: {{ include "snippet.postgresql.password.secret.key" . }} + key: {{ include "snippet.postgresql.password.secret.key" . | quote }} {{- end }} {{- define "snippet.postgresql.password.secret.name" -}} -{{- if and (not .Values.postgresql.enabled) .Values.externalPostgresql.password -}} -{{ include "oncall.fullname" . }}-postgresql-external -{{- else if and (not .Values.postgresql.enabled) .Values.externalPostgresql.existingSecret -}} -{{ .Values.externalPostgresql.existingSecret }} +{{ if .Values.postgresql.enabled -}} + {{ if .Values.postgresql.auth.existingSecret -}} + {{ .Values.postgresql.auth.existingSecret }} + {{- else -}} + {{ include "oncall.postgresql.fullname" . }} + {{- end }} {{- else -}} -{{ include "oncall.postgresql.fullname" . }} -{{- end -}} -{{- end -}} + {{ if .Values.externalPostgresql.existingSecret -}} + {{ .Values.externalPostgresql.existingSecret }} + {{- else -}} + {{ include "oncall.fullname" . }}-postgresql-external + {{- end }} +{{- end }} +{{- end }} {{- define "snippet.postgresql.password.secret.key" -}} -{{- if and (not .Values.postgresql.enabled) .Values.externalPostgresql.passwordKey -}} -{{ .Values.externalPostgresql.passwordKey }} -{{- else if .Values.postgresql.enabled -}} -{{ include "postgresql.userPasswordKey" .Subcharts.postgresql }} +{{ if .Values.postgresql.enabled -}} + {{ if .Values.postgresql.auth.existingSecret -}} + {{ required "postgresql.auth.secretKeys.adminPasswordKey is required if database.type=postgres and postgresql.enabled and postgresql.auth.existingSecret" .Values.postgresql.auth.secretKeys.adminPasswordKey }} + {{- else -}} + {{ include "postgresql.userPasswordKey" .Subcharts.postgresql }} + {{- end }} {{- else -}} -"postgres-password" -{{- end -}} -{{- end -}} + {{ if .Values.externalPostgresql.existingSecret -}} + {{ required "externalPostgresql.passwordKey is required if database.type=postgres and not postgresql.enabled and postgresql.auth.existingSecret" .Values.externalPostgresql.passwordKey }} + {{- else -}} + postgres-password + {{- end }} +{{- end }} +{{- end }} {{- define "snippet.postgresql.host" -}} -{{- if and (not .Values.postgresql.enabled) .Values.externalPostgresql.host -}} -{{- required "externalPostgresql.host is required if not postgresql.enabled" .Values.externalPostgresql.host | quote }} +{{ if not .Values.postgresql.enabled -}} + {{ required "externalPostgresql.host is required if database.type=postgres and not postgresql.enabled" .Values.externalPostgresql.host }} {{- else -}} -{{ include "oncall.postgresql.fullname" . }} -{{- end -}} -{{- end -}} + {{ include "oncall.postgresql.fullname" . }} +{{- end }} +{{- end }} {{- define "snippet.postgresql.port" -}} -{{- if and (not .Values.postgresql.enabled) .Values.externalPostgresql.port -}} -{{- required "externalPostgresql.port is required if not postgresql.enabled" .Values.externalPostgresql.port | quote }} +{{ if and (not .Values.postgresql.enabled) .Values.externalPostgresql.port -}} + {{ .Values.externalPostgresql.port }} {{- else -}} -"5432" -{{- end -}} -{{- end -}} + 5432 +{{- end }} +{{- end }} {{- define "snippet.postgresql.db" -}} -{{- if and (not .Values.postgresql.enabled) .Values.externalPostgresql.db_name -}} -{{- required "externalPostgresql.db_name is required if not postgresql.enabled" .Values.externalPostgresql.db_name | quote}} +{{ if not .Values.postgresql.enabled -}} + {{ .Values.externalPostgresql.db_name | default "oncall" }} {{- else -}} -{{- .Values.postgresql.auth.database | default "oncall" | quote -}} -{{- end -}} -{{- end -}} + {{ .Values.postgresql.auth.database | default "oncall" }} +{{- end }} +{{- end }} {{- define "snippet.postgresql.user" -}} -{{- if and (not .Values.postgresql.enabled) .Values.externalPostgresql.user -}} -{{- .Values.externalPostgresql.user | quote}} +{{ if and (not .Values.postgresql.enabled) -}} + {{ .Values.externalPostgresql.user | default "postgres" }} {{- else -}} -{{- .Values.postgresql.auth.username | default "postgres" | quote -}} -{{- end -}} -{{- end -}} + {{ .Values.postgresql.auth.username | default "postgres" }} +{{- end }} +{{- end }} -{{- define "snippet.rabbitmq.env" -}} +{{- define "snippet.rabbitmq.env" }} {{- if eq .Values.broker.type "rabbitmq" -}} -{{- if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.existingSecret .Values.externalRabbitmq.usernameKey (not .Values.externalRabbitmq.user) }} - name: RABBITMQ_USERNAME +{{- if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.existingSecret .Values.externalRabbitmq.usernameKey (not .Values.externalRabbitmq.user) }} valueFrom: secretKeyRef: name: {{ include "snippet.rabbitmq.password.secret.name" . }} - key: {{ .Values.externalRabbitmq.usernameKey }} + key: {{ .Values.externalRabbitmq.usernameKey | quote }} {{- else }} -- name: RABBITMQ_USERNAME - value: {{ include "snippet.rabbitmq.user" . }} + value: {{ include "snippet.rabbitmq.user" . | quote }} {{- end }} - name: RABBITMQ_PASSWORD valueFrom: secretKeyRef: name: {{ include "snippet.rabbitmq.password.secret.name" . }} - key: {{ include "snippet.rabbitmq.password.secret.key" . }} + key: {{ include "snippet.rabbitmq.password.secret.key" . | quote }} - name: RABBITMQ_HOST - value: {{ include "snippet.rabbitmq.host" . }} + value: {{ include "snippet.rabbitmq.host" . | quote }} - name: RABBITMQ_PORT - value: {{ include "snippet.rabbitmq.port" . }} + value: {{ include "snippet.rabbitmq.port" . | quote }} - name: RABBITMQ_PROTOCOL - value: {{ include "snippet.rabbitmq.protocol" . }} + value: {{ include "snippet.rabbitmq.protocol" . | quote }} - name: RABBITMQ_VHOST - value: {{ include "snippet.rabbitmq.vhost" . }} + value: {{ include "snippet.rabbitmq.vhost" . | quote }} +{{- end }} {{- end }} -{{- end -}} {{- define "snippet.rabbitmq.user" -}} -{{- if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.user -}} -{{- required "externalRabbitmq.user is required if not rabbitmq.enabled" .Values.externalRabbitmq.user | quote }} +{{ if not .Values.rabbitmq.enabled -}} + {{ required "externalRabbitmq.user is required if not rabbitmq.enabled" .Values.externalRabbitmq.user }} {{- else -}} -"user" -{{- end -}} -{{- end -}} + user +{{- end }} +{{- end }} {{- define "snippet.rabbitmq.host" -}} -{{- if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.host -}} -{{- required "externalRabbitmq.host is required if not rabbitmq.enabled" .Values.externalRabbitmq.host | quote }} +{{ if not .Values.rabbitmq.enabled -}} + {{ required "externalRabbitmq.host is required if not rabbitmq.enabled" .Values.externalRabbitmq.host }} {{- else -}} -{{ include "oncall.rabbitmq.fullname" . }} -{{- end -}} -{{- end -}} + {{ include "oncall.rabbitmq.fullname" . }} +{{- end }} +{{- end }} {{- define "snippet.rabbitmq.port" -}} -{{- if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.port -}} -{{- required "externalRabbitmq.port is required if not rabbitmq.enabled" .Values.externalRabbitmq.port | quote }} +{{ if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.port -}} + {{ required "externalRabbitmq.port is required if not rabbitmq.enabled" .Values.externalRabbitmq.port }} {{- else -}} -"5672" -{{- end -}} -{{- end -}} + 5672 +{{- end }} +{{- end }} {{- define "snippet.rabbitmq.protocol" -}} -{{- if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.protocol -}} -{{ .Values.externalRabbitmq.protocol | quote }} +{{ if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.protocol -}} + {{ .Values.externalRabbitmq.protocol }} {{- else -}} -"amqp" -{{- end -}} -{{- end -}} + amqp +{{- end }} +{{- end }} {{- define "snippet.rabbitmq.vhost" -}} -{{- if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.vhost -}} -{{ .Values.externalRabbitmq.vhost | quote }} -{{- else -}} -"" -{{- end -}} -{{- end -}} +{{ if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.vhost -}} + {{ .Values.externalRabbitmq.vhost }} +{{- end }} +{{- end }} {{- define "snippet.rabbitmq.password.secret.name" -}} -{{- if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.password -}} -{{ include "oncall.fullname" . }}-rabbitmq-external -{{- else if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.existingSecret -}} -{{ .Values.externalRabbitmq.existingSecret }} +{{ if .Values.rabbitmq.enabled -}} + {{ if .Values.rabbitmq.auth.existingPasswordSecret -}} + {{ .Values.rabbitmq.auth.existingPasswordSecret }} + {{- else -}} + {{ include "oncall.rabbitmq.fullname" . }} + {{- end }} {{- else -}} -{{ include "oncall.rabbitmq.fullname" . }} -{{- end -}} -{{- end -}} + {{ if .Values.externalRabbitmq.existingSecret -}} + {{ .Values.externalRabbitmq.existingSecret }} + {{- else -}} + {{ include "oncall.fullname" . }}-rabbitmq-external + {{- end }} +{{- end }} +{{- end }} {{- define "snippet.rabbitmq.password.secret.key" -}} -{{- if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.passwordKey -}} -{{ .Values.externalRabbitmq.passwordKey }} +{{ if and (not .Values.rabbitmq.enabled) .Values.externalRabbitmq.passwordKey -}} + {{ .Values.externalRabbitmq.passwordKey }} {{- else -}} -rabbitmq-password -{{- end -}} -{{- end -}} + rabbitmq-password +{{- end }} +{{- end }} {{- define "snippet.redis.host" -}} -{{- if and (not .Values.redis.enabled) .Values.externalRedis.host -}} -{{- required "externalRedis.host is required if not redis.enabled" .Values.externalRedis.host | quote }} +{{ if not .Values.redis.enabled -}} + {{ required "externalRedis.host is required if not redis.enabled" .Values.externalRedis.host | quote }} {{- else -}} -{{ include "oncall.redis.fullname" . }}-master -{{- end -}} -{{- end -}} + {{ include "oncall.redis.fullname" . }}-master +{{- end }} +{{- end }} {{- define "snippet.redis.password.secret.name" -}} -{{- if and (not .Values.redis.enabled) .Values.externalRedis.password -}} -{{ include "oncall.fullname" . }}-redis-external -{{- else if and (not .Values.redis.enabled) .Values.externalRedis.existingSecret -}} -{{ .Values.externalRedis.existingSecret }} +{{ if .Values.redis.enabled -}} + {{ if .Values.redis.auth.existingSecret -}} + {{ .Values.redis.auth.existingSecret }} + {{- else -}} + {{ include "oncall.redis.fullname" . }} + {{- end }} {{- else -}} -{{ include "oncall.redis.fullname" . }} -{{- end -}} -{{- end -}} + {{ if .Values.externalRedis.existingSecret -}} + {{ .Values.externalRedis.existingSecret }} + {{- else -}} + {{ include "oncall.fullname" . }}-redis-external + {{- end }} +{{- end }} +{{- end }} {{- define "snippet.redis.password.secret.key" -}} -{{- if and (not .Values.redis.enabled) .Values.externalRedis.passwordKey -}} -{{ .Values.externalRedis.passwordKey }} +{{ if .Values.redis.enabled -}} + {{ if .Values.redis.auth.existingSecret -}} + {{ required "redis.auth.existingSecretPasswordKey is required if redis.auth.existingSecret is non-empty" .Values.redis.auth.existingSecretPasswordKey }} + {{- else -}} + redis-password + {{- end }} {{- else -}} -redis-password -{{- end -}} -{{- end -}} + {{ if .Values.externalRedis.existingSecret -}} + {{ required "externalRedis.passwordKey is required if externalRedis.existingSecret is non-empty" .Values.externalRedis.passwordKey }} + {{- else -}} + redis-password + {{- end }} +{{- end }} +{{- end }} {{- define "snippet.redis.env" -}} - name: REDIS_HOST @@ -478,13 +509,13 @@ redis-password valueFrom: secretKeyRef: name: {{ include "snippet.redis.password.secret.name" . }} - key: {{ include "snippet.redis.password.secret.key" . }} + key: {{ include "snippet.redis.password.secret.key" . | quote}} {{- end }} {{- define "snippet.oncall.smtp.env" -}} -{{- if .Values.oncall.smtp.enabled -}} - name: FEATURE_EMAIL_INTEGRATION_ENABLED value: {{ .Values.oncall.smtp.enabled | toString | title | quote }} +{{- if .Values.oncall.smtp.enabled }} - name: EMAIL_HOST value: {{ .Values.oncall.smtp.host | quote }} - name: EMAIL_PORT @@ -503,14 +534,11 @@ redis-password value: {{ .Values.oncall.smtp.fromEmail | quote }} - name: EMAIL_NOTIFICATIONS_LIMIT value: {{ .Values.oncall.smtp.limitEmail | default "200" | quote }} -{{- else -}} -- name: FEATURE_EMAIL_INTEGRATION_ENABLED - value: {{ .Values.oncall.smtp.enabled | toString | title | quote }} -{{- end -}} +{{- end }} {{- end }} {{- define "snippet.oncall.exporter.env" -}} -{{- if .Values.oncall.exporter.enabled -}} +{{ if .Values.oncall.exporter.enabled -}} - name: FEATURE_PROMETHEUS_EXPORTER_ENABLED value: {{ .Values.oncall.exporter.enabled | toString | title | quote }} - name: PROMETHEUS_EXPORTER_SECRET @@ -522,5 +550,5 @@ redis-password {{- else -}} - name: FEATURE_PROMETHEUS_EXPORTER_ENABLED value: {{ .Values.oncall.exporter.enabled | toString | title | quote }} -{{- end -}} +{{- end }} {{- end }} diff --git a/helm/oncall/templates/celery/_deployment.tpl b/helm/oncall/templates/celery/_deployment.tpl index 7a8361dd5b..faafc5479a 100644 --- a/helm/oncall/templates/celery/_deployment.tpl +++ b/helm/oncall/templates/celery/_deployment.tpl @@ -75,4 +75,4 @@ spec: {{- end }} resources: {{- toYaml .Values.celery.resources | nindent 12 }} -{{- end}} \ No newline at end of file +{{- end}} diff --git a/helm/oncall/templates/celery/deployment-celery.yaml b/helm/oncall/templates/celery/deployment-celery.yaml index a9d49bf1e2..c33c98faec 100644 --- a/helm/oncall/templates/celery/deployment-celery.yaml +++ b/helm/oncall/templates/celery/deployment-celery.yaml @@ -1 +1 @@ -{{ include "template.oncall.celery.deployment" . }} \ No newline at end of file +{{ include "template.oncall.celery.deployment" . }} diff --git a/helm/oncall/templates/secrets.yaml b/helm/oncall/templates/secrets.yaml index aa1c86fe73..0db331d597 100644 --- a/helm/oncall/templates/secrets.yaml +++ b/helm/oncall/templates/secrets.yaml @@ -7,11 +7,11 @@ metadata: {{- include "oncall.labels" . | nindent 4 }} type: Opaque data: - {{ template "snippet.oncall.secret.secretKey" . }}: {{ randAlphaNum 40 | b64enc | quote }} - {{ template "snippet.oncall.secret.mirageSecretKey" . }}: {{ randAlphaNum 40 | b64enc | quote }} -{{- end }} + {{ include "snippet.oncall.secret.secretKey" . }}: {{ randAlphaNum 40 | b64enc | quote }} + {{ include "snippet.oncall.secret.mirageSecretKey" . }}: {{ randAlphaNum 40 | b64enc | quote }} --- -{{ if and (not .Values.mariadb.enabled) (eq .Values.database.type "mysql") (not .Values.externalMysql.existingSecret) -}} +{{- end }} +{{- if and (eq .Values.database.type "mysql") (not .Values.mariadb.enabled) (not .Values.externalMysql.existingSecret) }} apiVersion: v1 kind: Secret metadata: @@ -19,9 +19,19 @@ metadata: type: Opaque data: mariadb-root-password: {{ required "externalMysql.password is required if not mariadb.enabled and not externalMysql.existingSecret" .Values.externalMysql.password | b64enc | quote }} +--- {{- end }} +{{- if and (not .Values.postgresql.enabled) (eq .Values.database.type "postgresql") (not .Values.externalPostgresql.existingSecret) }} +apiVersion: v1 +kind: Secret +metadata: + name: {{ include "oncall.fullname" . }}-postgresql-external +type: Opaque +data: + postgres-password: {{ required "externalPostgresql.password is required if not postgresql.enabled and not externalPostgresql.existingSecret" .Values.externalPostgresql.password | b64enc | quote }} --- -{{ if and (eq .Values.broker.type "rabbitmq") (not .Values.rabbitmq.enabled) (not .Values.externalRabbitmq.existingSecret) -}} +{{- end }} +{{- if and (eq .Values.broker.type "rabbitmq") (not .Values.rabbitmq.enabled) (not .Values.externalRabbitmq.existingSecret) }} apiVersion: v1 kind: Secret metadata: @@ -29,9 +39,9 @@ metadata: type: Opaque data: rabbitmq-password: {{ required "externalRabbitmq.password is required if not rabbitmq.enabled and not externalRabbitmq.existingSecret" .Values.externalRabbitmq.password | b64enc | quote }} -{{- end }} --- -{{ if and (not .Values.redis.enabled) (not .Values.externalRedis.existingSecret) -}} +{{- end }} +{{- if and (not .Values.redis.enabled) (not .Values.externalRedis.existingSecret) }} apiVersion: v1 kind: Secret metadata: @@ -39,9 +49,9 @@ metadata: type: Opaque data: redis-password: {{ required "externalRedis.password is required if not redis.enabled and not externalRedis.existingSecret" .Values.externalRedis.password | b64enc | quote }} -{{- end }} --- -{{ if and .Values.oncall.smtp.enabled .Values.oncall.smtp.password -}} +{{- end }} +{{- if and .Values.oncall.smtp.enabled .Values.oncall.smtp.password }} apiVersion: v1 kind: Secret metadata: @@ -49,9 +59,9 @@ metadata: type: Opaque data: smtp-password: {{ .Values.oncall.smtp.password | b64enc | quote }} -{{- end }} --- -{{ if and .Values.oncall.exporter.enabled .Values.oncall.exporter.authToken -}} +{{- end }} +{{- if and .Values.oncall.exporter.enabled .Values.oncall.exporter.authToken }} apiVersion: v1 kind: Secret metadata: @@ -59,14 +69,5 @@ metadata: type: Opaque data: exporter-secret: {{ .Values.oncall.exporter.authToken | b64enc | quote }} -{{- end }} --- -{{ if and (not .Values.postgresql.enabled) (eq .Values.database.type "postgresql") (not .Values.externalPostgresql.existingSecret) -}} -apiVersion: v1 -kind: Secret -metadata: - name: {{ include "oncall.fullname" . }}-postgresql-external -type: Opaque -data: - postgres-password: {{ required "externalPostgresql.password is required if not postgresql.enabled and not externalPostgresql.existingSecret" .Values.externalPostgresql.password | b64enc | quote }} {{- end }} diff --git a/helm/oncall/tests/__snapshot__/wait_for_db_test.yaml.snap b/helm/oncall/tests/__snapshot__/wait_for_db_test.yaml.snap index 76d8cacea9..7d764bdef1 100644 --- a/helm/oncall/tests/__snapshot__/wait_for_db_test.yaml.snap +++ b/helm/oncall/tests/__snapshot__/wait_for_db_test.yaml.snap @@ -181,7 +181,7 @@ database.type=postgresql -> should create initContainer for PostgreSQL database: - name: DATABASE_TYPE value: postgresql - name: DATABASE_HOST - value: oncall-postgresql + value: some-postgresql-host - name: DATABASE_PORT value: "5432" - name: DATABASE_NAME @@ -192,7 +192,7 @@ database.type=postgresql -> should create initContainer for PostgreSQL database: valueFrom: secretKeyRef: key: postgres-password - name: oncall-postgresql + name: oncall-postgresql-external - name: RABBITMQ_USERNAME value: user - name: RABBITMQ_PASSWORD @@ -256,7 +256,7 @@ database.type=postgresql -> should create initContainer for PostgreSQL database: - name: DATABASE_TYPE value: postgresql - name: DATABASE_HOST - value: oncall-postgresql + value: some-postgresql-host - name: DATABASE_PORT value: "5432" - name: DATABASE_NAME @@ -267,7 +267,7 @@ database.type=postgresql -> should create initContainer for PostgreSQL database: valueFrom: secretKeyRef: key: postgres-password - name: oncall-postgresql + name: oncall-postgresql-external - name: RABBITMQ_USERNAME value: user - name: RABBITMQ_PASSWORD diff --git a/helm/oncall/tests/extra_env_test.yaml b/helm/oncall/tests/extra_env_test.yaml index 3c6e19d0e9..53c61c2570 100644 --- a/helm/oncall/tests/extra_env_test.yaml +++ b/helm/oncall/tests/extra_env_test.yaml @@ -76,6 +76,7 @@ tests: - celery/deployment-celery.yaml set: database.type: postgresql + postgresql.enabled: true env: SOME_VAR: some_value another_var: "another_value" @@ -97,6 +98,7 @@ tests: - celery/deployment-celery.yaml set: database.type: postgresql + postgresql.enabled: true env: - name: SOME_VAR value: some_value diff --git a/helm/oncall/tests/postgres_env_test.yaml b/helm/oncall/tests/postgres_env_test.yaml index bbacbe6eab..fc2a9ce2ec 100644 --- a/helm/oncall/tests/postgres_env_test.yaml +++ b/helm/oncall/tests/postgres_env_test.yaml @@ -10,6 +10,7 @@ tests: set: database.type: postgresql postgresql.enabled: false + externalPostgresql.host: custom-postgres-host asserts: - contains: path: spec.template.spec.containers[0].env @@ -35,7 +36,7 @@ tests: path: spec.template.spec.containers[0].env content: name: DATABASE_HOST - value: oncall-postgresql + value: custom-postgres-host - it: externalPostgresql -> should use external PostgreSQL custom settings set: diff --git a/helm/oncall/tests/postgres_password_env_test.yaml b/helm/oncall/tests/postgres_password_env_test.yaml index 997e6984d7..e35b146532 100644 --- a/helm/oncall/tests/postgres_password_env_test.yaml +++ b/helm/oncall/tests/postgres_password_env_test.yaml @@ -11,6 +11,7 @@ tests: set: database.type: postgresql postgresql.enabled: false + externalPostgresql.host: some-postgres-host asserts: - failedTemplate: errorMessage: externalPostgresql.password is required if not postgresql.enabled and not externalPostgresql.existingSecret @@ -26,6 +27,7 @@ tests: postgresql.enabled: false externalPostgresql: password: abcd123 + host: some-postgres-host asserts: - contains: path: spec.template.spec.containers[0].env @@ -57,6 +59,8 @@ tests: postgresql.enabled: false externalPostgresql: existingSecret: some-postgres-secret + host: some-postgres-host + passwordKey: postgres-password-key asserts: - contains: path: spec.template.spec.containers[0].env @@ -65,7 +69,7 @@ tests: valueFrom: secretKeyRef: name: some-postgres-secret - key: postgres-password + key: postgres-password-key - it: externalPostgresql.passwordKey -> should be used for existing secret templates: @@ -76,6 +80,7 @@ tests: database.type: postgresql postgresql.enabled: false externalPostgresql: + host: some-postgres-host existingSecret: some-postgres-secret passwordKey: postgres.key asserts: diff --git a/helm/oncall/tests/rabbitmq_env_test.yaml b/helm/oncall/tests/rabbitmq_env_test.yaml index a969ccd48e..9fdc6dc660 100644 --- a/helm/oncall/tests/rabbitmq_env_test.yaml +++ b/helm/oncall/tests/rabbitmq_env_test.yaml @@ -200,6 +200,7 @@ tests: broker.type: rabbitmq rabbitmq.enabled: false externalRabbitmq: + host: some-rabbitmq-host existingSecret: existing-secret passwordKey: password-key asserts: @@ -236,7 +237,7 @@ tests: path: spec.template.spec.containers[0].env content: name: RABBITMQ_HOST - value: oncall-rabbitmq + value: some-rabbitmq-host - contains: path: spec.template.spec.containers[0].env content: @@ -251,4 +252,19 @@ tests: path: spec.template.spec.containers[0].env content: name: RABBITMQ_VHOST - value: "" \ No newline at end of file + value: "" + - it: rabbitmq.enabled=false -> should fail if host is missing + templates: + - engine/deployment.yaml + - engine/job-migrate.yaml + - celery/deployment-celery.yaml + set: + broker.type: rabbitmq + rabbitmq.enabled: false + externalRabbitmq: + existingSecret: existing-secret + passwordKey: password-key + asserts: + - failedTemplate: + errorMessage: externalRabbitmq.host is required if not rabbitmq.enabled + template: engine/job-migrate.yaml diff --git a/helm/oncall/tests/redis_env_test.yaml b/helm/oncall/tests/redis_env_test.yaml index b1bc487131..5fc3739fb7 100644 --- a/helm/oncall/tests/redis_env_test.yaml +++ b/helm/oncall/tests/redis_env_test.yaml @@ -77,6 +77,16 @@ tests: key: redis-password name: oncall-redis + - it: redis.enabled=false -> should fail if host not set + set: + redis.enabled: false + externalRedis: + existingSecret: some-redis-secret + asserts: + - failedTemplate: + errorMessage: externalRedis.host is required if not redis.enabled + template: engine/job-migrate.yaml + - it: redis.enabled=false -> should fail if not externalRabbitmq.existingSecret or not externalRabbitmq.password templates: - engine/deployment.yaml diff --git a/helm/oncall/tests/redis_password_env_test.yaml b/helm/oncall/tests/redis_password_env_test.yaml index c5eff6a5d9..de8c8eeb0f 100644 --- a/helm/oncall/tests/redis_password_env_test.yaml +++ b/helm/oncall/tests/redis_password_env_test.yaml @@ -10,6 +10,7 @@ tests: - it: secrets -> should fail if externalRedis.password not set set: redis.enabled: false + externalRedis.host: some-redis-host asserts: - failedTemplate: errorMessage: externalRedis.password is required if not redis.enabled and not externalRedis.existingSecret @@ -23,6 +24,7 @@ tests: set: redis.enabled: false externalRedis: + host: some-redis-host password: abcd123 asserts: - contains: @@ -53,7 +55,9 @@ tests: set: redis.enabled: false externalRedis: + host: some-redis-host existingSecret: some-redis-secret + passwordKey: redis-password-key asserts: - contains: path: spec.template.spec.containers[0].env @@ -62,7 +66,7 @@ tests: valueFrom: secretKeyRef: name: some-redis-secret - key: redis-password + key: redis-password-key - it: externalRedis.passwordKey -> should be used for existing secret templates: @@ -72,6 +76,7 @@ tests: set: redis.enabled: false externalRedis: + host: some-redis-host existingSecret: some-redis-secret passwordKey: redis.key asserts: diff --git a/helm/oncall/tests/wait_for_db_test.yaml b/helm/oncall/tests/wait_for_db_test.yaml index a744962e0d..e43b1ef8cb 100644 --- a/helm/oncall/tests/wait_for_db_test.yaml +++ b/helm/oncall/tests/wait_for_db_test.yaml @@ -25,6 +25,7 @@ tests: - it: database.type=postgresql -> should create initContainer for PostgreSQL database set: database.type: postgresql + externalPostgresql.host: some-postgresql-host asserts: - contains: path: spec.template.spec.initContainers diff --git a/helm/oncall/values.yaml b/helm/oncall/values.yaml index 9c974780cc..bfaac90f3d 100644 --- a/helm/oncall/values.yaml +++ b/helm/oncall/values.yaml @@ -94,15 +94,15 @@ oncall: secrets: # Use existing secret. (secretKey and mirageSecretKey is required) existingSecret: "" - # the key in the secret containing secret key + # The key in the secret containing secret key secretKey: "" - # the key in the secret containing mirage secret key + # The key in the secret containing mirage secret key mirageSecretKey: "" - # slack configures the Grafana Oncall Slack ChatOps integration. + # Slack configures the Grafana Oncall Slack ChatOps integration. slack: - # enabled enable the Slack ChatOps integration for the Oncall Engine. + # Enable the Slack ChatOps integration for the Oncall Engine. enabled: false - # commandName sets the Slack bot slash-command + # Sets the Slack bot slash-command commandName: oncall # clientId configures the Slack app OAuth2 client ID. # api.slack.com/apps/ -> Basic Information -> App Credentials -> Client ID @@ -110,18 +110,18 @@ oncall: # clientSecret configures the Slack app OAuth2 client secret. # api.slack.com/apps/ -> Basic Information -> App Credentials -> Client Secret clientSecret: ~ - # signingSecret configures the Slack app signature secret used to sign + # signingSecret - configures the Slack app signature secret used to sign # requests comming from Slack. # api.slack.com/apps/ -> Basic Information -> App Credentials -> Signing Secret signingSecret: ~ # Use existing secret for clientId, clientSecret and signingSecret. # clientIdKey, clientSecretKey and signingSecretKey are required existingSecret: "" - # the key in the secret containing OAuth2 client ID + # The key in the secret containing OAuth2 client ID clientIdKey: "" - # the key in the secret containing OAuth2 client secret + # The key in the secret containing OAuth2 client secret clientSecretKey: "" - # the key in the secret containing the Slack app signature secret + # The key in the secret containing the Slack app signature secret signingSecretKey: "" # OnCall external URL redirectHost: ~ @@ -129,9 +129,9 @@ oncall: enabled: false token: ~ webhookUrl: ~ - # Use exsting secret. (tokenKey is required) + # Use existing secret. (tokenKey is required) existingSecret: "" - # the key in the secret containing Telegram token + # The key in the secret containing Telegram token tokenKey: "" smtp: enabled: false @@ -161,16 +161,19 @@ oncall: # Use existing secret for authToken, phoneNumber, verifySid, apiKeySid and apiKeySecret. existingSecret: "" # Twilio password to allow OnCall to send SMSes and make calls - # the key in the secret containing the auth token + # The key in the secret containing the auth token authTokenKey: "" - # the key in the secret containing the phone number + # The key in the secret containing the phone number phoneNumberKey: "" - # the key in the secret containing verify service sid + # The key in the secret containing verify service sid verifySidKey: "" - # the key in the secret containing api key sid + # The key in the secret containing api key sid apiKeySidKey: "" - # the key in the secret containing the api key secret + # The key in the secret containing the api key secret apiKeySecretKey: "" + # Phone notifications limit (the only non-secret value). + # TODO: rename to phoneNotificationLimit + limitPhone: # Whether to run django database migrations automatically migrate: @@ -252,6 +255,7 @@ mariadb: enabled: true auth: database: oncall + existingSecret: primary: extraEnvVars: - name: MARIADB_COLLATE @@ -273,11 +277,11 @@ externalMysql: db_name: user: password: - # use an existing secret for the mysql password - existingSecret: "" - # the key in the secret containing the mysql username + # Use an existing secret for the mysql password. + existingSecret: + # The key in the secret containing the mysql username usernameKey: - # the key in the secret containing the mysql password + # The key in the secret containing the mysql password passwordKey: # PostgreSQL is included into this release for the convenience. @@ -287,6 +291,7 @@ postgresql: enabled: false auth: database: oncall + existingSecret: # Make sure to create the database with the following parameters: # CREATE DATABASE oncall WITH ENCODING UTF8; @@ -296,9 +301,9 @@ externalPostgresql: db_name: user: password: - # use an existing secret for the database password - existingSecret: "" - # the key in the secret containing the database password + # Use an existing secret for the database password + existingSecret: + # The key in the secret containing the database password passwordKey: # RabbitMQ is included into this release for the convenience. @@ -306,6 +311,8 @@ externalPostgresql: # Set rabbitmq.enabled = false and configure externalRabbitmq rabbitmq: enabled: true + auth: + existingPasswordSecret: broker: type: rabbitmq @@ -317,24 +324,26 @@ externalRabbitmq: password: protocol: vhost: - # use an existing secret for the rabbitmq password - existingSecret: "" - # the key in the secret containing the rabbitmq password + # Use an existing secret for the rabbitmq password + existingSecret: + # The key in the secret containing the rabbitmq password passwordKey: "" - # the key in the secret containing the rabbitmq username + # The key in the secret containing the rabbitmq username usernameKey: username # Redis is included into this release for the convenience. # It is recommended to host it separately from this release redis: enabled: true + auth: + existingSecret: externalRedis: host: password: - # use an existing secret for the redis password - existingSecret: "" - # the key in the secret containing the redis password + # Use an existing secret for the redis password + existingSecret: + # The key in the secret containing the redis password passwordKey: # Grafana is included into this release for the convenience. @@ -355,6 +364,7 @@ grafana: - grafana-oncall-app externalGrafana: + # Example: https://grafana.mydomain.com url: nameOverride: ""