From cd6ab34b9e2b09689977a928dfee1f885326f693 Mon Sep 17 00:00:00 2001 From: Daren Desjardins Date: Wed, 18 Jan 2023 13:21:49 -0800 Subject: [PATCH] Support external secrets for service tokens and xsrf Signed-off-by: Daren Desjardins --- README.md | 10 ++++++++++ templates/core/core-dpl.yaml | 15 +++++++++++++-- templates/core/core-secret.yaml | 4 ++++ templates/jobservice/jobservice-dpl.yaml | 9 ++++++++- templates/jobservice/jobservice-secrets.yaml | 2 ++ templates/registry/registry-dpl.yaml | 15 +++++++++++++-- templates/registry/registry-secret.yaml | 2 ++ values.yaml | 17 ++++++++++++++++- 8 files changed, 68 insertions(+), 6 deletions(-) diff --git a/README.md b/README.md index f30598cc0..d2e1c587e 100644 --- a/README.md +++ b/README.md @@ -227,10 +227,13 @@ The following table lists the configurable parameters of the Harbor chart and th | `core.configureUserSettings` | A JSON string to set in the environment variable `CONFIG_OVERWRITE_JSON` to configure user settings. See the [official docs](https://goharbor.io/docs/latest/install-config/configure-user-settings-cli/#configure-users-settings-using-an-environment-variable). | | | `core.quotaUpdateProvider` | The provider for updating project quota(usage), there are 2 options, redis or db. By default it is implemented by db but you can configure it to redis which can improve the performance of high concurrent pushing to the same project, and reduce the database connections spike and occupies. Using redis will bring up some delay for quota usage updation for display, so only suggest switch provider to redis if you were ran into the db connections spike around the scenario of high concurrent pushing to same project, no improvment for other scenes. | `db` | | `core.secret` | Secret is used when core server communicates with other components. If a secret key is not specified, Helm will generate one. Must be a string of 16 chars. | | +| `core.existingSecret` | Use an existing kubernetes secret for the core secret. The key must be `secret` | | | `core.secretName` | Fill the name of a kubernetes secret if you want to use your own TLS certificate and private key for token encryption/decryption. The secret must contain keys named: `tls.crt` - the certificate and `tls.key` - the private key. The default key pair will be used if it isn't set | | | `core.tokenKey` | PEM-formatted RSA private key used to sign service tokens. Only used if `core.secretName` is unset. If set, `core.tokenCert` MUST also be set. | | | `core.tokenCert` | PEM-formatted certificate signed by `core.tokenKey` used to validate service tokens. Only used if `core.secretName` is unset. If set, `core.tokenKey` MUST also be set. | | | `core.xsrfKey` | The XSRF key. Will be generated automatically if it isn't specified | | +| `core.existingXsrfSecret` | Use an existing kubernetes secret for the xsrf key specified | | +| `core.existingXsrfSecretKey` | Key within the existing secret for the xsrf key specified | `CSRF_KEY` | | `core.priorityClassName` | The priority class to run the pod as | | | `core.artifactPullAsyncFlushDuration` | The time duration for async update artifact pull_time and repository pull_count | | | `core.gdpr.deleteUser` | Enable GDPR compliant user delete | `false` | @@ -255,6 +258,9 @@ The following table lists the configurable parameters of the Harbor chart and th | `jobservice.podAnnotations` | Annotations to add to the jobservice pod | `{}` | | `jobservice.priorityClassName` | The priority class to run the pod as | | | `jobservice.secret` | Secret is used when job service communicates with other components. If a secret key is not specified, Helm will generate one. Must be a string of 16 chars. | | +| `jobservice.existingSecret` | Use an existing kubernetes secret for the jobservice secret | | +| `jobservice.existingSecretKey` | Key within the existing secret for the job service secret chars. | `JOBSERVICE_SECRET` | + | **Registry** | | | | `registry.registry.image.repository` | Repository for registry image | `goharbor/registry-photon` | | `registry.registry.image.tag` | Tag for registry image | `dev` | @@ -275,6 +281,10 @@ The following table lists the configurable parameters of the Harbor chart and th | `registry.secret` | Secret is used to secure the upload state from client and registry storage backend. See [official docs](https://github.com/docker/distribution/blob/master/docs/configuration.md#http). If a secret key is not specified, Helm will generate one. Must be a string of 16 chars. | | | `registry.credentials.username` | The username that harbor core uses internally to access the registry instance. Together with the `registry.credentials.password`, a htpasswd  is created. This is an alternative to providing `registry.credentials.htpasswdString`. For more details see [official docs](https://github.com/docker/distribution/blob/master/docs/configuration.md#htpasswd). | `harbor_registry_user` | | `registry.credentials.password` | The password that harbor core uses internally to access the registry instance. Together with the `registry.credentials.username`, a htpasswd  is created. This is an alternative to providing `registry.credentials.htpasswdString`. For more details see [official docs](https://github.com/docker/distribution/blob/master/docs/configuration.md#htpasswd). It is suggested you update this value before installation. | `harbor_registry_password` | +| `registry.existingSecret` | An existing kubernetes secret containing the registry secret. The key is defined by `existingSecretKey` chars. | | +| `registry.existingSecretKey` | The key in `registry.existingSecret` containing the registry secret chars. | | `REGISTRY_HTTP_SECRET` | +| `registry.credentials.username` | The username for accessing the registry instance, which is hosted by htpasswd auth mode. More details see [official docs](https://github.com/docker/distribution/blob/master/docs/configuration.md#htpasswd). | `harbor_registry_user` | +| `registry.credentials.password` | The password for accessing the registry instance, which is hosted by htpasswd auth mode. More details see [official docs](https://github.com/docker/distribution/blob/master/docs/configuration.md#htpasswd). It is suggested you update this value before installation. | `harbor_registry_password` | | `registry.credentials.existingSecret` | An existing secret containing the password for accessing the registry instance, which is hosted by htpasswd auth mode. More details see [official docs](https://github.com/docker/distribution/blob/master/docs/configuration.md#htpasswd). The key must be `REGISTRY_PASSWD` | `""` | | `registry.credentials.htpasswdString` | Login and password in htpasswd string format. Excludes `registry.credentials.username` and `registry.credentials.password`. May come in handy when integrating with tools like argocd or flux. This allows the same line to be generated each time the template is rendered, instead of the `htpasswd` function from helm, which generates different lines each time because of the salt. | undefined | | `registry.relativeurls` | If true, the registry returns relative URLs in Location headers. The client is responsible for resolving the correct URL. Needed if harbor is behind a reverse proxy | `false` | diff --git a/templates/core/core-dpl.yaml b/templates/core/core-dpl.yaml index 8d202498d..9a92b45a4 100644 --- a/templates/core/core-dpl.yaml +++ b/templates/core/core-dpl.yaml @@ -92,13 +92,17 @@ spec: - name: CORE_SECRET valueFrom: secretKeyRef: - name: {{ template "harbor.core" . }} + name: {{ default (include "harbor.core" .) .Values.core.existingSecret }} key: secret - name: JOBSERVICE_SECRET valueFrom: secretKeyRef: - name: "{{ template "harbor.jobservice" . }}" + name: {{ default (include "harbor.jobservice" .) .Values.jobservice.existingSecret }} + {{- if .Values.jobservice.existingSecret }} + key: {{ .Values.jobservice.existingSecretKey }} + {{- else }} key: JOBSERVICE_SECRET + {{- end }} {{- if .Values.existingSecretAdminPassword }} - name: HARBOR_ADMIN_PASSWORD valueFrom: @@ -130,6 +134,13 @@ spec: name: {{ .Values.registry.credentials.existingSecret }} key: REGISTRY_PASSWD {{- end }} + {{- if .Values.core.existingXsrfSecret }} + - name: CSRF_KEY + valueFrom: + secretKeyRef: + name: {{ .Values.core.existingXsrfSecret }} + key: {{ .Values.core.existingXsrfSecretKey }} + {{- end }} {{- with .Values.core.extraEnvVars }} {{- toYaml . | nindent 10 }} {{- end }} diff --git a/templates/core/core-secret.yaml b/templates/core/core-secret.yaml index 23b352b47..8577942eb 100644 --- a/templates/core/core-secret.yaml +++ b/templates/core/core-secret.yaml @@ -9,7 +9,9 @@ data: {{- if not .Values.existingSecretSecretKey }} secretKey: {{ .Values.secretKey | b64enc | quote }} {{- end }} + {{- if not .Values.core.existingSecret }} secret: {{ .Values.core.secret | default (randAlphaNum 16) | b64enc | quote }} + {{- end }} {{- if not .Values.core.secretName }} {{- $ca := genCA "harbor-token-ca" 365 }} tls.key: {{ .Values.core.tokenKey | default $ca.Key | b64enc | quote }} @@ -24,7 +26,9 @@ data: {{- if not .Values.registry.credentials.existingSecret }} REGISTRY_CREDENTIAL_PASSWORD: {{ .Values.registry.credentials.password | b64enc | quote }} {{- end }} + {{- if not .Values.core.existingXsrfSecret }} CSRF_KEY: {{ .Values.core.xsrfKey | default (randAlphaNum 32) | b64enc | quote }} + {{- end }} {{- if .Values.core.configureUserSettings }} CONFIG_OVERWRITE_JSON: {{ .Values.core.configureUserSettings | b64enc | quote }} {{- end }} diff --git a/templates/jobservice/jobservice-dpl.yaml b/templates/jobservice/jobservice-dpl.yaml index 32df97db7..e39e77e6e 100644 --- a/templates/jobservice/jobservice-dpl.yaml +++ b/templates/jobservice/jobservice-dpl.yaml @@ -87,8 +87,15 @@ spec: - name: CORE_SECRET valueFrom: secretKeyRef: - name: {{ template "harbor.core" . }} + name: {{ default (include "harbor.core" .) .Values.core.existingSecret }} key: secret + {{- if .Values.jobservice.existingSecret }} + - name: JOBSERVICE_SECRET + valueFrom: + secretKeyRef: + name: {{ .Values.jobservice.existingSecret }} + key: {{ .Values.jobservice.existingSecretKey }} + {{- end }} {{- if .Values.internalTLS.enabled }} - name: INTERNAL_TLS_ENABLED value: "true" diff --git a/templates/jobservice/jobservice-secrets.yaml b/templates/jobservice/jobservice-secrets.yaml index 3dfa6bd5e..d5054f6b3 100644 --- a/templates/jobservice/jobservice-secrets.yaml +++ b/templates/jobservice/jobservice-secrets.yaml @@ -6,7 +6,9 @@ metadata: {{ include "harbor.labels" . | indent 4 }} type: Opaque data: + {{- if not .Values.jobservice.existingSecret }} JOBSERVICE_SECRET: {{ .Values.jobservice.secret | default (randAlphaNum 16) | b64enc | quote }} + {{- end }} {{- if not .Values.registry.credentials.existingSecret }} REGISTRY_CREDENTIAL_PASSWORD: {{ .Values.registry.credentials.password | b64enc | quote }} {{- end }} diff --git a/templates/registry/registry-dpl.yaml b/templates/registry/registry-dpl.yaml index b9c97ff89..22b5b789a 100644 --- a/templates/registry/registry-dpl.yaml +++ b/templates/registry/registry-dpl.yaml @@ -200,16 +200,27 @@ spec: name: {{ .Values.persistence.imageChartStorage.s3.existingSecret }} {{- end }} env: + {{- if .Values.registry.existingSecret }} + - name: REGISTRY_HTTP_SECRET + valueFrom: + secretKeyRef: + name: {{ .Values.registry.existingSecret }} + key: {{ .Values.registry.existingSecretKey }} + {{- end }} - name: CORE_SECRET valueFrom: secretKeyRef: - name: {{ template "harbor.core" . }} + name: {{ default (include "harbor.core" .) .Values.core.existingSecret }} key: secret - name: JOBSERVICE_SECRET valueFrom: secretKeyRef: - name: {{ template "harbor.jobservice" . }} + name: {{ default (include "harbor.jobservice" .) .Values.jobservice.existingSecret }} + {{- if .Values.jobservice.existingSecret }} + key: {{ .Values.jobservice.existingSecretKey }} + {{- else }} key: JOBSERVICE_SECRET + {{- end }} {{- if has "registry" .Values.proxy.components }} - name: HTTP_PROXY value: "{{ .Values.proxy.httpProxy }}" diff --git a/templates/registry/registry-secret.yaml b/templates/registry/registry-secret.yaml index 529462906..8ef6ce447 100644 --- a/templates/registry/registry-secret.yaml +++ b/templates/registry/registry-secret.yaml @@ -6,7 +6,9 @@ metadata: {{ include "harbor.labels" . | indent 4 }} type: Opaque data: + {{- if not .Values.registry.existingSecret }} REGISTRY_HTTP_SECRET: {{ .Values.registry.secret | default (randAlphaNum 16) | b64enc | quote }} + {{- end }} {{- if not .Values.redis.external.existingSecret }} REGISTRY_REDIS_PASSWORD: {{ include "harbor.redis.password" . | b64enc | quote }} {{- end }} diff --git a/values.yaml b/values.yaml index f0deb1b12..e66f4df63 100644 --- a/values.yaml +++ b/values.yaml @@ -483,10 +483,13 @@ core: # the scenario of high concurrent pushing to same project, no improvment for other scenes. quotaUpdateProvider: db # Or redis # Secret is used when core server communicates with other components. - # If a secret key is not specified, Helm will generate one. + # If a secret key is not specified, Helm will generate one. Alternatively set existingSecret to use an existing secret # Must be a string of 16 chars. secret: "" # Fill in the name of a kubernetes secret if you want to use your own + # If using existingSecret, the key must be secret + existingSecret: "" + # Fill the name of a kubernetes secret if you want to use your own # TLS certificate and private key for token encryption/decryption. # The secret must contain keys named: # "tls.key" - the private key @@ -501,6 +504,10 @@ core: tokenCert: | # The XSRF key. Will be generated automatically if it isn't specified xsrfKey: "" + # If using existingSecret, the key is defined by core.existingXsrfSecretKey + existingXsrfSecret: "" + # If using existingSecret, the key + existingXsrfSecretKey: CSRF_KEY ## The priority class to run the pod as priorityClassName: # The time duration for async update artifact pull_time and repository @@ -559,6 +566,10 @@ jobservice: # If a secret key is not specified, Helm will generate one. # Must be a string of 16 chars. secret: "" + # Use an existing secret resource + existingSecret: "" + # Key within the existing secret for the job service secret + existingSecretKey: JOBSERVICE_SECRET ## The priority class to run the pod as priorityClassName: @@ -609,6 +620,10 @@ registry: # If a secret key is not specified, Helm will generate one. # Must be a string of 16 chars. secret: "" + # Use an existing secret resource + existingSecret: "" + # Key within the existing secret for the registry service secret + existingSecretKey: REGISTRY_HTTP_SECRET # If true, the registry returns relative URLs in Location headers. The client is responsible for resolving the correct URL. relativeurls: false credentials: