Merge pull request #372 from samuelattwood/main

Release Partner Charts
pull/374/head
Samuel Attwood 2022-03-18 12:11:06 -04:00 committed by GitHub
commit 48293f6cd5
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
106 changed files with 7036 additions and 0 deletions

BIN
assets/logos/ziti-host.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 50 KiB

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -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

View File

@ -0,0 +1,6 @@
dependencies:
- name: standard-defs
repository: https://btp-charts-stable.s3.amazonaws.com/charts/
version: 0.1.2
digest: sha256:b072a3f7726bb97088f486103c12d3c8c01d81b31e72bd972b93fbd61f4adb85
generated: "2021-10-09T05:31:25.295386816Z"

View File

@ -0,0 +1,20 @@
annotations:
catalog.cattle.io/certified: partner
catalog.cattle.io/display-name: Sextant
catalog.cattle.io/release-name: sextant
apiVersion: v2
appVersion: 2.1.8
dependencies:
- name: standard-defs
repository: file://./charts/standard-defs
description: Sextant automates the deployment and management of enterprise blockchain
infrastructure.
home: https://www.blockchaintp.com/sextant
icon: https://sextant-resources.s3.amazonaws.com/icons/large-logo-blue.svg
keywords:
- blockchain
- smart contracts
kubeVersion: '>=1.19-0'
name: sextant
type: application
version: 2.2.1700

View File

@ -0,0 +1,74 @@
# Sextant
This chart is the base chart to install BTP Sextant. By default it
installs the development version of Sextant. It's intended use is as
a dependency of other charts which install particular editions of the
software.
## Configuration
| field | description | type | default |
|-|-|-|-|
| `imagePullSecrets.enabled` | true if imagePullSecrets are required | boolean | false |
| `imagePullSecrets.value` | a list of named secret references of the form ```- name: secretName```| list | [] |
| `imagePullSecrets.createSecret.enabled` | true to create a image pull secret | boolean | false |
| `imagePullSecrets.createSecret.registryUrl` | the registry url | string | nil |
| `imagePullSecrets.createSecret.registryUser` | the username for the registry | string | nil |
| `imagePullSecrets.createSecret.registryPassword` | the password for the registry | string | nil |
| `replicaCount` | number of Sextant replicas to run | int | 1 |
| `logging` | default logging level | string | "1" |
| `ui.env` | environment variables to set in the UI container | map | nil |
| `ui.image` | UI image settings | map | N/A |
| `ui.image.repository` | UI image repository | string | "dev.catenasys.com:8083/blockchaintp/sextant" |
| `ui.image.tag` | UI image tag | string | "latest" |
| `ui.image.pullPolicy` | UI image pull policy | string | "IfNotPresent" |
| `ui.resources` | UI resources | map | nil |
| `api.env` | API environment settings | map | N/A |
| `api.image` | API image settings | map | N/A |
| `api.image.repository` | API image repository | string | "dev.catenasys.com:8083/blockchaintp/sextant-api" |
| `api.image.tag` | API image tag | string | "latest" |
| `api.image.pullPolicy` | API image pull policy | string | "IfNotPresent" |
| `api.resources` | UI resources | map | nil |
| `noxy.env` | Noxy environment variables | map | N/A |
| `noxy.image` | noxy image settings | map | N/A |
| `noxy.image.repository` | NOXY image repository | string | "dev.catenasys.com:8083/blockchaintp/noxy" |
| `noxy.image.tag` | noxy image tag | string | "latest" |
| `noxy.image.pullPolicy` | API image pull policy | string | "IfNotPresent" |
| `noxy.resources` | UI resources | map | nil |
| `serviceAccount.create` | if true create the service account | boolean | true |
| `serviceAccount.name` | name of the service account for sextant | string | nil |
| `postgres.enabled` | if true create an internal postgres instance | boolean | true |
| `postgres.env` | postgres environment variables | map | N/A |
| `postgres.image.repository` | postgres image repository | string | "postgres" |
| `postgres.image.tag` | postgres image tag | string | "11" |
| `postgres.user` | user for the postgres database | string | "postgres" |
| `postgres.host` | host for the postgres database | string | "localhost" |
| `postgres.database` | database for the postgres database | string | "postgres" |
| `postgres.port` | port for the postgres database | int | 5432 |
| `postgres.password` | password for the postgres database | string | "postgres" |
| `postgres.existingPasswordSecret` | name of a secret containing the postgres password | string | nil |
| `postgres.existingPasswordSecret` | name of the key in a secret containing the postgres password | string | password |
| `postgres.tls` | postgres TLS configuration | string | nil |
| `postgres.persistence` | postgres persistence settings | map | N/A |
| `postgres.persistence.enabled` | if true allocate a PVC for the postgres instance | boolean | false |
| `postgres.persistence.annotations` | any custom annotations to the postgres PVC's | map | {} |
| `postgres.persistence.accessModes` | postgres PVC access modes | list | [ "ReadWriteOnce" ] |
| `postgres.persistence.storageClass` | postgres PVC storageClass | string | nil |
| `postgres.persistence.size` | postgres PVC volume size | string | "40Gi" |
| `postgres.resources` | UI resources | map | nil |
| `service.type` | Sextant service type | string | ClusterIP |
| `service.port` | Sextant service port | int | 8000 |
| `ingress.apiVersion` | if necessary the apiVersion of the ingress may be overridden | "" |
| `ingress.enabled` | true to enable the ingress to the main service rest-api | false |
| `ingress.certManager` | true to enable the acme certmanager for this ingress | false |
| `ingress.hostname` | primary hostname for the ingress | false |
| `ingress.path` | path for the ingress's primary hostname | / |
| `ingress.pathType` | pathType for the ingress's primary hostname | nil |
| `ingress.annotations` | annotations for the ingress | {} |
| `ingress.tls` | true to enable tls on the ingress with a secrete at hostname-tls | false(truthy) |
| `ingress.extraHosts` | list of extra hosts to add to the ingress | [] |
| `ingress.extraPaths` | list of extra paths to add to the primary host of the ingress | [] |
| `ingress.extraTls` | list of extra tls entries | [] |
| `ingress.hosts` | a list of host and path lists to publish in the ingress (deprecated)| map | {} |
| `extraVolumes` | a list of additional volumes to add to all StatefulSets, Deployments, and DaemonSets | `[]` |
| `extraVolumeMounts` | a list of additional volume mounts to add to all StatefulSet, Deployment, and DaemonSet containers | `[]` |

View File

@ -0,0 +1,24 @@
# Product Overview
__Sextant Community Edition__ focuses on two key areas:
Distributed Ledgers: Sextant automates the deployment and management of enterprise blockchain infrastructure, and currently supports the open-source Hyperledger Besu and Hyperledger Sawtooth distributed ledgers.
Smart Contracts: Sextant accelerates the adoption of Daml, an open-source smart contract language and application framework, by simplifying the deployment and management of the Daml runtime environment on distributed ledgers as well as centralized alternatives.
## License
Use of the Sextant Community Edition is governed by our
[Marketplace EULA](https://sextant-resources.s3.amazonaws.com/agreements/Blockchain+Technology+Partners+Limited+(Marketplace)+End+User+License+Agreement.pdf)
with the exception of Daml support which is subject to
our [Evaluation EULA](https://sextant-resources.s3.amazonaws.com/agreements/Blockchain+Technology+Partners+Limited+(Evaluation)+End+User+License+Agreement.pdf)
Find out more at [blockchaintp.com/sextant](http://blockchaintp.com/sextant)
For documentation visit [docs.blockchaintp.com](http://docs.blockchaintp.com)
### *Important*
*To install Sextant you will need credentials supplied by BTP.*
Please complete [this form](https://www.blockchaintp.com/sextant/suse-rancher) and we will provide you with the credentials required to launch Sextant Community Edition.

View File

@ -0,0 +1,6 @@
dependencies:
- name: common
repository: https://charts.bitnami.com/bitnami
version: 1.8.0
digest: sha256:4b6f60ea1981a1b98332e0149289002fe0f9ebf401de1ec19c8baaaf6b0d4b88
generated: "2021-09-02T01:05:15.012803203Z"

View File

@ -0,0 +1,10 @@
apiVersion: v2
appVersion: 0.1.0
dependencies:
- name: common
repository: https://charts.bitnami.com/bitnami
version: ~1.8.0
description: BTP Standard Template definitions and dependencies
name: standard-defs
type: library
version: 0.1.2

View File

@ -0,0 +1,22 @@
# 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
.vscode/

View File

@ -0,0 +1,23 @@
annotations:
category: Infrastructure
apiVersion: v2
appVersion: 1.8.0
description: A Library Helm Chart for grouping common logic between bitnami charts.
This chart is not deployable by itself.
home: https://github.com/bitnami/charts/tree/master/bitnami/common
icon: https://bitnami.com/downloads/logos/bitnami-mark.png
keywords:
- common
- helper
- template
- function
- bitnami
maintainers:
- email: containers@bitnami.com
name: Bitnami
name: common
sources:
- https://github.com/bitnami/charts
- http://www.bitnami.com/
type: library
version: 1.8.0

View File

@ -0,0 +1,327 @@
# Bitnami Common Library Chart
A [Helm Library Chart](https://helm.sh/docs/topics/library_charts/#helm) for grouping common logic between bitnami charts.
## TL;DR
```yaml
dependencies:
- name: common
version: 0.x.x
repository: https://charts.bitnami.com/bitnami
```
```bash
$ helm dependency update
```
```yaml
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ include "common.names.fullname" . }}
data:
myvalue: "Hello World"
```
## Introduction
This chart provides a common template helpers which can be used to develop new charts using [Helm](https://helm.sh) package manager.
Bitnami charts can be used with [Kubeapps](https://kubeapps.com/) for deployment and management of Helm Charts in clusters. This Helm chart has been tested on top of [Bitnami Kubernetes Production Runtime](https://kubeprod.io/) (BKPR). Deploy BKPR to get automated TLS certificates, logging and monitoring for your applications.
## Prerequisites
- Kubernetes 1.12+
- Helm 3.1.0
## Parameters
The following table lists the helpers available in the library which are scoped in different sections.
### Affinities
| Helper identifier | Description | Expected Input |
|-------------------------------|------------------------------------------------------|------------------------------------------------|
| `common.affinities.node.soft` | Return a soft nodeAffinity definition | `dict "key" "FOO" "values" (list "BAR" "BAZ")` |
| `common.affinities.node.hard` | Return a hard nodeAffinity definition | `dict "key" "FOO" "values" (list "BAR" "BAZ")` |
| `common.affinities.pod.soft` | Return a soft podAffinity/podAntiAffinity definition | `dict "component" "FOO" "context" $` |
| `common.affinities.pod.hard` | Return a hard podAffinity/podAntiAffinity definition | `dict "component" "FOO" "context" $` |
### Capabilities
| Helper identifier | Description | Expected Input |
|----------------------------------------------|------------------------------------------------------------------------------------------------|-------------------|
| `common.capabilities.kubeVersion` | Return the target Kubernetes version (using client default if .Values.kubeVersion is not set). | `.` Chart context |
| `common.capabilities.cronjob.apiVersion` | Return the appropriate apiVersion for cronjob. | `.` Chart context |
| `common.capabilities.deployment.apiVersion` | Return the appropriate apiVersion for deployment. | `.` Chart context |
| `common.capabilities.statefulset.apiVersion` | Return the appropriate apiVersion for statefulset. | `.` Chart context |
| `common.capabilities.ingress.apiVersion` | Return the appropriate apiVersion for ingress. | `.` Chart context |
| `common.capabilities.rbac.apiVersion` | Return the appropriate apiVersion for RBAC resources. | `.` Chart context |
| `common.capabilities.crd.apiVersion` | Return the appropriate apiVersion for CRDs. | `.` Chart context |
| `common.capabilities.policy.apiVersion` | Return the appropriate apiVersion for policy | `.` Chart context |
| `common.capabilities.supportsHelmVersion` | Returns true if the used Helm version is 3.3+ | `.` Chart context |
### Errors
| Helper identifier | Description | Expected Input |
|-----------------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-------------------------------------------------------------------------------------|
| `common.errors.upgrade.passwords.empty` | It will ensure required passwords are given when we are upgrading a chart. If `validationErrors` is not empty it will throw an error and will stop the upgrade action. | `dict "validationErrors" (list $validationError00 $validationError01) "context" $` |
### Images
| Helper identifier | Description | Expected Input |
|-----------------------------|------------------------------------------------------|---------------------------------------------------------------------------------------------------------|
| `common.images.image` | Return the proper and full image name | `dict "imageRoot" .Values.path.to.the.image "global" $`, see [ImageRoot](#imageroot) for the structure. |
| `common.images.pullSecrets` | Return the proper Docker Image Registry Secret Names (deprecated: use common.images.renderPullSecrets instead) | `dict "images" (list .Values.path.to.the.image1, .Values.path.to.the.image2) "global" .Values.global` |
| `common.images.renderPullSecrets` | Return the proper Docker Image Registry Secret Names (evaluates values as templates) | `dict "images" (list .Values.path.to.the.image1, .Values.path.to.the.image2) "context" $` |
### Ingress
| Helper identifier | Description | Expected Input |
|-------------------------------------------|----------------------------------------------------------------------|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| `common.ingress.backend` | Generate a proper Ingress backend entry depending on the API version | `dict "serviceName" "foo" "servicePort" "bar"`, see the [Ingress deprecation notice](https://kubernetes.io/blog/2019/07/18/api-deprecations-in-1-16/) for the syntax differences |
| `common.ingress.supportsPathType` | Prints "true" if the pathType field is supported | `.` Chart context |
| `common.ingress.supportsIngressClassname` | Prints "true" if the ingressClassname field is supported | `.` Chart context |
### Labels
| Helper identifier | Description | Expected Input |
|-----------------------------|------------------------------------------------------|-------------------|
| `common.labels.standard` | Return Kubernetes standard labels | `.` Chart context |
| `common.labels.matchLabels` | Return the proper Docker Image Registry Secret Names | `.` Chart context |
### Names
| Helper identifier | Description | Expected Inpput |
|-------------------------|------------------------------------------------------------|-------------------|
| `common.names.name` | Expand the name of the chart or use `.Values.nameOverride` | `.` Chart context |
| `common.names.fullname` | Create a default fully qualified app name. | `.` Chart context |
| `common.names.chart` | Chart name plus version | `.` Chart context |
### Secrets
| Helper identifier | Description | Expected Input |
|---------------------------|--------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| `common.secrets.name` | Generate the name of the secret. | `dict "existingSecret" .Values.path.to.the.existingSecret "defaultNameSuffix" "mySuffix" "context" $` see [ExistingSecret](#existingsecret) for the structure. |
| `common.secrets.key` | Generate secret key. | `dict "existingSecret" .Values.path.to.the.existingSecret "key" "keyName"` see [ExistingSecret](#existingsecret) for the structure. |
| `common.passwords.manage` | Generate secret password or retrieve one if already created. | `dict "secret" "secret-name" "key" "keyName" "providedValues" (list "path.to.password1" "path.to.password2") "length" 10 "strong" false "chartName" "chartName" "context" $`, length, strong and chartNAme fields are optional. |
| `common.secrets.exists` | Returns whether a previous generated secret already exists. | `dict "secret" "secret-name" "context" $` |
### Storage
| Helper identifier | Description | Expected Input |
|-------------------------------|---------------------------------------|---------------------------------------------------------------------------------------------------------------------|
| `common.affinities.node.soft` | Return a soft nodeAffinity definition | `dict "persistence" .Values.path.to.the.persistence "global" $`, see [Persistence](#persistence) for the structure. |
### TplValues
| Helper identifier | Description | Expected Input |
|---------------------------|----------------------------------------|----------------------------------------------------------------------------------------------------------------------------------------------------------|
| `common.tplvalues.render` | Renders a value that contains template | `dict "value" .Values.path.to.the.Value "context" $`, value is the value should rendered as template, context frequently is the chart context `$` or `.` |
### Utils
| Helper identifier | Description | Expected Input |
|--------------------------------|------------------------------------------------------------------------------------------|------------------------------------------------------------------------|
| `common.utils.fieldToEnvVar` | Build environment variable name given a field. | `dict "field" "my-password"` |
| `common.utils.secret.getvalue` | Print instructions to get a secret value. | `dict "secret" "secret-name" "field" "secret-value-field" "context" $` |
| `common.utils.getValueFromKey` | Gets a value from `.Values` object given its key path | `dict "key" "path.to.key" "context" $` |
| `common.utils.getKeyFromList` | Returns first `.Values` key with a defined value or first of the list if all non-defined | `dict "keys" (list "path.to.key1" "path.to.key2") "context" $` |
### Validations
| Helper identifier | Description | Expected Input |
|--------------------------------------------------|-------------------------------------------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| `common.validations.values.single.empty` | Validate a value must not be empty. | `dict "valueKey" "path.to.value" "secret" "secret.name" "field" "my-password" "subchart" "subchart" "context" $` secret, field and subchart are optional. In case they are given, the helper will generate a how to get instruction. See [ValidateValue](#validatevalue) |
| `common.validations.values.multiple.empty` | Validate a multiple values must not be empty. It returns a shared error for all the values. | `dict "required" (list $validateValueConf00 $validateValueConf01) "context" $`. See [ValidateValue](#validatevalue) |
| `common.validations.values.mariadb.passwords` | This helper will ensure required password for MariaDB are not empty. It returns a shared error for all the values. | `dict "secret" "mariadb-secret" "subchart" "true" "context" $` subchart field is optional and could be true or false it depends on where you will use mariadb chart and the helper. |
| `common.validations.values.postgresql.passwords` | This helper will ensure required password for PostgreSQL are not empty. It returns a shared error for all the values. | `dict "secret" "postgresql-secret" "subchart" "true" "context" $` subchart field is optional and could be true or false it depends on where you will use postgresql chart and the helper. |
| `common.validations.values.redis.passwords` | This helper will ensure required password for Redis™ are not empty. It returns a shared error for all the values. | `dict "secret" "redis-secret" "subchart" "true" "context" $` subchart field is optional and could be true or false it depends on where you will use redis chart and the helper. |
| `common.validations.values.cassandra.passwords` | This helper will ensure required password for Cassandra are not empty. It returns a shared error for all the values. | `dict "secret" "cassandra-secret" "subchart" "true" "context" $` subchart field is optional and could be true or false it depends on where you will use cassandra chart and the helper. |
| `common.validations.values.mongodb.passwords` | This helper will ensure required password for MongoDB® are not empty. It returns a shared error for all the values. | `dict "secret" "mongodb-secret" "subchart" "true" "context" $` subchart field is optional and could be true or false it depends on where you will use mongodb chart and the helper. |
### Warnings
| Helper identifier | Description | Expected Input |
|------------------------------|----------------------------------|------------------------------------------------------------|
| `common.warnings.rollingTag` | Warning about using rolling tag. | `ImageRoot` see [ImageRoot](#imageroot) for the structure. |
## Special input schemas
### ImageRoot
```yaml
registry:
type: string
description: Docker registry where the image is located
example: docker.io
repository:
type: string
description: Repository and image name
example: bitnami/nginx
tag:
type: string
description: image tag
example: 1.16.1-debian-10-r63
pullPolicy:
type: string
description: Specify a imagePullPolicy. Defaults to 'Always' if image tag is 'latest', else set to 'IfNotPresent'
pullSecrets:
type: array
items:
type: string
description: Optionally specify an array of imagePullSecrets (evaluated as templates).
debug:
type: boolean
description: Set to true if you would like to see extra information on logs
example: false
## An instance would be:
# registry: docker.io
# repository: bitnami/nginx
# tag: 1.16.1-debian-10-r63
# pullPolicy: IfNotPresent
# debug: false
```
### Persistence
```yaml
enabled:
type: boolean
description: Whether enable persistence.
example: true
storageClass:
type: string
description: Ghost data Persistent Volume Storage Class, If set to "-", storageClassName: "" which disables dynamic provisioning.
example: "-"
accessMode:
type: string
description: Access mode for the Persistent Volume Storage.
example: ReadWriteOnce
size:
type: string
description: Size the Persistent Volume Storage.
example: 8Gi
path:
type: string
description: Path to be persisted.
example: /bitnami
## An instance would be:
# enabled: true
# storageClass: "-"
# accessMode: ReadWriteOnce
# size: 8Gi
# path: /bitnami
```
### ExistingSecret
```yaml
name:
type: string
description: Name of the existing secret.
example: mySecret
keyMapping:
description: Mapping between the expected key name and the name of the key in the existing secret.
type: object
## An instance would be:
# name: mySecret
# keyMapping:
# password: myPasswordKey
```
#### Example of use
When we store sensitive data for a deployment in a secret, some times we want to give to users the possibility of using theirs existing secrets.
```yaml
# templates/secret.yaml
---
apiVersion: v1
kind: Secret
metadata:
name: {{ include "common.names.fullname" . }}
labels:
app: {{ include "common.names.fullname" . }}
type: Opaque
data:
password: {{ .Values.password | b64enc | quote }}
# templates/dpl.yaml
---
...
env:
- name: PASSWORD
valueFrom:
secretKeyRef:
name: {{ include "common.secrets.name" (dict "existingSecret" .Values.existingSecret "context" $) }}
key: {{ include "common.secrets.key" (dict "existingSecret" .Values.existingSecret "key" "password") }}
...
# values.yaml
---
name: mySecret
keyMapping:
password: myPasswordKey
```
### ValidateValue
#### NOTES.txt
```console
{{- $validateValueConf00 := (dict "valueKey" "path.to.value00" "secret" "secretName" "field" "password-00") -}}
{{- $validateValueConf01 := (dict "valueKey" "path.to.value01" "secret" "secretName" "field" "password-01") -}}
{{ include "common.validations.values.multiple.empty" (dict "required" (list $validateValueConf00 $validateValueConf01) "context" $) }}
```
If we force those values to be empty we will see some alerts
```console
$ helm install test mychart --set path.to.value00="",path.to.value01=""
'path.to.value00' must not be empty, please add '--set path.to.value00=$PASSWORD_00' to the command. To get the current value:
export PASSWORD_00=$(kubectl get secret --namespace default secretName -o jsonpath="{.data.password-00}" | base64 --decode)
'path.to.value01' must not be empty, please add '--set path.to.value01=$PASSWORD_01' to the command. To get the current value:
export PASSWORD_01=$(kubectl get secret --namespace default secretName -o jsonpath="{.data.password-01}" | base64 --decode)
```
## Upgrading
### To 1.0.0
[On November 13, 2020, Helm v2 support was formally finished](https://github.com/helm/charts#status-of-the-project), this major version is the result of the required changes applied to the Helm Chart to be able to incorporate the different features added in Helm v3 and to be consistent with the Helm project itself regarding the Helm v2 EOL.
**What changes were introduced in this major version?**
- Previous versions of this Helm Chart use `apiVersion: v1` (installable by both Helm 2 and 3), this Helm Chart was updated to `apiVersion: v2` (installable by Helm 3 only). [Here](https://helm.sh/docs/topics/charts/#the-apiversion-field) you can find more information about the `apiVersion` field.
- Use `type: library`. [Here](https://v3.helm.sh/docs/faq/#library-chart-support) you can find more information.
- The different fields present in the *Chart.yaml* file has been ordered alphabetically in a homogeneous way for all the Bitnami Helm Charts
**Considerations when upgrading to this version**
- If you want to upgrade to this version from a previous one installed with Helm v3, you shouldn't face any issues
- If you want to upgrade to this version using Helm v2, this scenario is not supported as this version doesn't support Helm v2 anymore
- If you installed the previous version with Helm v2 and wants to upgrade to this version with Helm v3, please refer to the [official Helm documentation](https://helm.sh/docs/topics/v2_v3_migration/#migration-use-cases) about migrating from Helm v2 to v3
**Useful links**
- https://docs.bitnami.com/tutorials/resolve-helm2-helm3-post-migration-issues/
- https://helm.sh/docs/topics/v2_v3_migration/
- https://helm.sh/blog/migrate-from-helm-v2-to-helm-v3/

View File

@ -0,0 +1,102 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Return a soft nodeAffinity definition
{{ include "common.affinities.nodes.soft" (dict "key" "FOO" "values" (list "BAR" "BAZ")) -}}
*/}}
{{- define "common.affinities.nodes.soft" -}}
preferredDuringSchedulingIgnoredDuringExecution:
- preference:
matchExpressions:
- key: {{ .key }}
operator: In
values:
{{- range .values }}
- {{ . | quote }}
{{- end }}
weight: 1
{{- end -}}
{{/*
Return a hard nodeAffinity definition
{{ include "common.affinities.nodes.hard" (dict "key" "FOO" "values" (list "BAR" "BAZ")) -}}
*/}}
{{- define "common.affinities.nodes.hard" -}}
requiredDuringSchedulingIgnoredDuringExecution:
nodeSelectorTerms:
- matchExpressions:
- key: {{ .key }}
operator: In
values:
{{- range .values }}
- {{ . | quote }}
{{- end }}
{{- end -}}
{{/*
Return a nodeAffinity definition
{{ include "common.affinities.nodes" (dict "type" "soft" "key" "FOO" "values" (list "BAR" "BAZ")) -}}
*/}}
{{- define "common.affinities.nodes" -}}
{{- if eq .type "soft" }}
{{- include "common.affinities.nodes.soft" . -}}
{{- else if eq .type "hard" }}
{{- include "common.affinities.nodes.hard" . -}}
{{- end -}}
{{- end -}}
{{/*
Return a soft podAffinity/podAntiAffinity definition
{{ include "common.affinities.pods.soft" (dict "component" "FOO" "extraMatchLabels" .Values.extraMatchLabels "context" $) -}}
*/}}
{{- define "common.affinities.pods.soft" -}}
{{- $component := default "" .component -}}
{{- $extraMatchLabels := default (dict) .extraMatchLabels -}}
preferredDuringSchedulingIgnoredDuringExecution:
- podAffinityTerm:
labelSelector:
matchLabels: {{- (include "common.labels.matchLabels" .context) | nindent 10 }}
{{- if not (empty $component) }}
{{ printf "app.kubernetes.io/component: %s" $component }}
{{- end }}
{{- range $key, $value := $extraMatchLabels }}
{{ $key }}: {{ $value | quote }}
{{- end }}
namespaces:
- {{ .context.Release.Namespace | quote }}
topologyKey: kubernetes.io/hostname
weight: 1
{{- end -}}
{{/*
Return a hard podAffinity/podAntiAffinity definition
{{ include "common.affinities.pods.hard" (dict "component" "FOO" "extraMatchLabels" .Values.extraMatchLabels "context" $) -}}
*/}}
{{- define "common.affinities.pods.hard" -}}
{{- $component := default "" .component -}}
{{- $extraMatchLabels := default (dict) .extraMatchLabels -}}
requiredDuringSchedulingIgnoredDuringExecution:
- labelSelector:
matchLabels: {{- (include "common.labels.matchLabels" .context) | nindent 8 }}
{{- if not (empty $component) }}
{{ printf "app.kubernetes.io/component: %s" $component }}
{{- end }}
{{- range $key, $value := $extraMatchLabels }}
{{ $key }}: {{ $value | quote }}
{{- end }}
namespaces:
- {{ .context.Release.Namespace | quote }}
topologyKey: kubernetes.io/hostname
{{- end -}}
{{/*
Return a podAffinity/podAntiAffinity definition
{{ include "common.affinities.pods" (dict "type" "soft" "key" "FOO" "values" (list "BAR" "BAZ")) -}}
*/}}
{{- define "common.affinities.pods" -}}
{{- if eq .type "soft" }}
{{- include "common.affinities.pods.soft" . -}}
{{- else if eq .type "hard" }}
{{- include "common.affinities.pods.hard" . -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,117 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Return the target Kubernetes version
*/}}
{{- define "common.capabilities.kubeVersion" -}}
{{- if .Values.global }}
{{- if .Values.global.kubeVersion }}
{{- .Values.global.kubeVersion -}}
{{- else }}
{{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
{{- end -}}
{{- else }}
{{- default .Capabilities.KubeVersion.Version .Values.kubeVersion -}}
{{- end -}}
{{- end -}}
{{/*
Return the appropriate apiVersion for policy.
*/}}
{{- define "common.capabilities.policy.apiVersion" -}}
{{- if semverCompare "<1.21-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "policy/v1beta1" -}}
{{- else -}}
{{- print "policy/v1" -}}
{{- end -}}
{{- end -}}
{{/*
Return the appropriate apiVersion for cronjob.
*/}}
{{- define "common.capabilities.cronjob.apiVersion" -}}
{{- if semverCompare "<1.21-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "batch/v1beta1" -}}
{{- else -}}
{{- print "batch/v1" -}}
{{- end -}}
{{- end -}}
{{/*
Return the appropriate apiVersion for deployment.
*/}}
{{- define "common.capabilities.deployment.apiVersion" -}}
{{- if semverCompare "<1.14-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "extensions/v1beta1" -}}
{{- else -}}
{{- print "apps/v1" -}}
{{- end -}}
{{- end -}}
{{/*
Return the appropriate apiVersion for statefulset.
*/}}
{{- define "common.capabilities.statefulset.apiVersion" -}}
{{- if semverCompare "<1.14-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "apps/v1beta1" -}}
{{- else -}}
{{- print "apps/v1" -}}
{{- end -}}
{{- end -}}
{{/*
Return the appropriate apiVersion for ingress.
*/}}
{{- define "common.capabilities.ingress.apiVersion" -}}
{{- if .Values.ingress -}}
{{- if .Values.ingress.apiVersion -}}
{{- .Values.ingress.apiVersion -}}
{{- else if semverCompare "<1.14-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "extensions/v1beta1" -}}
{{- else if semverCompare "<1.19-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "networking.k8s.io/v1beta1" -}}
{{- else -}}
{{- print "networking.k8s.io/v1" -}}
{{- end }}
{{- else if semverCompare "<1.14-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "extensions/v1beta1" -}}
{{- else if semverCompare "<1.19-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "networking.k8s.io/v1beta1" -}}
{{- else -}}
{{- print "networking.k8s.io/v1" -}}
{{- end -}}
{{- end -}}
{{/*
Return the appropriate apiVersion for RBAC resources.
*/}}
{{- define "common.capabilities.rbac.apiVersion" -}}
{{- if semverCompare "<1.17-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "rbac.authorization.k8s.io/v1beta1" -}}
{{- else -}}
{{- print "rbac.authorization.k8s.io/v1" -}}
{{- end -}}
{{- end -}}
{{/*
Return the appropriate apiVersion for CRDs.
*/}}
{{- define "common.capabilities.crd.apiVersion" -}}
{{- if semverCompare "<1.19-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "apiextensions.k8s.io/v1beta1" -}}
{{- else -}}
{{- print "apiextensions.k8s.io/v1" -}}
{{- end -}}
{{- end -}}
{{/*
Returns true if the used Helm version is 3.3+.
A way to check the used Helm version was not introduced until version 3.3.0 with .Capabilities.HelmVersion, which contains an additional "{}}" structure.
This check is introduced as a regexMatch instead of {{ if .Capabilities.HelmVersion }} because checking for the key HelmVersion in <3.3 results in a "interface not found" error.
**To be removed when the catalog's minimun Helm version is 3.3**
*/}}
{{- define "common.capabilities.supportsHelmVersion" -}}
{{- if regexMatch "{(v[0-9])*[^}]*}}$" (.Capabilities | toString ) }}
{{- true -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,23 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Through error when upgrading using empty passwords values that must not be empty.
Usage:
{{- $validationError00 := include "common.validations.values.single.empty" (dict "valueKey" "path.to.password00" "secret" "secretName" "field" "password-00") -}}
{{- $validationError01 := include "common.validations.values.single.empty" (dict "valueKey" "path.to.password01" "secret" "secretName" "field" "password-01") -}}
{{ include "common.errors.upgrade.passwords.empty" (dict "validationErrors" (list $validationError00 $validationError01) "context" $) }}
Required password params:
- validationErrors - String - Required. List of validation strings to be return, if it is empty it won't throw error.
- context - Context - Required. Parent context.
*/}}
{{- define "common.errors.upgrade.passwords.empty" -}}
{{- $validationErrors := join "" .validationErrors -}}
{{- if and $validationErrors .context.Release.IsUpgrade -}}
{{- $errorString := "\nPASSWORDS ERROR: You must provide your current passwords when upgrading the release." -}}
{{- $errorString = print $errorString "\n Note that even after reinstallation, old credentials may be needed as they may be kept in persistent volume claims." -}}
{{- $errorString = print $errorString "\n Further information can be obtained at https://docs.bitnami.com/general/how-to/troubleshoot-helm-chart-issues/#credential-errors-while-upgrading-chart-releases" -}}
{{- $errorString = print $errorString "\n%s" -}}
{{- printf $errorString $validationErrors | fail -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,75 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Return the proper image name
{{ include "common.images.image" ( dict "imageRoot" .Values.path.to.the.image "global" $) }}
*/}}
{{- define "common.images.image" -}}
{{- $registryName := .imageRoot.registry -}}
{{- $repositoryName := .imageRoot.repository -}}
{{- $tag := .imageRoot.tag | toString -}}
{{- if .global }}
{{- if .global.imageRegistry }}
{{- $registryName = .global.imageRegistry -}}
{{- end -}}
{{- end -}}
{{- if $registryName }}
{{- printf "%s/%s:%s" $registryName $repositoryName $tag -}}
{{- else -}}
{{- printf "%s:%s" $repositoryName $tag -}}
{{- end -}}
{{- end -}}
{{/*
Return the proper Docker Image Registry Secret Names (deprecated: use common.images.renderPullSecrets instead)
{{ include "common.images.pullSecrets" ( dict "images" (list .Values.path.to.the.image1, .Values.path.to.the.image2) "global" .Values.global) }}
*/}}
{{- define "common.images.pullSecrets" -}}
{{- $pullSecrets := list }}
{{- if .global }}
{{- range .global.imagePullSecrets -}}
{{- $pullSecrets = append $pullSecrets . -}}
{{- end -}}
{{- end -}}
{{- range .images -}}
{{- range .pullSecrets -}}
{{- $pullSecrets = append $pullSecrets . -}}
{{- end -}}
{{- end -}}
{{- if (not (empty $pullSecrets)) }}
imagePullSecrets:
{{- range $pullSecrets }}
- name: {{ . }}
{{- end }}
{{- end }}
{{- end -}}
{{/*
Return the proper Docker Image Registry Secret Names evaluating values as templates
{{ include "common.images.renderPullSecrets" ( dict "images" (list .Values.path.to.the.image1, .Values.path.to.the.image2) "context" $) }}
*/}}
{{- define "common.images.renderPullSecrets" -}}
{{- $pullSecrets := list }}
{{- $context := .context }}
{{- if $context.Values.global }}
{{- range $context.Values.global.imagePullSecrets -}}
{{- $pullSecrets = append $pullSecrets (include "common.tplvalues.render" (dict "value" . "context" $context)) -}}
{{- end -}}
{{- end -}}
{{- range .images -}}
{{- range .pullSecrets -}}
{{- $pullSecrets = append $pullSecrets (include "common.tplvalues.render" (dict "value" . "context" $context)) -}}
{{- end -}}
{{- end -}}
{{- if (not (empty $pullSecrets)) }}
imagePullSecrets:
{{- range $pullSecrets }}
- name: {{ . }}
{{- end }}
{{- end }}
{{- end -}}

View File

@ -0,0 +1,55 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Generate backend entry that is compatible with all Kubernetes API versions.
Usage:
{{ include "common.ingress.backend" (dict "serviceName" "backendName" "servicePort" "backendPort" "context" $) }}
Params:
- serviceName - String. Name of an existing service backend
- servicePort - String/Int. Port name (or number) of the service. It will be translated to different yaml depending if it is a string or an integer.
- context - Dict - Required. The context for the template evaluation.
*/}}
{{- define "common.ingress.backend" -}}
{{- $apiVersion := (include "common.capabilities.ingress.apiVersion" .context) -}}
{{- if or (eq $apiVersion "extensions/v1beta1") (eq $apiVersion "networking.k8s.io/v1beta1") -}}
serviceName: {{ .serviceName }}
servicePort: {{ .servicePort }}
{{- else -}}
service:
name: {{ .serviceName }}
port:
{{- if typeIs "string" .servicePort }}
name: {{ .servicePort }}
{{- else if or (typeIs "int" .servicePort) (typeIs "float64" .servicePort) }}
number: {{ .servicePort | int }}
{{- end }}
{{- end -}}
{{- end -}}
{{/*
Print "true" if the API pathType field is supported
Usage:
{{ include "common.ingress.supportsPathType" . }}
*/}}
{{- define "common.ingress.supportsPathType" -}}
{{- if (semverCompare "<1.18-0" (include "common.capabilities.kubeVersion" .)) -}}
{{- print "false" -}}
{{- else -}}
{{- print "true" -}}
{{- end -}}
{{- end -}}
{{/*
Returns true if the ingressClassname field is supported
Usage:
{{ include "common.ingress.supportsIngressClassname" . }}
*/}}
{{- define "common.ingress.supportsIngressClassname" -}}
{{- if semverCompare "<1.18-0" (include "common.capabilities.kubeVersion" .) -}}
{{- print "false" -}}
{{- else -}}
{{- print "true" -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,18 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Kubernetes standard labels
*/}}
{{- define "common.labels.standard" -}}
app.kubernetes.io/name: {{ include "common.names.name" . }}
helm.sh/chart: {{ include "common.names.chart" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
{{- end -}}
{{/*
Labels to use on deploy.spec.selector.matchLabels and svc.spec.selector
*/}}
{{- define "common.labels.matchLabels" -}}
app.kubernetes.io/name: {{ include "common.names.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- end -}}

View File

@ -0,0 +1,32 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Expand the name of the chart.
*/}}
{{- define "common.names.name" -}}
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Create chart name and version as used by the chart label.
*/}}
{{- define "common.names.chart" -}}
{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Create a default fully qualified app name.
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
If release name contains chart name it will be used as a full name.
*/}}
{{- define "common.names.fullname" -}}
{{- if .Values.fullnameOverride -}}
{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" -}}
{{- else -}}
{{- $name := default .Chart.Name .Values.nameOverride -}}
{{- if contains $name .Release.Name -}}
{{- .Release.Name | trunc 63 | trimSuffix "-" -}}
{{- else -}}
{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,129 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Generate secret name.
Usage:
{{ include "common.secrets.name" (dict "existingSecret" .Values.path.to.the.existingSecret "defaultNameSuffix" "mySuffix" "context" $) }}
Params:
- existingSecret - ExistingSecret/String - Optional. The path to the existing secrets in the values.yaml given by the user
to be used instead of the default one. Allows for it to be of type String (just the secret name) for backwards compatibility.
+info: https://github.com/bitnami/charts/tree/master/bitnami/common#existingsecret
- defaultNameSuffix - String - Optional. It is used only if we have several secrets in the same deployment.
- context - Dict - Required. The context for the template evaluation.
*/}}
{{- define "common.secrets.name" -}}
{{- $name := (include "common.names.fullname" .context) -}}
{{- if .defaultNameSuffix -}}
{{- $name = printf "%s-%s" $name .defaultNameSuffix | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{- with .existingSecret -}}
{{- if not (typeIs "string" .) -}}
{{- with .name -}}
{{- $name = . -}}
{{- end -}}
{{- else -}}
{{- $name = . -}}
{{- end -}}
{{- end -}}
{{- printf "%s" $name -}}
{{- end -}}
{{/*
Generate secret key.
Usage:
{{ include "common.secrets.key" (dict "existingSecret" .Values.path.to.the.existingSecret "key" "keyName") }}
Params:
- existingSecret - ExistingSecret/String - Optional. The path to the existing secrets in the values.yaml given by the user
to be used instead of the default one. Allows for it to be of type String (just the secret name) for backwards compatibility.
+info: https://github.com/bitnami/charts/tree/master/bitnami/common#existingsecret
- key - String - Required. Name of the key in the secret.
*/}}
{{- define "common.secrets.key" -}}
{{- $key := .key -}}
{{- if .existingSecret -}}
{{- if not (typeIs "string" .existingSecret) -}}
{{- if .existingSecret.keyMapping -}}
{{- $key = index .existingSecret.keyMapping $.key -}}
{{- end -}}
{{- end }}
{{- end -}}
{{- printf "%s" $key -}}
{{- end -}}
{{/*
Generate secret password or retrieve one if already created.
Usage:
{{ include "common.secrets.passwords.manage" (dict "secret" "secret-name" "key" "keyName" "providedValues" (list "path.to.password1" "path.to.password2") "length" 10 "strong" false "chartName" "chartName" "context" $) }}
Params:
- secret - String - Required - Name of the 'Secret' resource where the password is stored.
- key - String - Required - Name of the key in the secret.
- providedValues - List<String> - Required - The path to the validating value in the values.yaml, e.g: "mysql.password". Will pick first parameter with a defined value.
- length - int - Optional - Length of the generated random password.
- strong - Boolean - Optional - Whether to add symbols to the generated random password.
- chartName - String - Optional - Name of the chart used when said chart is deployed as a subchart.
- context - Context - Required - Parent context.
*/}}
{{- define "common.secrets.passwords.manage" -}}
{{- $password := "" }}
{{- $subchart := "" }}
{{- $chartName := default "" .chartName }}
{{- $passwordLength := default 10 .length }}
{{- $providedPasswordKey := include "common.utils.getKeyFromList" (dict "keys" .providedValues "context" $.context) }}
{{- $providedPasswordValue := include "common.utils.getValueFromKey" (dict "key" $providedPasswordKey "context" $.context) }}
{{- $secret := (lookup "v1" "Secret" $.context.Release.Namespace .secret) }}
{{- if $secret }}
{{- if index $secret.data .key }}
{{- $password = index $secret.data .key }}
{{- end -}}
{{- else if $providedPasswordValue }}
{{- $password = $providedPasswordValue | toString | b64enc | quote }}
{{- else }}
{{- if .context.Values.enabled }}
{{- $subchart = $chartName }}
{{- end -}}
{{- $requiredPassword := dict "valueKey" $providedPasswordKey "secret" .secret "field" .key "subchart" $subchart "context" $.context -}}
{{- $requiredPasswordError := include "common.validations.values.single.empty" $requiredPassword -}}
{{- $passwordValidationErrors := list $requiredPasswordError -}}
{{- include "common.errors.upgrade.passwords.empty" (dict "validationErrors" $passwordValidationErrors "context" $.context) -}}
{{- if .strong }}
{{- $subStr := list (lower (randAlpha 1)) (randNumeric 1) (upper (randAlpha 1)) | join "_" }}
{{- $password = randAscii $passwordLength }}
{{- $password = regexReplaceAllLiteral "\\W" $password "@" | substr 5 $passwordLength }}
{{- $password = printf "%s%s" $subStr $password | toString | shuffle | b64enc | quote }}
{{- else }}
{{- $password = randAlphaNum $passwordLength | b64enc | quote }}
{{- end }}
{{- end -}}
{{- printf "%s" $password -}}
{{- end -}}
{{/*
Returns whether a previous generated secret already exists
Usage:
{{ include "common.secrets.exists" (dict "secret" "secret-name" "context" $) }}
Params:
- secret - String - Required - Name of the 'Secret' resource where the password is stored.
- context - Context - Required - Parent context.
*/}}
{{- define "common.secrets.exists" -}}
{{- $secret := (lookup "v1" "Secret" $.context.Release.Namespace .secret) }}
{{- if $secret }}
{{- true -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,23 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Return the proper Storage Class
{{ include "common.storage.class" ( dict "persistence" .Values.path.to.the.persistence "global" $) }}
*/}}
{{- define "common.storage.class" -}}
{{- $storageClass := .persistence.storageClass -}}
{{- if .global -}}
{{- if .global.storageClass -}}
{{- $storageClass = .global.storageClass -}}
{{- end -}}
{{- end -}}
{{- if $storageClass -}}
{{- if (eq "-" $storageClass) -}}
{{- printf "storageClassName: \"\"" -}}
{{- else }}
{{- printf "storageClassName: %s" $storageClass -}}
{{- end -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,13 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Renders a value that contains template.
Usage:
{{ include "common.tplvalues.render" ( dict "value" .Values.path.to.the.Value "context" $) }}
*/}}
{{- define "common.tplvalues.render" -}}
{{- if typeIs "string" .value }}
{{- tpl .value .context }}
{{- else }}
{{- tpl (.value | toYaml) .context }}
{{- end }}
{{- end -}}

View File

@ -0,0 +1,62 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Print instructions to get a secret value.
Usage:
{{ include "common.utils.secret.getvalue" (dict "secret" "secret-name" "field" "secret-value-field" "context" $) }}
*/}}
{{- define "common.utils.secret.getvalue" -}}
{{- $varname := include "common.utils.fieldToEnvVar" . -}}
export {{ $varname }}=$(kubectl get secret --namespace {{ .context.Release.Namespace | quote }} {{ .secret }} -o jsonpath="{.data.{{ .field }}}" | base64 --decode)
{{- end -}}
{{/*
Build env var name given a field
Usage:
{{ include "common.utils.fieldToEnvVar" dict "field" "my-password" }}
*/}}
{{- define "common.utils.fieldToEnvVar" -}}
{{- $fieldNameSplit := splitList "-" .field -}}
{{- $upperCaseFieldNameSplit := list -}}
{{- range $fieldNameSplit -}}
{{- $upperCaseFieldNameSplit = append $upperCaseFieldNameSplit ( upper . ) -}}
{{- end -}}
{{ join "_" $upperCaseFieldNameSplit }}
{{- end -}}
{{/*
Gets a value from .Values given
Usage:
{{ include "common.utils.getValueFromKey" (dict "key" "path.to.key" "context" $) }}
*/}}
{{- define "common.utils.getValueFromKey" -}}
{{- $splitKey := splitList "." .key -}}
{{- $value := "" -}}
{{- $latestObj := $.context.Values -}}
{{- range $splitKey -}}
{{- if not $latestObj -}}
{{- printf "please review the entire path of '%s' exists in values" $.key | fail -}}
{{- end -}}
{{- $value = ( index $latestObj . ) -}}
{{- $latestObj = $value -}}
{{- end -}}
{{- printf "%v" (default "" $value) -}}
{{- end -}}
{{/*
Returns first .Values key with a defined value or first of the list if all non-defined
Usage:
{{ include "common.utils.getKeyFromList" (dict "keys" (list "path.to.key1" "path.to.key2") "context" $) }}
*/}}
{{- define "common.utils.getKeyFromList" -}}
{{- $key := first .keys -}}
{{- $reverseKeys := reverse .keys }}
{{- range $reverseKeys }}
{{- $value := include "common.utils.getValueFromKey" (dict "key" . "context" $.context ) }}
{{- if $value -}}
{{- $key = . }}
{{- end -}}
{{- end -}}
{{- printf "%s" $key -}}
{{- end -}}

View File

@ -0,0 +1,14 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Warning about using rolling tag.
Usage:
{{ include "common.warnings.rollingTag" .Values.path.to.the.imageRoot }}
*/}}
{{- define "common.warnings.rollingTag" -}}
{{- if and (contains "bitnami/" .repository) (not (.tag | toString | regexFind "-r\\d+$|sha256:")) }}
WARNING: Rolling tag detected ({{ .repository }}:{{ .tag }}), please note that it is strongly recommended to avoid using rolling tags in a production environment.
+info https://docs.bitnami.com/containers/how-to/understand-rolling-tags-containers/
{{- end }}
{{- end -}}

View File

@ -0,0 +1,72 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Validate Cassandra required passwords are not empty.
Usage:
{{ include "common.validations.values.cassandra.passwords" (dict "secret" "secretName" "subchart" false "context" $) }}
Params:
- secret - String - Required. Name of the secret where Cassandra values are stored, e.g: "cassandra-passwords-secret"
- subchart - Boolean - Optional. Whether Cassandra is used as subchart or not. Default: false
*/}}
{{- define "common.validations.values.cassandra.passwords" -}}
{{- $existingSecret := include "common.cassandra.values.existingSecret" . -}}
{{- $enabled := include "common.cassandra.values.enabled" . -}}
{{- $dbUserPrefix := include "common.cassandra.values.key.dbUser" . -}}
{{- $valueKeyPassword := printf "%s.password" $dbUserPrefix -}}
{{- if and (not $existingSecret) (eq $enabled "true") -}}
{{- $requiredPasswords := list -}}
{{- $requiredPassword := dict "valueKey" $valueKeyPassword "secret" .secret "field" "cassandra-password" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredPassword -}}
{{- include "common.validations.values.multiple.empty" (dict "required" $requiredPasswords "context" .context) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for existingSecret.
Usage:
{{ include "common.cassandra.values.existingSecret" (dict "context" $) }}
Params:
- subchart - Boolean - Optional. Whether Cassandra is used as subchart or not. Default: false
*/}}
{{- define "common.cassandra.values.existingSecret" -}}
{{- if .subchart -}}
{{- .context.Values.cassandra.dbUser.existingSecret | quote -}}
{{- else -}}
{{- .context.Values.dbUser.existingSecret | quote -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for enabled cassandra.
Usage:
{{ include "common.cassandra.values.enabled" (dict "context" $) }}
*/}}
{{- define "common.cassandra.values.enabled" -}}
{{- if .subchart -}}
{{- printf "%v" .context.Values.cassandra.enabled -}}
{{- else -}}
{{- printf "%v" (not .context.Values.enabled) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for the key dbUser
Usage:
{{ include "common.cassandra.values.key.dbUser" (dict "subchart" "true" "context" $) }}
Params:
- subchart - Boolean - Optional. Whether Cassandra is used as subchart or not. Default: false
*/}}
{{- define "common.cassandra.values.key.dbUser" -}}
{{- if .subchart -}}
cassandra.dbUser
{{- else -}}
dbUser
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,103 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Validate MariaDB required passwords are not empty.
Usage:
{{ include "common.validations.values.mariadb.passwords" (dict "secret" "secretName" "subchart" false "context" $) }}
Params:
- secret - String - Required. Name of the secret where MariaDB values are stored, e.g: "mysql-passwords-secret"
- subchart - Boolean - Optional. Whether MariaDB is used as subchart or not. Default: false
*/}}
{{- define "common.validations.values.mariadb.passwords" -}}
{{- $existingSecret := include "common.mariadb.values.auth.existingSecret" . -}}
{{- $enabled := include "common.mariadb.values.enabled" . -}}
{{- $architecture := include "common.mariadb.values.architecture" . -}}
{{- $authPrefix := include "common.mariadb.values.key.auth" . -}}
{{- $valueKeyRootPassword := printf "%s.rootPassword" $authPrefix -}}
{{- $valueKeyUsername := printf "%s.username" $authPrefix -}}
{{- $valueKeyPassword := printf "%s.password" $authPrefix -}}
{{- $valueKeyReplicationPassword := printf "%s.replicationPassword" $authPrefix -}}
{{- if and (not $existingSecret) (eq $enabled "true") -}}
{{- $requiredPasswords := list -}}
{{- $requiredRootPassword := dict "valueKey" $valueKeyRootPassword "secret" .secret "field" "mariadb-root-password" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredRootPassword -}}
{{- $valueUsername := include "common.utils.getValueFromKey" (dict "key" $valueKeyUsername "context" .context) }}
{{- if not (empty $valueUsername) -}}
{{- $requiredPassword := dict "valueKey" $valueKeyPassword "secret" .secret "field" "mariadb-password" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredPassword -}}
{{- end -}}
{{- if (eq $architecture "replication") -}}
{{- $requiredReplicationPassword := dict "valueKey" $valueKeyReplicationPassword "secret" .secret "field" "mariadb-replication-password" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredReplicationPassword -}}
{{- end -}}
{{- include "common.validations.values.multiple.empty" (dict "required" $requiredPasswords "context" .context) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for existingSecret.
Usage:
{{ include "common.mariadb.values.auth.existingSecret" (dict "context" $) }}
Params:
- subchart - Boolean - Optional. Whether MariaDB is used as subchart or not. Default: false
*/}}
{{- define "common.mariadb.values.auth.existingSecret" -}}
{{- if .subchart -}}
{{- .context.Values.mariadb.auth.existingSecret | quote -}}
{{- else -}}
{{- .context.Values.auth.existingSecret | quote -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for enabled mariadb.
Usage:
{{ include "common.mariadb.values.enabled" (dict "context" $) }}
*/}}
{{- define "common.mariadb.values.enabled" -}}
{{- if .subchart -}}
{{- printf "%v" .context.Values.mariadb.enabled -}}
{{- else -}}
{{- printf "%v" (not .context.Values.enabled) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for architecture
Usage:
{{ include "common.mariadb.values.architecture" (dict "subchart" "true" "context" $) }}
Params:
- subchart - Boolean - Optional. Whether MariaDB is used as subchart or not. Default: false
*/}}
{{- define "common.mariadb.values.architecture" -}}
{{- if .subchart -}}
{{- .context.Values.mariadb.architecture -}}
{{- else -}}
{{- .context.Values.architecture -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for the key auth
Usage:
{{ include "common.mariadb.values.key.auth" (dict "subchart" "true" "context" $) }}
Params:
- subchart - Boolean - Optional. Whether MariaDB is used as subchart or not. Default: false
*/}}
{{- define "common.mariadb.values.key.auth" -}}
{{- if .subchart -}}
mariadb.auth
{{- else -}}
auth
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,108 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Validate MongoDB&reg; required passwords are not empty.
Usage:
{{ include "common.validations.values.mongodb.passwords" (dict "secret" "secretName" "subchart" false "context" $) }}
Params:
- secret - String - Required. Name of the secret where MongoDB&reg; values are stored, e.g: "mongodb-passwords-secret"
- subchart - Boolean - Optional. Whether MongoDB&reg; is used as subchart or not. Default: false
*/}}
{{- define "common.validations.values.mongodb.passwords" -}}
{{- $existingSecret := include "common.mongodb.values.auth.existingSecret" . -}}
{{- $enabled := include "common.mongodb.values.enabled" . -}}
{{- $authPrefix := include "common.mongodb.values.key.auth" . -}}
{{- $architecture := include "common.mongodb.values.architecture" . -}}
{{- $valueKeyRootPassword := printf "%s.rootPassword" $authPrefix -}}
{{- $valueKeyUsername := printf "%s.username" $authPrefix -}}
{{- $valueKeyDatabase := printf "%s.database" $authPrefix -}}
{{- $valueKeyPassword := printf "%s.password" $authPrefix -}}
{{- $valueKeyReplicaSetKey := printf "%s.replicaSetKey" $authPrefix -}}
{{- $valueKeyAuthEnabled := printf "%s.enabled" $authPrefix -}}
{{- $authEnabled := include "common.utils.getValueFromKey" (dict "key" $valueKeyAuthEnabled "context" .context) -}}
{{- if and (not $existingSecret) (eq $enabled "true") (eq $authEnabled "true") -}}
{{- $requiredPasswords := list -}}
{{- $requiredRootPassword := dict "valueKey" $valueKeyRootPassword "secret" .secret "field" "mongodb-root-password" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredRootPassword -}}
{{- $valueUsername := include "common.utils.getValueFromKey" (dict "key" $valueKeyUsername "context" .context) }}
{{- $valueDatabase := include "common.utils.getValueFromKey" (dict "key" $valueKeyDatabase "context" .context) }}
{{- if and $valueUsername $valueDatabase -}}
{{- $requiredPassword := dict "valueKey" $valueKeyPassword "secret" .secret "field" "mongodb-password" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredPassword -}}
{{- end -}}
{{- if (eq $architecture "replicaset") -}}
{{- $requiredReplicaSetKey := dict "valueKey" $valueKeyReplicaSetKey "secret" .secret "field" "mongodb-replica-set-key" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredReplicaSetKey -}}
{{- end -}}
{{- include "common.validations.values.multiple.empty" (dict "required" $requiredPasswords "context" .context) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for existingSecret.
Usage:
{{ include "common.mongodb.values.auth.existingSecret" (dict "context" $) }}
Params:
- subchart - Boolean - Optional. Whether MongoDb is used as subchart or not. Default: false
*/}}
{{- define "common.mongodb.values.auth.existingSecret" -}}
{{- if .subchart -}}
{{- .context.Values.mongodb.auth.existingSecret | quote -}}
{{- else -}}
{{- .context.Values.auth.existingSecret | quote -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for enabled mongodb.
Usage:
{{ include "common.mongodb.values.enabled" (dict "context" $) }}
*/}}
{{- define "common.mongodb.values.enabled" -}}
{{- if .subchart -}}
{{- printf "%v" .context.Values.mongodb.enabled -}}
{{- else -}}
{{- printf "%v" (not .context.Values.enabled) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for the key auth
Usage:
{{ include "common.mongodb.values.key.auth" (dict "subchart" "true" "context" $) }}
Params:
- subchart - Boolean - Optional. Whether MongoDB&reg; is used as subchart or not. Default: false
*/}}
{{- define "common.mongodb.values.key.auth" -}}
{{- if .subchart -}}
mongodb.auth
{{- else -}}
auth
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for architecture
Usage:
{{ include "common.mongodb.values.architecture" (dict "subchart" "true" "context" $) }}
Params:
- subchart - Boolean - Optional. Whether MariaDB is used as subchart or not. Default: false
*/}}
{{- define "common.mongodb.values.architecture" -}}
{{- if .subchart -}}
{{- .context.Values.mongodb.architecture -}}
{{- else -}}
{{- .context.Values.architecture -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,131 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Validate PostgreSQL required passwords are not empty.
Usage:
{{ include "common.validations.values.postgresql.passwords" (dict "secret" "secretName" "subchart" false "context" $) }}
Params:
- secret - String - Required. Name of the secret where postgresql values are stored, e.g: "postgresql-passwords-secret"
- subchart - Boolean - Optional. Whether postgresql is used as subchart or not. Default: false
*/}}
{{- define "common.validations.values.postgresql.passwords" -}}
{{- $existingSecret := include "common.postgresql.values.existingSecret" . -}}
{{- $enabled := include "common.postgresql.values.enabled" . -}}
{{- $valueKeyPostgresqlPassword := include "common.postgresql.values.key.postgressPassword" . -}}
{{- $valueKeyPostgresqlReplicationEnabled := include "common.postgresql.values.key.replicationPassword" . -}}
{{- if and (not $existingSecret) (eq $enabled "true") -}}
{{- $requiredPasswords := list -}}
{{- $requiredPostgresqlPassword := dict "valueKey" $valueKeyPostgresqlPassword "secret" .secret "field" "postgresql-password" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredPostgresqlPassword -}}
{{- $enabledReplication := include "common.postgresql.values.enabled.replication" . -}}
{{- if (eq $enabledReplication "true") -}}
{{- $requiredPostgresqlReplicationPassword := dict "valueKey" $valueKeyPostgresqlReplicationEnabled "secret" .secret "field" "postgresql-replication-password" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredPostgresqlReplicationPassword -}}
{{- end -}}
{{- include "common.validations.values.multiple.empty" (dict "required" $requiredPasswords "context" .context) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to decide whether evaluate global values.
Usage:
{{ include "common.postgresql.values.use.global" (dict "key" "key-of-global" "context" $) }}
Params:
- key - String - Required. Field to be evaluated within global, e.g: "existingSecret"
*/}}
{{- define "common.postgresql.values.use.global" -}}
{{- if .context.Values.global -}}
{{- if .context.Values.global.postgresql -}}
{{- index .context.Values.global.postgresql .key | quote -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for existingSecret.
Usage:
{{ include "common.postgresql.values.existingSecret" (dict "context" $) }}
*/}}
{{- define "common.postgresql.values.existingSecret" -}}
{{- $globalValue := include "common.postgresql.values.use.global" (dict "key" "existingSecret" "context" .context) -}}
{{- if .subchart -}}
{{- default (.context.Values.postgresql.existingSecret | quote) $globalValue -}}
{{- else -}}
{{- default (.context.Values.existingSecret | quote) $globalValue -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for enabled postgresql.
Usage:
{{ include "common.postgresql.values.enabled" (dict "context" $) }}
*/}}
{{- define "common.postgresql.values.enabled" -}}
{{- if .subchart -}}
{{- printf "%v" .context.Values.postgresql.enabled -}}
{{- else -}}
{{- printf "%v" (not .context.Values.enabled) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for the key postgressPassword.
Usage:
{{ include "common.postgresql.values.key.postgressPassword" (dict "subchart" "true" "context" $) }}
Params:
- subchart - Boolean - Optional. Whether postgresql is used as subchart or not. Default: false
*/}}
{{- define "common.postgresql.values.key.postgressPassword" -}}
{{- $globalValue := include "common.postgresql.values.use.global" (dict "key" "postgresqlUsername" "context" .context) -}}
{{- if not $globalValue -}}
{{- if .subchart -}}
postgresql.postgresqlPassword
{{- else -}}
postgresqlPassword
{{- end -}}
{{- else -}}
global.postgresql.postgresqlPassword
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for enabled.replication.
Usage:
{{ include "common.postgresql.values.enabled.replication" (dict "subchart" "true" "context" $) }}
Params:
- subchart - Boolean - Optional. Whether postgresql is used as subchart or not. Default: false
*/}}
{{- define "common.postgresql.values.enabled.replication" -}}
{{- if .subchart -}}
{{- printf "%v" .context.Values.postgresql.replication.enabled -}}
{{- else -}}
{{- printf "%v" .context.Values.replication.enabled -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for the key replication.password.
Usage:
{{ include "common.postgresql.values.key.replicationPassword" (dict "subchart" "true" "context" $) }}
Params:
- subchart - Boolean - Optional. Whether postgresql is used as subchart or not. Default: false
*/}}
{{- define "common.postgresql.values.key.replicationPassword" -}}
{{- if .subchart -}}
postgresql.replication.password
{{- else -}}
replication.password
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,76 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Validate Redis&trade; required passwords are not empty.
Usage:
{{ include "common.validations.values.redis.passwords" (dict "secret" "secretName" "subchart" false "context" $) }}
Params:
- secret - String - Required. Name of the secret where redis values are stored, e.g: "redis-passwords-secret"
- subchart - Boolean - Optional. Whether redis is used as subchart or not. Default: false
*/}}
{{- define "common.validations.values.redis.passwords" -}}
{{- $enabled := include "common.redis.values.enabled" . -}}
{{- $valueKeyPrefix := include "common.redis.values.keys.prefix" . -}}
{{- $standarizedVersion := include "common.redis.values.standarized.version" . }}
{{- $existingSecret := ternary (printf "%s%s" $valueKeyPrefix "auth.existingSecret") (printf "%s%s" $valueKeyPrefix "existingSecret") (eq $standarizedVersion "true") }}
{{- $existingSecretValue := include "common.utils.getValueFromKey" (dict "key" $existingSecret "context" .context) }}
{{- $valueKeyRedisPassword := ternary (printf "%s%s" $valueKeyPrefix "auth.password") (printf "%s%s" $valueKeyPrefix "password") (eq $standarizedVersion "true") }}
{{- $valueKeyRedisUseAuth := ternary (printf "%s%s" $valueKeyPrefix "auth.enabled") (printf "%s%s" $valueKeyPrefix "usePassword") (eq $standarizedVersion "true") }}
{{- if and (not $existingSecretValue) (eq $enabled "true") -}}
{{- $requiredPasswords := list -}}
{{- $useAuth := include "common.utils.getValueFromKey" (dict "key" $valueKeyRedisUseAuth "context" .context) -}}
{{- if eq $useAuth "true" -}}
{{- $requiredRedisPassword := dict "valueKey" $valueKeyRedisPassword "secret" .secret "field" "redis-password" -}}
{{- $requiredPasswords = append $requiredPasswords $requiredRedisPassword -}}
{{- end -}}
{{- include "common.validations.values.multiple.empty" (dict "required" $requiredPasswords "context" .context) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right value for enabled redis.
Usage:
{{ include "common.redis.values.enabled" (dict "context" $) }}
*/}}
{{- define "common.redis.values.enabled" -}}
{{- if .subchart -}}
{{- printf "%v" .context.Values.redis.enabled -}}
{{- else -}}
{{- printf "%v" (not .context.Values.enabled) -}}
{{- end -}}
{{- end -}}
{{/*
Auxiliary function to get the right prefix path for the values
Usage:
{{ include "common.redis.values.key.prefix" (dict "subchart" "true" "context" $) }}
Params:
- subchart - Boolean - Optional. Whether redis is used as subchart or not. Default: false
*/}}
{{- define "common.redis.values.keys.prefix" -}}
{{- if .subchart -}}redis.{{- else -}}{{- end -}}
{{- end -}}
{{/*
Checks whether the redis chart's includes the standarizations (version >= 14)
Usage:
{{ include "common.redis.values.standarized.version" (dict "context" $) }}
*/}}
{{- define "common.redis.values.standarized.version" -}}
{{- $standarizedAuth := printf "%s%s" (include "common.redis.values.keys.prefix" .) "auth" -}}
{{- $standarizedAuthValues := include "common.utils.getValueFromKey" (dict "key" $standarizedAuth "context" .context) }}
{{- if $standarizedAuthValues -}}
{{- true -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,46 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Validate values must not be empty.
Usage:
{{- $validateValueConf00 := (dict "valueKey" "path.to.value" "secret" "secretName" "field" "password-00") -}}
{{- $validateValueConf01 := (dict "valueKey" "path.to.value" "secret" "secretName" "field" "password-01") -}}
{{ include "common.validations.values.empty" (dict "required" (list $validateValueConf00 $validateValueConf01) "context" $) }}
Validate value params:
- valueKey - String - Required. The path to the validating value in the values.yaml, e.g: "mysql.password"
- secret - String - Optional. Name of the secret where the validating value is generated/stored, e.g: "mysql-passwords-secret"
- field - String - Optional. Name of the field in the secret data, e.g: "mysql-password"
*/}}
{{- define "common.validations.values.multiple.empty" -}}
{{- range .required -}}
{{- include "common.validations.values.single.empty" (dict "valueKey" .valueKey "secret" .secret "field" .field "context" $.context) -}}
{{- end -}}
{{- end -}}
{{/*
Validate a value must not be empty.
Usage:
{{ include "common.validations.value.empty" (dict "valueKey" "mariadb.password" "secret" "secretName" "field" "my-password" "subchart" "subchart" "context" $) }}
Validate value params:
- valueKey - String - Required. The path to the validating value in the values.yaml, e.g: "mysql.password"
- secret - String - Optional. Name of the secret where the validating value is generated/stored, e.g: "mysql-passwords-secret"
- field - String - Optional. Name of the field in the secret data, e.g: "mysql-password"
- subchart - String - Optional - Name of the subchart that the validated password is part of.
*/}}
{{- define "common.validations.values.single.empty" -}}
{{- $value := include "common.utils.getValueFromKey" (dict "key" .valueKey "context" .context) }}
{{- $subchart := ternary "" (printf "%s." .subchart) (empty .subchart) }}
{{- if not $value -}}
{{- $varname := "my-value" -}}
{{- $getCurrentValue := "" -}}
{{- if and .secret .field -}}
{{- $varname = include "common.utils.fieldToEnvVar" . -}}
{{- $getCurrentValue = printf " To get the current value:\n\n %s\n" (include "common.utils.secret.getvalue" .) -}}
{{- end -}}
{{- printf "\n '%s' must not be empty, please add '--set %s%s=$%s' to the command.%s" .valueKey $subchart .valueKey $varname $getCurrentValue -}}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,5 @@
## bitnami/common
## It is required by CI/CD tools and processes.
## @skip exampleValue
##
exampleValue: common-chart

View File

@ -0,0 +1,101 @@
{{/*
include "ingress" (dict "ingressName" "myingress" "ingress" path.to.ingress "serviceName" "the-service" "servicePort" 9090 "context" $)
ingress:
enabled: true
certManager: false
pathType: ImplementationSpecific
apiVersion: ""
hostname: theservice.local
path: /
annotations: {}
tls: false
extraHosts: []
extraPaths: []
extraTls: []
secrets: []
*/}}
{{- define "lib.ingress" -}}
{{- $ctx := .context -}}
{{- $ingressName := .ingressName -}}
{{- $serviceName := .serviceName -}}
{{- $servicePort := .servicePort -}}
{{- $extraPaths := .ingress.extraPaths -}}
{{- if .ingress.enabled -}}
apiVersion: {{ include "common.capabilities.ingress.apiVersion" $ctx }}
kind: Ingress
metadata:
name: {{ $ingressName }}
namespace: {{ $ctx.Release.Namespace | quote }}
labels: {{- include "common.labels.standard" $ctx | nindent 4 }}
{{- if $ctx.Values.commonLabels }}
{{- include "common.tplvalues.render" ( dict "value" $ctx.Values.commonLabels "context" $ctx ) | nindent 4 }}
{{- end }}
annotations:
{{- if .ingress.certManager }}
kubernetes.io/tls-acme: "true"
{{- end }}
{{- if .ingress.annotations }}
{{- include "common.tplvalues.render" ( dict "value" .ingress.annotations "context" $ctx ) | nindent 4 }}
{{- end }}
{{- if $ctx.Values.commonAnnotations }}
{{- include "common.tplvalues.render" ( dict "value" $ctx.Values.commonAnnotations "context" $ctx ) | nindent 4 }}
{{- end }}
spec:
rules:
{{- if .ingress.hostname }}
- host: {{ .ingress.hostname }}
http:
paths:
- path: {{ .ingress.path }}
{{- if eq "true" (include "common.ingress.supportsPathType" $ctx) }}
pathType: {{ default "ImplementationSpecific" .ingress.pathType }}
{{- end }}
backend: {{- include "common.ingress.backend" (dict "serviceName" $serviceName "servicePort" $servicePort "context" $ctx) | nindent 14 }}
{{- include "lib.safeToYaml" $extraPaths | nindent 10 }}
{{- end }}
{{- range .ingress.extraHosts }}
- host: {{ .name | quote }}
http:
paths:
- path: {{ default "/" .path }}
{{- if eq "true" (include "common.ingress.supportsPathType" $ctx) }}
pathType: {{ default "ImplementationSpecific" .pathType }}
{{- end }}
backend: {{- include "common.ingress.backend" (dict "serviceName" $serviceName "servicePort" $servicePort "context" $ctx) | nindent 14 }}
{{- include "lib.safeToYaml" $extraPaths | nindent 10 }}
{{- end }}
{{/* .ingress.hosts is deprecated */}}
{{- range .ingress.hosts }}
- host: {{ .host | quote }}
http:
paths:
{{- if .path }}
- path: {{ default "/" .path }}
{{- if eq "true" (include "common.ingress.supportsPathType" $ctx) }}
pathType: {{ default "ImplementationSpecific" .pathType }}
{{- end }}
backend: {{- include "common.ingress.backend" (dict "serviceName" $serviceName "servicePort" $servicePort "context" $ctx) | nindent 14 }}
{{- end }}
{{- range .paths }}
- path: {{ . | quote }}
{{- if eq "true" (include "common.ingress.supportsPathType" $ctx) }}
pathType: ImplementationSpecific
{{- end }}
backend: {{- include "common.ingress.backend" (dict "serviceName" $serviceName "servicePort" $servicePort "context" $ctx) | nindent 14 }}
{{- end }}
{{- end }}
{{/* .ingress.hosts is deprecated */}}
{{- if or .ingress.tls .ingress.extraTls }}
tls:
{{- if .ingress.tls }}
- hosts:
- {{ .ingress.hostname }}
secretName: {{ printf "%s-tls" .ingress.hostname }}
{{- end }}
{{- if .ingress.extraTls }}
{{- include "common.tplvalues.render" ( dict "value" .ingress.extraTls "context" $ctx ) | nindent 4 }}
{{- end }}
{{- end }}
{{- end }}
{{- end -}}

View File

@ -0,0 +1,51 @@
{{/*
Call a template function in the context of a sub-chart, as opposed to the
current context of the caller
{{ include "lib.call-nested" (list . "subchart" "template_name") }}
*/}}
{{- define "lib.call-nested" }}
{{- $dot := index . 0 }}
{{- $subchart := index . 1 | splitList "." }}
{{- $template := index . 2 }}
{{- $values := $dot.Values }}
{{- range $subchart }}
{{- $values = index $values . }}
{{- end }}
{{- include $template (dict "Chart" (dict "Name" (last $subchart)) "Values" $values "Release" $dot.Release "Capabilities" $dot.Capabilities) }}
{{- end }}
{{/*
Common labels
*/}}
{{- define "lib.labels" -}}
helm.sh/chart: {{ include "common.names.chart" . }}
{{- if .Chart.AppVersion }}
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
{{- end }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
{{ include "common.labels.matchLabels" . }}
{{- end -}}
{{/*
Create the name of the service account to use
*/}}
{{- define "lib.serviceAccountName" -}}
{{- if .Values.serviceAccount.create -}}
{{ default (include "common.names.fullname" .) .Values.serviceAccount.name }}
{{- else -}}
{{ default "default" .Values.serviceAccount.name }}
{{- end -}}
{{- end -}}
{{/*
Given a variable, if it is not false, output as Yaml
include "lib.safeToYaml" .Values.something
*/}}
{{- define "lib.safeToYaml" -}}
{{- if . -}}
{{ toYaml . }}
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,46 @@
{{/*
Given a setup like the following:
# global and on down are optional
global:
image:
registry: my-registry.com
tag: latest
# This is the imageRoot
somecomponent:
image:
registry: my-other-registry.com
tag: 1.0.0
repository: bobs/coolthing
*/}}
{{/*
{{ include "utils.image.url" (dict "imageRoot" .Values.sawtooth.containers.validator.image "global" .Values.global)}}
*/}}
{{- define "lib.image.url" -}}
{{- $globalRegistryName := "index.docker.io" -}}
{{- $globalTag := "latest" -}}
{{- if .global -}}
{{- if .global.image -}}
{{- if .global.image.registry -}}
{{- $globalRegistryName = .global.image.registry -}}
{{- end -}}
{{- if .global.image.tag -}}
{{- $globalTag = .global.image.tag -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{- $repository := .imageRoot.repository -}}
{{- $registry := default $globalRegistryName .imageRoot.registry -}}
{{- $tag := default $globalTag .imageRoot.tag -}}
{{- printf "%s/%s:%s" $registry $repository $tag -}}
{{- end -}}
{{/*
{{ include "utils.image" (dict "imageRoot" .Values.sawtooth.containers.validator.image "global" .Values.global)}}
*/}}
{{- define "lib.image" -}}
image: {{ include "lib.image.url" . }}
imagePullPolicy: {{ default "IfNotPresent" .imageRoot.pullPolicy }}
{{- end -}}

View File

@ -0,0 +1,34 @@
{{/*
given a variable list, create a list of volumes
extraVolumes:
- name: pv-data
persistentVolumeClaim:
claimName: pvc-persistent-cfg
- name: scratch
emptyDir: {}
include "lib.volumes" .Values.extraVolumes
*/}}
{{- define "lib.volumes" -}}
{{ include "lib.safeToYaml" . }}
{{- end -}}
{{/*
given a variable list, create a list of volumeMounts
extraVolumeMounts:
- name: pv-data
mountPath: /data
- name: scratch
mountPath: /scratch
include "lib.volumeMounts" .Values.extraVolumeMounts
*/}}
{{- define "lib.volumeMounts" -}}
{{ include "lib.safeToYaml" . }}
{{- end -}}

View File

@ -0,0 +1 @@
exampleValue: example

View File

@ -0,0 +1,113 @@
questions:
# User Credentials
- variable: imagePullSecrets.createSecret.registryUser
default: ""
required: true
type: string
label: Username
description: Your username for the BTP licenced image registry, supplied by BTP
group: "User Credentials"
- variable: imagePullSecrets.createSecret.registryPassword
default: ""
required: true
type: password
label: Password
description: Your password for the BTP licenced image registry, supplied by BTP
group: "User Credentials"
# Ingress Settings
- variable: ingress.enabled
default: "false"
required: true
type: boolean
label: Enable Sextant Ingress
description: Enable an ingress for Sextant
group: "Ingress Settings"
show_subquestion_if: true
subquestions:
- variable: ingress.hostname
default: ""
required: false
type: string
label: Ingress hostname
description: Primary hostname for the ingress
group: "Ingress Settings"
- variable: ingress.path
default: ""
required: false
type: string
label: Hostname Path
description: Path for the ingress's primary hostname
group: "Ingress Settings"
- variable: ingress.pathType
default: ""
required: false
type: string
label: Hostname PathType
description: PathType for the ingress's primary hostname
group: "Ingress Settings"
- variable: ingress.certManager
default: "false"
required: false
type: boolean
label: Enable the acme certmanager for this ingress
description: Enable the acme certmanager for this ingress
group: "Ingress Settings"
- variable: ingress.annotations
default: ""
required: false
type: string
label: Ingress annotations
description: Annotations for the ingress
group: "Ingress Settings"
- variable: ingress.tls
default: false
required: false
type: boolean
label: Ingress TLS
description: Enable tls on the ingress with a secrete at hostname-tls
group: "Ingress Settings"
# Sextant database settings
- variable: postgres.enabled
default: "true"
required: true
type: boolean
label: Use internal postgres database
description: Create an internal postgres instance for Sextant, or if not supply details of an external postgres
group: "Database settings"
show_subquestion_if: false
subquestions:
- variable: postgres.user
default: "postgres"
required: true
type: string
label: Postgres user
description: User for the postgres database
group: "Database settings"
- variable: postgres.host
default: "localhost"
required: true
type: string
label: Postgres host
description: Host for the postgres database
group: "Database settings"
- variable: postgres.database
default: "postgres"
required: true
type: string
label: Database name
description: Database name for the postgres database
group: "Database settings"
- variable: postgres.port
default: "5432"
required: true
type: int
label: Postgres port
description: Port for the postgres database
group: "Database settings"
- variable: postgres.password
default: "postgres"
required: true
type: password
label: Postgres password
description: Password for the postgres database
group: "Database settings"

View File

@ -0,0 +1,27 @@
apiVersion: v2
name: sextant
description: Sextant
# Replaces the index.js in the deployment templates directory, sawtooth/index
# The deploymentType and deploymentVersion help build the object structure
deploymentType: sextant
deploymentVersion: 2.1
# absolute path to form.js
form: sextant/sextant/form.js
# absolute path to summary.jst
summary: sextant/sextant/summary.js
# paths to be used in the getField function
namePath: deployment.name
namespacePath: deployment.namespace
# additional fields for the button
# form: <same as deploymentVersion>
title: Sextant
sextantVersion: 2.1
buttonIcon: /sextant-detailed.png
features:
# documentation pull down mark down

View File

@ -0,0 +1,205 @@
const options = require('./options')
const validators = require('./validators')
// `^[a-z0-9]([-a-z0-9]*[a-z0-9])?(\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*`
const form = [
'Sextant Deployment',
[
{
id: 'deployment.name',
title: 'Deployment Name',
helperText: 'The name of the deployment',
component: 'text',
editable: {
new: true,
},
validate: {
type: 'string',
methods: [
['required', 'Required'],
validators.dns1123,
],
},
},
{
id: 'deployment.namespace',
title: 'Kubernetes Namespace',
helperText: 'The Kubernetes namespace',
component: 'text',
editable: {
new: true,
},
validate: {
type: 'string',
methods: [
['required', 'Required'],
validators.dns1123,
],
},
},
],
{
id: 'postgres.enabled',
title: 'Postgres Enabled',
helperText:
'If enabled, a local postgres database instance will be created',
component: 'radio',
default: false,
dataType: 'boolean',
editable: {
new: true,
},
row: true,
options: options.activated,
validate: {
type: 'string',
methods: [['required', 'Required']],
},
},
{
id: 'postgres.persistence.enabled',
title: 'Postgres Persistence',
helperText:
'If enabled data will be stored on PersistentVolumeClaims ',
component: 'radio',
default: false,
dataType: 'boolean',
editable: {
new: true,
},
row: true,
options: options.activated,
linked: {
linkedId: 'postgres.enabled',
visibilityParameter: 'true', // for what value of linkedId, will this component be visible
},
validate: {
type: 'string',
methods: [['required', 'Required']],
},
},
{
id: 'postgres.persistence.storageClass',
title: 'Postgres StorageClass',
helperText: 'The name of the StorageClass for the PersistentVolumeClaims',
component: 'text',
default: null,
editable: {
new: true,
},
linked: {
linkedId: 'postgres.persistence.enabled',
visibilityParameter: 'true', // for what value of linkedId, will this component be visible
},
validate: {
type: 'string',
methods: [
validators.dns1123,
],
},
},
'Postgres Credentials',
{
id: 'passwordOrSecret',
title: 'Password Or Secret',
helperText: 'Choose whether to enter a database password or the name of a secret',
component: 'radio',
default: true,
dataType: 'boolean',
row: true,
options: options.passwordOrSecret,
validate: {
type: 'string',
methods: [
['required', 'Required'],
],
},
},
{
id: 'postgres.password',
title: 'Postgres Password',
helperText: 'The password for the postgres instance',
component: 'text',
default: '',
linked: {
linkedId: 'passwordOrSecret',
visibilityParameter: 'true', // for what value of linkedId, will this component be visible
},
validate: {
type: 'string',
methods: [
validators.password,
],
},
},
{
id: 'postgres.existingPasswordSecret',
title: 'Postgres Password Secret Name',
helperText: 'The name of a pre-existing secret with a field "password" containing the password of the postgres instance',
component: 'text',
default: '',
linked: {
linkedId: 'passwordOrSecret',
visibilityParameter: 'false', // for what value of linkedId, will this component be visible
},
validate: {
type: 'string',
methods: [
validators.password,
],
},
},
'Image Pull Secrets',
{
id: 'imagePullSecrets.enabled',
title: 'Do you need to enable image pull secrets?',
helperText: 'Provide secrets to be injected into the namespace and used to pull images from your secure registry',
component: 'radio',
default: false,
dataType: 'boolean',
row: true,
options: options.yesNo,
validate: {
type: 'string',
methods: [
['required', 'Required'],
],
},
}, {
id: 'imagePullSecrets.value',
title: 'Image Pull Secrets',
helperText: null,
default: null,
linked: {
linkedId: 'imagePullSecrets.enabled',
visibilityParameter: 'true', // for what value of linkedId, will this component be visible
},
list: {
mainField: 'name',
schema: [{
id: 'name',
title: 'Name',
helperText: 'The name of the secret',
component: 'text',
validate: {
type: 'string',
methods: [
['required', 'Required'],
validators.dns1123,
],
},
}],
table: [{
title: 'Name',
name: 'name',
}],
},
},
]
module.exports = form

View File

@ -0,0 +1,33 @@
const activated = [{
value: true,
title: 'Enabled',
}, {
value: false,
title: 'Disabled',
}]
const passwordOrSecret = [
{
value: true,
title: 'Password',
},
{
value: false,
title: 'Existing Secret',
},
]
const yesNo = [{
value: true,
title: 'Yes',
}, {
value: false,
title: 'No',
}]
module.exports = {
activated,
yesNo,
passwordOrSecret,
}

View File

@ -0,0 +1,17 @@
const summary = (values) => {
const {
deployment,
} = values
return [
{
title: 'Deployment Name',
value: deployment.name,
}, {
title: 'Namespace',
value: deployment.namespace,
},
]
}
module.exports = summary

View File

@ -0,0 +1,11 @@
const dns1123 = [
'matches', ['^[a-z]([-a-z0-9]*[a-z0-9])*$'],
'a DNS-1123 label must consist of lower case alphanumeric characters or \'-\', and must start and end with an alphanumeric character',
]
const password = ['matches', '^\\S*$', 'Cannot contain spaces']
module.exports = {
dns1123,
password,
}

View File

@ -0,0 +1,27 @@
1. Get the initial Sextant application username and password by running this command
kubectl describe pod/{{ template "common.names.fullname" .}}-0 --namespace {{ .Release.Namespace }} | grep INITIAL_
2. Get the application URL by running these commands:
{{- if .Values.ingress.enabled }}
{{- range $host := .Values.ingress.hosts }}
{{- range .paths }}
http{{ if $.Values.ingress.tls }}s{{ end }}://{{ $host.host }}{{ . }}
{{- end }}
{{- end }}
{{- else if contains "NodePort" .Values.service.type }}
export NODE_PORT=$(kubectl get -o jsonpath="{.spec.ports[0].nodePort}" services {{ template "common.names.fullname" . }})
export NODE_IP=$(kubectl get nodes -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 svc -w {{ template "common.names.fullname" . }}'
export SERVICE_IP=$(kubectl get svc {{ template "common.names.fullname" . }} -o jsonpath='{.status.loadBalancer.ingress[0].ip}')
echo http://$SERVICE_IP:{{ .Values.service.port }}
{{- else if contains "ClusterIP" .Values.service.type }}
export POD_NAME=$(kubectl get pods -l "app.kubernetes.io/name={{ template "common.names.fullname" . }}" -o jsonpath="{.items[0].metadata.name}")
echo "Visit http://127.0.0.1:8080 to use your application"
kubectl port-forward $POD_NAME 8080:80
{{- end }}

View File

@ -0,0 +1,100 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Create a random alphanumeric password string.
We append a random number to the string to avoid password validation errors
*/}}
{{- define "sextant.randomPassword" -}}
{{- randAlphaNum 25 -}}{{- randNumeric 1 -}}
{{- end -}}
{{/*
{{ include "sextant.image" (dict "imageRoot" .Values.sawtooth.containers.validator.image "editionRoot" .Values.editionImages.api "edition" .Values.edition "global" .Values.global)}}
*/}}
{{- define "sextant.image" -}}
image: {{ include "sextant.image.url" . }}
imagePullPolicy: {{ default "IfNotPresent" .imageRoot.pullPolicy }}
{{- end -}}
{{/*
{{ include "sextant.image.url" (dict "imageRoot" .Values.api.image "editionRoot" .Values.editionImages.api "edition" .Values.edition "global" .Values.global)}}
*/}}
{{- define "sextant.image.url" -}}
{{- $registry := .imageRoot.registry -}}
{{- $repository := .imageRoot.repository -}}
{{- $tag := .imageRoot.tag -}}
{{- if eq .edition "development" -}}
{{- $registry = .imageRoot.registry -}}
{{- $repository = .imageRoot.repository -}}
{{- $tag = .imageRoot.tag -}}
{{- else if eq .edition "aws-standard" -}}
{{- $registry = .editionRoot.awsStandard.registry -}}
{{- $repository = .editionRoot.awsStandard.repository -}}
{{- $tag = .editionRoot.awsStandard.tag -}}
{{- else if eq .edition "aws-premium" -}}
{{- $registry = .editionRoot.awsPremium.registry -}}
{{- $repository = .editionRoot.awsPremium.repository -}}
{{- $tag = .editionRoot.awsPremium.tag -}}
{{- else if eq .edition "aws-enterprise" -}}
{{- $registry = .editionRoot.awsEnterprise.registry -}}
{{- $repository = .editionRoot.awsEnterprise.repository -}}
{{- $tag = .editionRoot.awsEnterprise.tag -}}
{{- else if eq .edition "enterprise" -}}
{{- $registry = .editionRoot.enterprise.registry -}}
{{- $repository = .editionRoot.enterprise.repository -}}
{{- $tag = .editionRoot.enterprise.tag -}}
{{- else if eq .edition "community" -}}
{{- $registry = .editionRoot.community.registry -}}
{{- $repository = .editionRoot.community.repository -}}
{{- $tag = .editionRoot.community.tag -}}
{{- else -}}
{{- $registry = .imageRoot.registry -}}
{{- $repository = .imageRoot.repository -}}
{{- $tag = .imageRoot.tag -}}
{{- end -}}
{{- if $registry -}}
{{- printf "%s/%s:%s" $registry $repository $tag -}}
{{- else -}}
{{- printf "%s:%s" $repository $tag -}}
{{- end -}}
{{- end -}}
{{/*
Local alternative of lib.image.url until the correct version is stable
{{ include "lib.image.url" (dict "imageRoot" .Values.sawtooth.containers.validator.image "global" .Values.global)}}
*/}}
{{- define "override.lib.image.url" -}}
{{- $globalRegistryName := "" -}}
{{- $globalTag := "latest" -}}
{{- if .global -}}
{{- if .global.image -}}
{{- if .global.image.registry -}}
{{- $globalRegistryName = .global.image.registry -}}
{{- end -}}
{{- if .global.image.tag -}}
{{- $globalTag = .global.image.tag -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{- $repository := .imageRoot.repository -}}
{{- $registry := default $globalRegistryName .imageRoot.registry -}}
{{- $tag := default $globalTag .imageRoot.tag -}}
{{- if $registry -}}
{{- printf "%s/%s:%s" $registry $repository $tag -}}
{{- else -}}
{{- printf "%s:%s" $repository $tag -}}
{{- end -}}
{{- end -}}
{{/*
Local alternative of lib.image.url until the correct version is stable
{{ include "lib.image" (dict "imageRoot" .Values.sawtooth.containers.validator.image "global" .Values.global)}}
*/}}
{{- define "override.lib.image" -}}
image: {{ include "override.lib.image.url" . }}
imagePullPolicy: {{ default "IfNotPresent" .imageRoot.pullPolicy }}
{{- end -}}
{{- define "dockerconfigjson" }}
{{- printf "{\"auths\": {\"%s\": {\"auth\": \"%s\"}}}" .Values.imagePullSecrets.createSecret.registryUrl (printf "%s:%s" .Values.imagePullSecrets.createSecret.registryUser .Values.imagePullSecrets.createSecret.registryPassword | b64enc) | b64enc }}
{{- end }}

View File

@ -0,0 +1,5 @@
---
{{- $serviceName := include "common.names.fullname" . -}}
{{- $ingressName := printf "%s" $serviceName -}}
{{- $servicePort := .Values.service.port -}}
{{ include "lib.ingress" (dict "ingressName" $ingressName "ingress" .Values.ingress "serviceName" $serviceName "servicePort" $servicePort "context" $) }}

View File

@ -0,0 +1,11 @@
{{- if .Values.imagePullSecrets.createSecret.enabled }}
apiVersion: v1
kind: Secret
metadata:
name: {{ template "common.names.fullname" . }}-btp-lic
labels: {{- include "lib.labels" . | nindent 4 }}
component: sextant
type: kubernetes.io/dockerconfigjson
data:
.dockerconfigjson: {{ template "dockerconfigjson" . }}
{{- end }}

View File

@ -0,0 +1,13 @@
apiVersion: v1
kind: Service
metadata:
name: {{ template "common.names.fullname" . }}
labels: {{- include "lib.labels" . | nindent 4 }}
component: sextant
spec:
type: {{ .Values.service.type }}
ports:
- port: {{ .Values.service.port }}
targetPort: 80
protocol: TCP
selector: {{- include "common.labels.matchLabels" . | nindent 4}}

View File

@ -0,0 +1,17 @@
---
{{- if .Values.serviceAccount.create }}
apiVersion: v1
kind: ServiceAccount
metadata:
name: {{ include "lib.serviceAccountName" . }}
namespace: {{.Release.Namespace}}
{{- if or .Values.imagePullSecrets.enabled .Values.imagePullSecrets.createSecret.enabled }}
imagePullSecrets:
{{- if.Values.imagePullSecrets.createSecret.enabled }}
- name: {{ template "common.names.fullname" . }}-btp-lic
{{- end }}
{{- range .Values.imagePullSecrets.value }}
- name: {{ .name }}
{{- end }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,141 @@
---
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: {{ template "common.names.fullname" . }}
namespace: {{.Release.Namespace}}
labels: {{- include "lib.labels" . | nindent 4 }}
spec:
selector:
matchLabels: {{- include "common.labels.matchLabels" . | nindent 6}}
serviceName: {{ include "common.names.fullname" . }}
template:
metadata:
labels: {{- include "lib.labels" .| nindent 8}}
spec:
serviceAccountName: {{ include "lib.serviceAccountName" . }}
containers:
{{- if .Values.postgres.enabled }}
- name: postgres
{{- include "override.lib.image" (dict "imageRoot" .Values.postgres.image "global" .Values.global ) | nindent 10 }}
ports:
- containerPort: {{.Values.postgres.port }}
resources: {{- include "lib.safeToYaml" .Values.postgres.resources | nindent 12 }}
env:
- name: PGDATA
value: /data/sextant
- name: POSTGRES_PASSWORD
{{- if .Values.postgres.existingPasswordSecret }}
valueFrom:
secretKeyRef:
name: {{ .Values.postgres.existingPasswordSecret }}
key: password
{{- else }}
value: {{ .Values.postgres.password }}
{{- end }}
{{- include "lib.safeToYaml" .Values.postgres.env | nindent 12 }}
volumeMounts:
- mountPath: /data
name: "pgdata"
{{- include "lib.volumeMounts" .Values.extraVolumeMounts | nindent 12 }}
{{- end }}
- name: api
{{- include "sextant.image" (dict "imageRoot" .Values.api.image "editionRoot" .Values.editionImages.api "edition" .Values.edition "global" .Values.global ) | nindent 10 }}
ports:
- containerPort: 8080
protocol: TCP
resources: {{- include "lib.safeToYaml" .Values.api.resources | nindent 12 }}
env:
- name: PORT
value: "8080"
- name: LOGGING
value: {{ default "1" .Values.logging |quote }}
- name: POSTGRES_USER
value: {{ default "postgres" .Values.postgres.user }}
- name: INITIAL_PASSWORD
{{- if .Values.intialPassword }}
value: {{ .Values.initialPassword | quote}}
{{- else }}
value: {{ include "sextant.randomPassword" .}}
{{- end }}
- name: INITIAL_USER
value: {{ default "admin" .Values.initialUser}}
- name: POSTGRES_PASSWORD
{{- if .Values.postgres.existingPasswordSecret }}
valueFrom:
secretKeyRef:
name: {{.Values.postgres.existingPasswordSecret}}
key: {{.Values.postgres.existingPasswordSecretKey}}
{{- else }}
value: {{ .Values.postgres.password }}
{{- end }}
- name: POSTGRES_DB
value: {{ default "postgres" .Values.postgres.database }}
- name: POSTGRES_SERVICE_HOST
value: {{ default "localhost" .Values.postgres.host }}
- name: POSTGRES_SERVICE_PORT
value: {{ default "5432" .Values.postgres.port | quote }}
{{- if .Values.postgres.tls }}
- name: POSTGRES_TLS
value: {{ .Values.postgres.tls | quote }}
{{- end }}
{{ if eq .Values.edition "enterprise" -}}
- name: NODE_ENV
value: "development"
{{- end -}}
{{- include "lib.safeToYaml" .Values.api.env | nindent 12 }}
volumeMounts:
{{- include "lib.volumeMounts" .Values.extraVolumeMounts | nindent 12 }}
- name: frontend
{{- include "sextant.image" (dict "imageRoot" .Values.ui.image "editionRoot" .Values.editionImages.ui "edition" .Values.edition "global" .Values.global ) | nindent 10 }}
ports:
- containerPort: 8081
protocol: TCP
resources: {{- include "lib.safeToYaml" .Values.ui.resources | nindent 12 }}
env:
- name: PORT
value: "8081"
{{- include "lib.safeToYaml" .Values.ui.env | nindent 12 }}
volumeMounts: {{- include "lib.volumeMounts" .Values.extraVolumeMounts | nindent 12 }}
- name: router
{{- include "override.lib.image" (dict "imageRoot" .Values.noxy.image "global" .Values.global ) | nindent 10 }}
ports:
- containerPort: 80
protocol: TCP
env:
- name: NOXY_DEFAULT_HOST
value: localhost
- name: NOXY_DEFAULT_PORT
value: "8081"
- name: NOXY_API_FRONT
value: /api/v1
- name: NOXY_API_HOST
value: localhost
- name: NOXY_API_PORT
value: "8080"
- name: NOXY_PROXY_FRONT
value: /proxy
- name: NOXY_PROXY_HOST
value: localhost
- name: NOXY_PROXY_PORT
value: "8080"
{{- include "lib.safeToYaml" .Values.noxy.env | nindent 12 }}
resources: {{- include "lib.safeToYaml" .Values.noxy.resources | nindent 12 }}
volumeMounts: {{- include "lib.volumeMounts" .Values.extraVolumeMounts | nindent 12 }}
restartPolicy: "Always"
volumes: {{- include "lib.volumes" .Values.extraVolumes | nindent 8 }}
{{- if not .Values.postgres.persistence.enabled }}
- name: "pgdata"
emptyDir: {}
{{- else }}
volumeClaimTemplates:
- metadata:
name: "pgdata"
annotations: {{- include "lib.safeToYaml" .Values.postgres.persistence.annotations | nindent 10 }}
spec:
accessModes: {{- include "lib.safeToYaml" .Values.postgres.persistence.accessModes | nindent 10 }}
storageClassName: {{ .Values.postgres.persistence.storageClass | quote }}
resources:
requests:
storage: {{ .Values.postgres.persistence.size | quote }}
{{- end }}

View File

@ -0,0 +1,11 @@
ingress links to service properly:
1: |
rules:
- host: test-host
http:
paths:
- backend:
serviceName: test-sextant
servicePort: 8000
path: /path
pathType: ImplementationSpecific

View File

@ -0,0 +1,10 @@
check for stable PVC names:
1: |
pgdata
check for stable entity names (services, statefulsets, serviceaccounts):
1: |
test-sextant
2: |
test-sextant
3: |
test-sextant

View File

@ -0,0 +1,76 @@
suite: test edition image variations
templates:
- statefulset.yaml
release:
name: test
namespace: testns
tests:
- it: default edition
set:
ui:
image:
registry: testregister:8080
repository: testui
tag: testtag
api:
image:
registry: testregister:8080
repository: testapi
tag: testtag
asserts:
- equal:
path: spec.template.spec.containers[1].image
value: testregister:8080/testapi:testtag
- equal:
path: spec.template.spec.containers[2].image
value: testregister:8080/testui:testtag
- it: aws-standard edition
set:
edition: aws-standard
editionImages:
ui:
awsStandard:
tag: testtag
api:
awsStandard:
tag: testtag
ui:
image:
registry: testregister:8080
repository: testui
tag: testtag
api:
image:
registry: testregister:8080
repository: testapi
tag: testtag
asserts:
- equal:
path: spec.template.spec.containers[1].image
value: 709825985650.dkr.ecr.us-east-1.amazonaws.com/blockchain-technology/sextant-api-standard:testtag
- equal:
path: spec.template.spec.containers[2].image
value: 709825985650.dkr.ecr.us-east-1.amazonaws.com/blockchain-technology/sextant-standard:testtag
- it: development no registry edition
set:
edition: development
editionImages:
ui:
awsStandard:
tag: testtag
api:
awsStandard:
tag: testtag
ui:
image:
registry: testregister:8080
repository: testui
tag: testtag
api:
image:
repository: testapi
tag: testtag
asserts:
- equal:
path: spec.template.spec.containers[1].image
value: testapi:testtag

View File

@ -0,0 +1,25 @@
suite: sextant.test the ingresses
templates:
- ingress.yaml
release:
name: test
namespace: testns
tests:
- it: ingress links to service properly
set:
ingress:
enabled: true
hosts:
- host: test-host
paths:
- /path
apiVersion: extensions/v1beta1
asserts:
- equal:
path: spec.rules[0].http.paths[0].backend.serviceName
value: test-sextant
- equal:
path: spec.rules[0].http.paths[0].backend.servicePort
value: 8000
- matchSnapshot:
path: spec

View File

@ -0,0 +1,22 @@
suite: sextant.test for stable names
templates:
- serviceaccount.yaml
- statefulset.yaml
- service.yaml
release:
name: test
namespace: testns
tests:
- it: check for stable entity names (services, statefulsets, serviceaccounts)
asserts:
- matchSnapshot:
path: metadata.name
- it: check for stable PVC names
template: statefulset.yaml
set:
postgres:
persistence:
enabled: true
asserts:
- matchSnapshot:
path: spec.volumeClaimTemplates[0].metadata.name

View File

@ -0,0 +1,36 @@
suite: sextant.test for storageClass values
templates:
- statefulset.yaml
release:
name: test
namespace: testns
tests:
- it: check the postgres PVC storageClassName is set to null
set:
postgres:
persistence:
enabled: true
asserts:
- equal:
path: spec.volumeClaimTemplates[0].spec.storageClassName
value: null
- it: check the postgres PVC storageClassName is set to an empty string
set:
postgres:
persistence:
enabled: true
storageClass: ""
asserts:
- equal:
path: spec.volumeClaimTemplates[0].spec.storageClassName
value: ""
- it: check the postgres PVC storageClassName is set to ab1
set:
postgres:
persistence:
enabled: true
storageClass: ab1
asserts:
- equal:
path: spec.volumeClaimTemplates[0].spec.storageClassName
value: ab1

View File

@ -0,0 +1,244 @@
## @md # Sextant
## @md
## @md This chart is the base chart to install BTP Sextant. By default it
## @md installs the development version of Sextant. It's intended use is as
## @md a dependency of other charts which install particular editions of the
## @md software.
## @md
## @md ## Configuration
## @md
## @md | field | description | type | default |
## @md |-|-|-|-|
# aws-standard
# aws-premium
# aws-enterprise
# enterprise
# development
# community
edition: community
editionImages:
ui:
awsStandard:
registry: 709825985650.dkr.ecr.us-east-1.amazonaws.com
repository: blockchain-technology/sextant-standard
tag: BTP2.1.0-2.1.5
awsPremium:
registry: 709825985650.dkr.ecr.us-east-1.amazonaws.com
repository: blockchain-technology/sextant-premium
tag: BTP2.1.0-2.1.5
awsEnterprise:
registry: 709825985650.dkr.ecr.us-east-1.amazonaws.com
repository: blockchain-technology/sextant-enterprise
tag: BTP2.1.0-2.1.5
enterprise:
registry: dev.catenasys.com:8084
repository: blockchaintp/sextant-enterprise
tag: BTP2.1.0-2.1.5
community:
registry: dev.catenasys.com:8084
repository: blockchaintp/sextant-community
tag: BTP2.1.0
api:
awsStandard:
registry: 709825985650.dkr.ecr.us-east-1.amazonaws.com
repository: blockchain-technology/sextant-api-standard
tag: BTP2.1.0-2.2.5
awsPremium:
registry: 709825985650.dkr.ecr.us-east-1.amazonaws.com
repository: blockchain-technology/sextant-api-premium
tag: BTP2.1.0-2.2.5
awsEnterprise:
registry: 709825985650.dkr.ecr.us-east-1.amazonaws.com
repository: blockchain-technology/sextant-api-enterprise
tag: BTP2.1.0-2.2.5
enterprise:
registry: dev.catenasys.com:8084
repository: blockchaintp/sextant-api-enterprise
tag: BTP2.1.0-2.2.5
community:
registry: dev.catenasys.com:8084
repository: blockchaintp/sextant-api-community
tag: BTP2.1.0
deployment:
name: sextant
namespace: default
imagePullSecrets:
## @md | `imagePullSecrets.enabled` | true if imagePullSecrets are required | boolean | false |
enabled: false
## @md | `imagePullSecrets.value` | a list of named secret references of the form ```- name: secretName```| list | [] |
value: []
createSecret:
## @md | `imagePullSecrets.createSecret.enabled` | true to create a image pull secret | boolean | false |
enabled: true
## @md | `imagePullSecrets.createSecret.registryUrl` | the registry url | string | nil |
registryUrl: dev.catenasys.com:8084
## @md | `imagePullSecrets.createSecret.registryUser` | the username for the registry | string | nil |
registryUser:
## @md | `imagePullSecrets.createSecret.registryPassword` | the password for the registry | string | nil |
registryPassword:
## @md | `replicaCount` | number of Sextant replicas to run | int | 1 |
replicaCount: 1
## @md | `logging` | default logging level | string | "1" |
logging: "1"
ui:
## @md | `ui.env` | environment variables to set in the UI container | map | nil |
env:
## @md | `ui.image` | UI image settings | map | N/A |
image:
registry:
## @md | `ui.image.repository` | UI image repository | string | "dev.catenasys.com:8083/blockchaintp/sextant" |
repository: blockchaintp/sextant
## @md | `ui.image.tag` | UI image tag | string | "latest" |
tag: latest
## @md | `ui.image.pullPolicy` | UI image pull policy | string | "IfNotPresent" |
pullPolicy: IfNotPresent
## @md | `ui.resources` | UI resources | map | nil |
resources:
limits:
cpu: "100m"
memory: "400Mi"
requests:
cpu: "20m"
memory: "40Mi"
api:
## @md | `api.env` | API environment settings | map | N/A |
env:
## @md | `api.image` | API image settings | map | N/A |
image:
registry:
## @md | `api.image.repository` | API image repository | string | "dev.catenasys.com:8083/blockchaintp/sextant-api" |
repository: blockchaintp/sextant-api
## @md | `api.image.tag` | API image tag | string | "latest" |
tag: latest
## @md | `api.image.pullPolicy` | API image pull policy | string | "IfNotPresent" |
pullPolicy: IfNotPresent
## @md | `api.resources` | UI resources | map | nil |
resources:
limits:
cpu: "100m"
memory: "300Mi"
requests:
cpu: "20m"
memory: "80Mi"
noxy:
## @md | `noxy.env` | Noxy environment variables | map | N/A |
env:
## @md | `noxy.image` | noxy image settings | map | N/A |
image:
registry:
## @md | `noxy.image.repository` | NOXY image repository | string | "dev.catenasys.com:8083/blockchaintp/noxy" |
repository: blockchaintp/noxy
## @md | `noxy.image.tag` | noxy image tag | string | "latest" |
tag: BTP2.1.0
## @md | `noxy.image.pullPolicy` | API image pull policy | string | "IfNotPresent" |
pullPolicy: IfNotPresent
## @md | `noxy.resources` | UI resources | map | nil |
resources:
limits:
cpu: "100m"
memory: "60Mi"
requests:
cpu: "20m"
memory: "30Mi"
serviceAccount:
## @md | `serviceAccount.create` | if true create the service account | boolean | true |
create: true
## @md | `serviceAccount.name` | name of the service account for sextant | string | nil |
name:
postgres:
# if enabled we allocate a postgres database here
## @md | `postgres.enabled` | if true create an internal postgres instance | boolean | true |
enabled: true
## @md | `postgres.env` | postgres environment variables | map | N/A |
env:
image:
registry:
## @md | `postgres.image.repository` | postgres image repository | string | "postgres" |
repository: postgres
## @md | `postgres.image.tag` | postgres image tag | string | "11" |
tag: "11"
## @md | `postgres.user` | user for the postgres database | string | "postgres" |
user: postgres
## @md | `postgres.host` | host for the postgres database | string | "localhost" |
host: localhost
## @md | `postgres.database` | database for the postgres database | string | "postgres" |
database: postgres
## @md | `postgres.port` | port for the postgres database | int | 5432 |
port: 5432
## @md | `postgres.password` | password for the postgres database | string | "postgres" |
password: postgres
## @md | `postgres.existingPasswordSecret` | name of a secret containing the postgres password | string | nil |
existingPasswordSecret:
## @md | `postgres.existingPasswordSecret` | name of the key in a secret containing the postgres password | string | password |
existingPasswordSecretKey: password
## @md | `postgres.tls` | postgres TLS configuration | string | nil |
tls:
## @md | `postgres.persistence` | postgres persistence settings | map | N/A |
persistence:
## @md | `postgres.persistence.enabled` | if true allocate a PVC for the postgres instance | boolean | false |
enabled: true
## @md | `postgres.persistence.annotations` | any custom annotations to the postgres PVC's | map | {} |
annotations: {}
## @md | `postgres.persistence.accessModes` | postgres PVC access modes | list | [ "ReadWriteOnce" ] |
accessModes:
- "ReadWriteOnce"
## if set to "-" (empty string) then storageClassName: "", which disables dynamic provisioning
## if undefined or set to null, no storageClassName is set and the clusters default StorageClass will be used
## if a storageClass name is set then storageClassName: "setValue"
## @md | `postgres.persistence.storageClass` | postgres PVC storageClass | string | nil |
storageClass:
## @md | `postgres.persistence.size` | postgres PVC volume size | string | "40Gi" |
size: "40Gi"
## @md | `postgres.resources` | UI resources | map | nil |
resources:
service:
## @md | `service.type` | Sextant service type | string | ClusterIP |
type: ClusterIP
## @md | `service.port` | Sextant service port | int | 8000 |
port: 8000
ingress:
## @md | `ingress.apiVersion` | if necessary the apiVersion of the ingress may be overridden | "" |
apiVersion: ""
## @md | `ingress.enabled` | true to enable the ingress to the main service rest-api | false |
enabled: false
## @md | `ingress.certManager` | true to enable the acme certmanager for this ingress | false |
certManager: false
## @md | `ingress.hostname` | primary hostname for the ingress | false |
hostname:
## @md | `ingress.path` | path for the ingress's primary hostname | / |
path: /
## @md | `ingress.pathType` | pathType for the ingress's primary hostname | nil |
pathType:
## @md | `ingress.annotations` | annotations for the ingress | {} |
annotations: {}
## @md | `ingress.tls` | true to enable tls on the ingress with a secrete at hostname-tls | false(truthy) |
tls: false
## @md | `ingress.extraHosts` | list of extra hosts to add to the ingress | [] |
extraHosts: []
## @md | `ingress.extraPaths` | list of extra paths to add to the primary host of the ingress | [] |
extraPaths: []
## @md | `ingress.extraTls` | list of extra tls entries | [] |
extraTls: []
## @md | `ingress.hosts` | a list of host and path lists to publish in the ingress (deprecated)| map | {} |
hosts: []
## @md | `extraVolumes` | a list of additional volumes to add to all StatefulSets, Deployments, and DaemonSets | `[]` |
extraVolumes: []
## @md | `extraVolumeMounts` | a list of additional volume mounts to add to all StatefulSet, Deployment, and DaemonSet containers | `[]` |
extraVolumeMounts: []

View File

@ -0,0 +1 @@
tests/

View File

@ -0,0 +1,26 @@
annotations:
catalog.cattle.io/certified: partner
catalog.cattle.io/display-name: Traefik Proxy
catalog.cattle.io/release-name: traefik
apiVersion: v2
appVersion: 2.6.1
description: A Traefik based Kubernetes ingress controller
home: https://traefik.io/
icon: https://raw.githubusercontent.com/traefik/traefik/v2.3/docs/content/assets/img/traefik.logo.png
keywords:
- traefik
- ingress
kubeVersion: '>= 1.16.0-0'
maintainers:
- email: emile@vauge.com
name: emilevauge
- email: daniel.tomcej@gmail.com
name: dtomcej
- email: ldez@traefik.io
name: ldez
name: traefik
sources:
- https://github.com/traefik/traefik
- https://github.com/traefik/traefik-helm-chart
type: application
version: 10.15.0

View File

@ -0,0 +1,93 @@
# Traefik Helm Chart Guidelines
This document outlines the guidelines for developing, managing and extending the Traefik helm chart.
Optionallity
All non-critical features (Features not mandatory to starting Traefik) in the helm chart must be optional. All non-critical features should be disabled (commented out) in the values.yaml file. All optional non-critical features should be disabled (commented out) in the values.yaml file, and have a comment # (Optional) in the line above. This allows minimal configuration, and ease of extension.
## Critical Feature Example
```yaml
image:
name: traefik
```
This feature is critical, and therefore is defined clearly in the values.yaml file.
## Non-Critical Feature Example
```yaml
# storage:
# controlNode:
# type: emptyDir
```
This feature is non-critical, and therefore is commented out by default in the values.yaml file.
To allow this, template blocks that use this need to recursively test for existence of values before using them:
```yaml
{{- if .Values.storage}}
{{- if .Values.storage.controlNode }}
//code
{{ .Values.storage.controlNode.type }}
{{- end }}
{{- end }}
```
The non-critical feature defaults should be populated so that they can be enabled by simply uncommenting the section in the values.yaml file.
## Optional Non-Critical Feature Example
```yaml
# storage:
# controlNode:
# type: emptyDir
# # (Optional)
# # volume: 1Gi
```
The volume option is clearly optional, and non-critical. It is commented out (apart from the storage section comment block), and is also preceeded by a comment of # (Optional) in the preceeding line. This facilitates configuration, when the storage section is uncommented, the optional features are still disabled by default.
Similar to non-critical feaures, these options need to be tested for existance before use in the template.
Note
There can be optional values in critical features. These should just be added as an uncommented non-critical feature:
```yaml
image:
name: traefik
tag: 2.0.0
# (Optional)
# pullPolicy: IfNotPresent
```
Also, the first value under the primary value key does not require an optional comment:
```yaml
# ports:
# http: 80
# # (Optional)
# # https: 443
```
This is because if the main subkey is not defined, the entirety of the feature is optional.
## Whitespace
Extra whitespace is to be avoided in templating. Conditionals should chomp whitespace:
```yaml
{{- if .Values }}
{{- end }}
```
There should be an empty commented line between each primary key in the values.yaml file to separate features from each other.
## Values YAML Design
The values.yaml file is designed to be user-friendly. It does not have to resemble the templated configuration if it is not conducive. Similarly, value names to not have to correspond to fields in the tempate if it is not condusive.
## Comments
The values.yaml file should not contain comments or explainations of what options are, or what values are available. The values table in the README file is for this purpose.

View File

@ -0,0 +1,202 @@
Apache License
Version 2.0, January 2004
http://www.apache.org/licenses/
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
1. Definitions.
"License" shall mean the terms and conditions for use, reproduction,
and distribution as defined by Sections 1 through 9 of this document.
"Licensor" shall mean the copyright owner or entity authorized by
the copyright owner that is granting the License.
"Legal Entity" shall mean the union of the acting entity and all
other entities that control, are controlled by, or are under common
control with that entity. For the purposes of this definition,
"control" means (i) the power, direct or indirect, to cause the
direction or management of such entity, whether by contract or
otherwise, or (ii) ownership of fifty percent (50%) or more of the
outstanding shares, or (iii) beneficial ownership of such entity.
"You" (or "Your") shall mean an individual or Legal Entity
exercising permissions granted by this License.
"Source" form shall mean the preferred form for making modifications,
including but not limited to software source code, documentation
source, and configuration files.
"Object" form shall mean any form resulting from mechanical
transformation or translation of a Source form, including but
not limited to compiled object code, generated documentation,
and conversions to other media types.
"Work" shall mean the work of authorship, whether in Source or
Object form, made available under the License, as indicated by a
copyright notice that is included in or attached to the work
(an example is provided in the Appendix below).
"Derivative Works" shall mean any work, whether in Source or Object
form, that is based on (or derived from) the Work and for which the
editorial revisions, annotations, elaborations, or other modifications
represent, as a whole, an original work of authorship. For the purposes
of this License, Derivative Works shall not include works that remain
separable from, or merely link (or bind by name) to the interfaces of,
the Work and Derivative Works thereof.
"Contribution" shall mean any work of authorship, including
the original version of the Work and any modifications or additions
to that Work or Derivative Works thereof, that is intentionally
submitted to Licensor for inclusion in the Work by the copyright owner
or by an individual or Legal Entity authorized to submit on behalf of
the copyright owner. For the purposes of this definition, "submitted"
means any form of electronic, verbal, or written communication sent
to the Licensor or its representatives, including but not limited to
communication on electronic mailing lists, source code control systems,
and issue tracking systems that are managed by, or on behalf of, the
Licensor for the purpose of discussing and improving the Work, but
excluding communication that is conspicuously marked or otherwise
designated in writing by the copyright owner as "Not a Contribution."
"Contributor" shall mean Licensor and any individual or Legal Entity
on behalf of whom a Contribution has been received by Licensor and
subsequently incorporated within the Work.
2. Grant of Copyright License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
copyright license to reproduce, prepare Derivative Works of,
publicly display, publicly perform, sublicense, and distribute the
Work and such Derivative Works in Source or Object form.
3. Grant of Patent License. Subject to the terms and conditions of
this License, each Contributor hereby grants to You a perpetual,
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
(except as stated in this section) patent license to make, have made,
use, offer to sell, sell, import, and otherwise transfer the Work,
where such license applies only to those patent claims licensable
by such Contributor that are necessarily infringed by their
Contribution(s) alone or by combination of their Contribution(s)
with the Work to which such Contribution(s) was submitted. If You
institute patent litigation against any entity (including a
cross-claim or counterclaim in a lawsuit) alleging that the Work
or a Contribution incorporated within the Work constitutes direct
or contributory patent infringement, then any patent licenses
granted to You under this License for that Work shall terminate
as of the date such litigation is filed.
4. Redistribution. You may reproduce and distribute copies of the
Work or Derivative Works thereof in any medium, with or without
modifications, and in Source or Object form, provided that You
meet the following conditions:
(a) You must give any other recipients of the Work or
Derivative Works a copy of this License; and
(b) You must cause any modified files to carry prominent notices
stating that You changed the files; and
(c) You must retain, in the Source form of any Derivative Works
that You distribute, all copyright, patent, trademark, and
attribution notices from the Source form of the Work,
excluding those notices that do not pertain to any part of
the Derivative Works; and
(d) If the Work includes a "NOTICE" text file as part of its
distribution, then any Derivative Works that You distribute must
include a readable copy of the attribution notices contained
within such NOTICE file, excluding those notices that do not
pertain to any part of the Derivative Works, in at least one
of the following places: within a NOTICE text file distributed
as part of the Derivative Works; within the Source form or
documentation, if provided along with the Derivative Works; or,
within a display generated by the Derivative Works, if and
wherever such third-party notices normally appear. The contents
of the NOTICE file are for informational purposes only and
do not modify the License. You may add Your own attribution
notices within Derivative Works that You distribute, alongside
or as an addendum to the NOTICE text from the Work, provided
that such additional attribution notices cannot be construed
as modifying the License.
You may add Your own copyright statement to Your modifications and
may provide additional or different license terms and conditions
for use, reproduction, or distribution of Your modifications, or
for any such Derivative Works as a whole, provided Your use,
reproduction, and distribution of the Work otherwise complies with
the conditions stated in this License.
5. Submission of Contributions. Unless You explicitly state otherwise,
any Contribution intentionally submitted for inclusion in the Work
by You to the Licensor shall be under the terms and conditions of
this License, without any additional terms or conditions.
Notwithstanding the above, nothing herein shall supersede or modify
the terms of any separate license agreement you may have executed
with Licensor regarding such Contributions.
6. Trademarks. This License does not grant permission to use the trade
names, trademarks, service marks, or product names of the Licensor,
except as required for reasonable and customary use in describing the
origin of the Work and reproducing the content of the NOTICE file.
7. Disclaimer of Warranty. Unless required by applicable law or
agreed to in writing, Licensor provides the Work (and each
Contributor provides its Contributions) on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
implied, including, without limitation, any warranties or conditions
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
PARTICULAR PURPOSE. You are solely responsible for determining the
appropriateness of using or redistributing the Work and assume any
risks associated with Your exercise of permissions under this License.
8. Limitation of Liability. In no event and under no legal theory,
whether in tort (including negligence), contract, or otherwise,
unless required by applicable law (such as deliberate and grossly
negligent acts) or agreed to in writing, shall any Contributor be
liable to You for damages, including any direct, indirect, special,
incidental, or consequential damages of any character arising as a
result of this License or out of the use or inability to use the
Work (including but not limited to damages for loss of goodwill,
work stoppage, computer failure or malfunction, or any and all
other commercial damages or losses), even if such Contributor
has been advised of the possibility of such damages.
9. Accepting Warranty or Additional Liability. While redistributing
the Work or Derivative Works thereof, You may choose to offer,
and charge a fee for, acceptance of support, warranty, indemnity,
or other liability obligations and/or rights consistent with this
License. However, in accepting such obligations, You may act only
on Your own behalf and on Your sole responsibility, not on behalf
of any other Contributor, and only if You agree to indemnify,
defend, and hold each Contributor harmless for any liability
incurred by, or claims asserted against, such Contributor by reason
of your accepting any such warranty or additional liability.
END OF TERMS AND CONDITIONS
APPENDIX: How to apply the Apache License to your work.
To apply the Apache License to your work, attach the following
boilerplate notice, with the fields enclosed by brackets "[]"
replaced with your own identifying information. (Don't include
the brackets!) The text should be enclosed in the appropriate
comment syntax for the file format. We also recommend that a
file or class name and description of purpose be included on the
same "printed page" as the copyright notice for easier
identification within third-party archives.
Copyright 2020 Containous
Copyright 2020 Traefik Labs
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.

View File

@ -0,0 +1,93 @@
# Traefik
[Traefik](https://traefik.io/) is a modern HTTP reverse proxy and load balancer made to deploy
microservices with ease.
## Introduction
This chart bootstraps Traefik version 2 as a Kubernetes ingress controller,
using Custom Resources `IngressRoute`: <https://docs.traefik.io/providers/kubernetes-crd/>.
### Philosophy
The Traefik HelmChart is focused on Traefik deployment configuration.
To keep this HelmChart as generic as possible we tend
to avoid integrating any third party solutions nor any specific use cases.
Accordingly, the encouraged approach to fulfill your needs:
1. override the default Traefik configuration values ([yaml file or cli](https://helm.sh/docs/chart_template_guide/values_files/))
2. append your own configurations (`kubectl apply -f myconf.yaml`)
3. extend this HelmChart ([as a Subchart](https://helm.sh/docs/chart_template_guide/subcharts_and_globals/))
## Installing
### Prerequisites
With the command `helm version`, make sure that you have:
- Helm v3 [installed](https://helm.sh/docs/using_helm/#installing-helm)
Add Traefik's chart repository to Helm:
```bash
helm repo add traefik https://helm.traefik.io/traefik
```
You can update the chart repository by running:
```bash
helm repo update
```
### Kubernetes Version Support
Due to changes in CRD version support, the following versions of the chart are usable and supported on the following kubernetes versions:
| | Kubernetes v1.15 and below | Kubernetes v1.16-v1.21 | Kubernetes v1.22 and above |
|-------------------------|-----------------------------|------------------------|----------------------------|
| Chart v9.20.2 and below | [x] | [x] | |
| Chart 10.0.0 and above | | [x] | [x] |
### Deploying Traefik
```bash
helm install traefik traefik/traefik
```
#### Warning
Helm v2 support was removed in the chart version 10.0.0.
### Exposing the Traefik dashboard
This HelmChart does not expose the Traefik dashboard by default, for security concerns.
Thus, there are multiple ways to expose the dashboard.
For instance, the dashboard access could be achieved through a port-forward :
```
kubectl port-forward $(kubectl get pods --selector "app.kubernetes.io/name=traefik" --output=name) 9000:9000
```
Another way would be to apply your own configuration, for instance,
by defining and applying an IngressRoute CRD (`kubectl apply -f dashboard.yaml`):
```yaml
# dashboard.yaml
apiVersion: traefik.containo.us/v1alpha1
kind: IngressRoute
metadata:
name: dashboard
spec:
entryPoints:
- web
routes:
- match: Host(`traefik.localhost`) && (PathPrefix(`/dashboard`) || PathPrefix(`/api`))
kind: Rule
services:
- name: api@internal
kind: TraefikService
```
## Contributing
If you want to contribute to this chart, please read the [Contributing Guide](../CONTRIBUTING.md).

View File

@ -0,0 +1,5 @@
# Traefik Proxy
[Traefik](https://traefik.io/) is a modern HTTP reverse proxy and load balancer made to deploy microservices with ease.
This chart bootstraps Traefik version 2 as a Kubernetes ingress controller.

View File

@ -0,0 +1,196 @@
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.4.1
creationTimestamp: null
name: ingressroutes.traefik.containo.us
spec:
group: traefik.containo.us
names:
kind: IngressRoute
listKind: IngressRouteList
plural: ingressroutes
singular: ingressroute
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: IngressRoute is an Ingress CRD specification.
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this representation
of an object. Servers should convert recognized schemas to the latest
internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: IngressRouteSpec is a specification for a IngressRouteSpec
resource.
properties:
entryPoints:
items:
type: string
type: array
routes:
items:
description: Route contains the set of routes.
properties:
kind:
enum:
- Rule
type: string
match:
type: string
middlewares:
items:
description: MiddlewareRef is a ref to the Middleware resources.
properties:
name:
type: string
namespace:
type: string
required:
- name
type: object
type: array
priority:
type: integer
services:
items:
description: Service defines an upstream to proxy traffic.
properties:
kind:
enum:
- Service
- TraefikService
type: string
name:
description: Name is a reference to a Kubernetes Service
object (for a load-balancer of servers), or to a TraefikService
object (service load-balancer, mirroring, etc). The
differentiation between the two is specified in the
Kind field.
type: string
namespace:
type: string
passHostHeader:
type: boolean
port:
anyOf:
- type: integer
- type: string
x-kubernetes-int-or-string: true
responseForwarding:
description: ResponseForwarding holds configuration for
the forward of the response.
properties:
flushInterval:
type: string
type: object
scheme:
type: string
serversTransport:
type: string
sticky:
description: Sticky holds the sticky configuration.
properties:
cookie:
description: Cookie holds the sticky configuration
based on cookie.
properties:
httpOnly:
type: boolean
name:
type: string
sameSite:
type: string
secure:
type: boolean
type: object
type: object
strategy:
type: string
weight:
description: Weight should only be specified when Name
references a TraefikService object (and to be precise,
one that embeds a Weighted Round Robin).
type: integer
required:
- name
type: object
type: array
required:
- kind
- match
type: object
type: array
tls:
description: "TLS contains the TLS certificates configuration of the
routes. To enable Let's Encrypt, use an empty TLS struct, e.g. in
YAML: \n \t tls: {} # inline format \n \t tls: \t secretName:
# block format"
properties:
certResolver:
type: string
domains:
items:
description: Domain holds a domain name with SANs.
properties:
main:
type: string
sans:
items:
type: string
type: array
type: object
type: array
options:
description: Options is a reference to a TLSOption, that specifies
the parameters of the TLS connection.
properties:
name:
type: string
namespace:
type: string
required:
- name
type: object
secretName:
description: SecretName is the name of the referenced Kubernetes
Secret to specify the certificate details.
type: string
store:
description: Store is a reference to a TLSStore, that specifies
the parameters of the TLS store.
properties:
name:
type: string
namespace:
type: string
required:
- name
type: object
type: object
required:
- routes
type: object
required:
- metadata
- spec
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []

View File

@ -0,0 +1,158 @@
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.4.1
creationTimestamp: null
name: ingressroutetcps.traefik.containo.us
spec:
group: traefik.containo.us
names:
kind: IngressRouteTCP
listKind: IngressRouteTCPList
plural: ingressroutetcps
singular: ingressroutetcp
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: IngressRouteTCP is an Ingress CRD specification.
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this representation
of an object. Servers should convert recognized schemas to the latest
internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: IngressRouteTCPSpec is a specification for a IngressRouteTCPSpec
resource.
properties:
entryPoints:
items:
type: string
type: array
routes:
items:
description: RouteTCP contains the set of routes.
properties:
match:
type: string
middlewares:
description: Middlewares contains references to MiddlewareTCP
resources.
items:
description: ObjectReference is a generic reference to a Traefik
resource.
properties:
name:
type: string
namespace:
type: string
required:
- name
type: object
type: array
services:
items:
description: ServiceTCP defines an upstream to proxy traffic.
properties:
name:
type: string
namespace:
type: string
port:
anyOf:
- type: integer
- type: string
x-kubernetes-int-or-string: true
proxyProtocol:
description: ProxyProtocol holds the ProxyProtocol configuration.
properties:
version:
type: integer
type: object
terminationDelay:
type: integer
weight:
type: integer
required:
- name
- port
type: object
type: array
required:
- match
type: object
type: array
tls:
description: "TLSTCP contains the TLS certificates configuration of
the routes. To enable Let's Encrypt, use an empty TLS struct, e.g.
in YAML: \n \t tls: {} # inline format \n \t tls: \t secretName:
# block format"
properties:
certResolver:
type: string
domains:
items:
description: Domain holds a domain name with SANs.
properties:
main:
type: string
sans:
items:
type: string
type: array
type: object
type: array
options:
description: Options is a reference to a TLSOption, that specifies
the parameters of the TLS connection.
properties:
name:
type: string
namespace:
type: string
required:
- name
type: object
passthrough:
type: boolean
secretName:
description: SecretName is the name of the referenced Kubernetes
Secret to specify the certificate details.
type: string
store:
description: Store is a reference to a TLSStore, that specifies
the parameters of the TLS store.
properties:
name:
type: string
namespace:
type: string
required:
- name
type: object
type: object
required:
- routes
type: object
required:
- metadata
- spec
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []

View File

@ -0,0 +1,82 @@
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.4.1
creationTimestamp: null
name: ingressrouteudps.traefik.containo.us
spec:
group: traefik.containo.us
names:
kind: IngressRouteUDP
listKind: IngressRouteUDPList
plural: ingressrouteudps
singular: ingressrouteudp
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: IngressRouteUDP is an Ingress CRD specification.
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this representation
of an object. Servers should convert recognized schemas to the latest
internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: IngressRouteUDPSpec is a specification for a IngressRouteUDPSpec
resource.
properties:
entryPoints:
items:
type: string
type: array
routes:
items:
description: RouteUDP contains the set of routes.
properties:
services:
items:
description: ServiceUDP defines an upstream to proxy traffic.
properties:
name:
type: string
namespace:
type: string
port:
anyOf:
- type: integer
- type: string
x-kubernetes-int-or-string: true
weight:
type: integer
required:
- name
- port
type: object
type: array
type: object
type: array
required:
- routes
type: object
required:
- metadata
- spec
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []

View File

@ -0,0 +1,564 @@
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.4.1
creationTimestamp: null
name: middlewares.traefik.containo.us
spec:
group: traefik.containo.us
names:
kind: Middleware
listKind: MiddlewareList
plural: middlewares
singular: middleware
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: Middleware is a specification for a Middleware resource.
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this representation
of an object. Servers should convert recognized schemas to the latest
internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: MiddlewareSpec holds the Middleware configuration.
properties:
addPrefix:
description: AddPrefix holds the AddPrefix configuration.
properties:
prefix:
type: string
type: object
basicAuth:
description: BasicAuth holds the HTTP basic authentication configuration.
properties:
headerField:
type: string
realm:
type: string
removeHeader:
type: boolean
secret:
type: string
type: object
buffering:
description: Buffering holds the request/response buffering configuration.
properties:
maxRequestBodyBytes:
format: int64
type: integer
maxResponseBodyBytes:
format: int64
type: integer
memRequestBodyBytes:
format: int64
type: integer
memResponseBodyBytes:
format: int64
type: integer
retryExpression:
type: string
type: object
chain:
description: Chain holds a chain of middlewares.
properties:
middlewares:
items:
description: MiddlewareRef is a ref to the Middleware resources.
properties:
name:
type: string
namespace:
type: string
required:
- name
type: object
type: array
type: object
circuitBreaker:
description: CircuitBreaker holds the circuit breaker configuration.
properties:
expression:
type: string
type: object
compress:
description: Compress holds the compress configuration.
properties:
excludedContentTypes:
items:
type: string
type: array
type: object
contentType:
description: ContentType middleware - or rather its unique `autoDetect`
option - specifies whether to let the `Content-Type` header, if
it has not been set by the backend, be automatically set to a value
derived from the contents of the response. As a proxy, the default
behavior should be to leave the header alone, regardless of what
the backend did with it. However, the historic default was to always
auto-detect and set the header if it was nil, and it is going to
be kept that way in order to support users currently relying on
it. This middleware exists to enable the correct behavior until
at least the default one can be changed in a future version.
properties:
autoDetect:
type: boolean
type: object
digestAuth:
description: DigestAuth holds the Digest HTTP authentication configuration.
properties:
headerField:
type: string
realm:
type: string
removeHeader:
type: boolean
secret:
type: string
type: object
errors:
description: ErrorPage holds the custom error page configuration.
properties:
query:
type: string
service:
description: Service defines an upstream to proxy traffic.
properties:
kind:
enum:
- Service
- TraefikService
type: string
name:
description: Name is a reference to a Kubernetes Service object
(for a load-balancer of servers), or to a TraefikService
object (service load-balancer, mirroring, etc). The differentiation
between the two is specified in the Kind field.
type: string
namespace:
type: string
passHostHeader:
type: boolean
port:
anyOf:
- type: integer
- type: string
x-kubernetes-int-or-string: true
responseForwarding:
description: ResponseForwarding holds configuration for the
forward of the response.
properties:
flushInterval:
type: string
type: object
scheme:
type: string
serversTransport:
type: string
sticky:
description: Sticky holds the sticky configuration.
properties:
cookie:
description: Cookie holds the sticky configuration based
on cookie.
properties:
httpOnly:
type: boolean
name:
type: string
sameSite:
type: string
secure:
type: boolean
type: object
type: object
strategy:
type: string
weight:
description: Weight should only be specified when Name references
a TraefikService object (and to be precise, one that embeds
a Weighted Round Robin).
type: integer
required:
- name
type: object
status:
items:
type: string
type: array
type: object
forwardAuth:
description: ForwardAuth holds the http forward authentication configuration.
properties:
address:
type: string
authRequestHeaders:
items:
type: string
type: array
authResponseHeaders:
items:
type: string
type: array
authResponseHeadersRegex:
type: string
tls:
description: ClientTLS holds TLS specific configurations as client.
properties:
caOptional:
type: boolean
caSecret:
type: string
certSecret:
type: string
insecureSkipVerify:
type: boolean
type: object
trustForwardHeader:
type: boolean
type: object
headers:
description: Headers holds the custom header configuration.
properties:
accessControlAllowCredentials:
description: AccessControlAllowCredentials is only valid if true.
false is ignored.
type: boolean
accessControlAllowHeaders:
description: AccessControlAllowHeaders must be used in response
to a preflight request with Access-Control-Request-Headers set.
items:
type: string
type: array
accessControlAllowMethods:
description: AccessControlAllowMethods must be used in response
to a preflight request with Access-Control-Request-Method set.
items:
type: string
type: array
accessControlAllowOriginList:
description: AccessControlAllowOriginList is a list of allowable
origins. Can also be a wildcard origin "*".
items:
type: string
type: array
accessControlAllowOriginListRegex:
description: AccessControlAllowOriginListRegex is a list of allowable
origins written following the Regular Expression syntax (https://golang.org/pkg/regexp/).
items:
type: string
type: array
accessControlExposeHeaders:
description: AccessControlExposeHeaders sets valid headers for
the response.
items:
type: string
type: array
accessControlMaxAge:
description: AccessControlMaxAge sets the time that a preflight
request may be cached.
format: int64
type: integer
addVaryHeader:
description: AddVaryHeader controls if the Vary header is automatically
added/updated when the AccessControlAllowOriginList is set.
type: boolean
allowedHosts:
items:
type: string
type: array
browserXssFilter:
type: boolean
contentSecurityPolicy:
type: string
contentTypeNosniff:
type: boolean
customBrowserXSSValue:
type: string
customFrameOptionsValue:
type: string
customRequestHeaders:
additionalProperties:
type: string
type: object
customResponseHeaders:
additionalProperties:
type: string
type: object
featurePolicy:
description: 'Deprecated: use PermissionsPolicy instead.'
type: string
forceSTSHeader:
type: boolean
frameDeny:
type: boolean
hostsProxyHeaders:
items:
type: string
type: array
isDevelopment:
type: boolean
permissionsPolicy:
type: string
publicKey:
type: string
referrerPolicy:
type: string
sslForceHost:
description: 'Deprecated: use RedirectRegex instead.'
type: boolean
sslHost:
description: 'Deprecated: use RedirectRegex instead.'
type: string
sslProxyHeaders:
additionalProperties:
type: string
type: object
sslRedirect:
description: 'Deprecated: use EntryPoint redirection or RedirectScheme
instead.'
type: boolean
sslTemporaryRedirect:
description: 'Deprecated: use EntryPoint redirection or RedirectScheme
instead.'
type: boolean
stsIncludeSubdomains:
type: boolean
stsPreload:
type: boolean
stsSeconds:
format: int64
type: integer
type: object
inFlightReq:
description: InFlightReq limits the number of requests being processed
and served concurrently.
properties:
amount:
format: int64
type: integer
sourceCriterion:
description: SourceCriterion defines what criterion is used to
group requests as originating from a common source. If none
are set, the default is to use the request's remote address
field. All fields are mutually exclusive.
properties:
ipStrategy:
description: IPStrategy holds the ip strategy configuration.
properties:
depth:
type: integer
excludedIPs:
items:
type: string
type: array
type: object
requestHeaderName:
type: string
requestHost:
type: boolean
type: object
type: object
ipWhiteList:
description: IPWhiteList holds the ip white list configuration.
properties:
ipStrategy:
description: IPStrategy holds the ip strategy configuration.
properties:
depth:
type: integer
excludedIPs:
items:
type: string
type: array
type: object
sourceRange:
items:
type: string
type: array
type: object
passTLSClientCert:
description: PassTLSClientCert holds the TLS client cert headers configuration.
properties:
info:
description: TLSClientCertificateInfo holds the client TLS certificate
info configuration.
properties:
issuer:
description: TLSCLientCertificateDNInfo holds the client TLS
certificate distinguished name info configuration. cf https://tools.ietf.org/html/rfc3739
properties:
commonName:
type: boolean
country:
type: boolean
domainComponent:
type: boolean
locality:
type: boolean
organization:
type: boolean
province:
type: boolean
serialNumber:
type: boolean
type: object
notAfter:
type: boolean
notBefore:
type: boolean
sans:
type: boolean
serialNumber:
type: boolean
subject:
description: TLSCLientCertificateDNInfo holds the client TLS
certificate distinguished name info configuration. cf https://tools.ietf.org/html/rfc3739
properties:
commonName:
type: boolean
country:
type: boolean
domainComponent:
type: boolean
locality:
type: boolean
organization:
type: boolean
province:
type: boolean
serialNumber:
type: boolean
type: object
type: object
pem:
type: boolean
type: object
plugin:
additionalProperties:
x-kubernetes-preserve-unknown-fields: true
type: object
rateLimit:
description: RateLimit holds the rate limiting configuration for a
given router.
properties:
average:
format: int64
type: integer
burst:
format: int64
type: integer
period:
anyOf:
- type: integer
- type: string
x-kubernetes-int-or-string: true
sourceCriterion:
description: SourceCriterion defines what criterion is used to
group requests as originating from a common source. If none
are set, the default is to use the request's remote address
field. All fields are mutually exclusive.
properties:
ipStrategy:
description: IPStrategy holds the ip strategy configuration.
properties:
depth:
type: integer
excludedIPs:
items:
type: string
type: array
type: object
requestHeaderName:
type: string
requestHost:
type: boolean
type: object
type: object
redirectRegex:
description: RedirectRegex holds the redirection configuration.
properties:
permanent:
type: boolean
regex:
type: string
replacement:
type: string
type: object
redirectScheme:
description: RedirectScheme holds the scheme redirection configuration.
properties:
permanent:
type: boolean
port:
type: string
scheme:
type: string
type: object
replacePath:
description: ReplacePath holds the ReplacePath configuration.
properties:
path:
type: string
type: object
replacePathRegex:
description: ReplacePathRegex holds the ReplacePathRegex configuration.
properties:
regex:
type: string
replacement:
type: string
type: object
retry:
description: Retry holds the retry configuration.
properties:
attempts:
type: integer
initialInterval:
anyOf:
- type: integer
- type: string
x-kubernetes-int-or-string: true
type: object
stripPrefix:
description: StripPrefix holds the StripPrefix configuration.
properties:
forceSlash:
type: boolean
prefixes:
items:
type: string
type: array
type: object
stripPrefixRegex:
description: StripPrefixRegex holds the StripPrefixRegex configuration.
properties:
regex:
items:
type: string
type: array
type: object
type: object
required:
- metadata
- spec
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []

View File

@ -0,0 +1,64 @@
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.4.1
creationTimestamp: null
name: middlewaretcps.traefik.containo.us
spec:
group: traefik.containo.us
names:
kind: MiddlewareTCP
listKind: MiddlewareTCPList
plural: middlewaretcps
singular: middlewaretcp
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: MiddlewareTCP is a specification for a MiddlewareTCP resource.
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this representation
of an object. Servers should convert recognized schemas to the latest
internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: MiddlewareTCPSpec holds the MiddlewareTCP configuration.
properties:
inFlightConn:
description: TCPInFlightConn holds the TCP in flight connection configuration.
properties:
amount:
format: int64
type: integer
type: object
ipWhiteList:
description: TCPIPWhiteList holds the TCP ip white list configuration.
properties:
sourceRange:
items:
type: string
type: array
type: object
type: object
required:
- metadata
- spec
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []

View File

@ -0,0 +1,103 @@
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.4.1
creationTimestamp: null
name: serverstransports.traefik.containo.us
spec:
group: traefik.containo.us
names:
kind: ServersTransport
listKind: ServersTransportList
plural: serverstransports
singular: serverstransport
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: ServersTransport is a specification for a ServersTransport resource.
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this representation
of an object. Servers should convert recognized schemas to the latest
internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: ServersTransportSpec options to configure communication between
Traefik and the servers.
properties:
certificatesSecrets:
description: Certificates for mTLS.
items:
type: string
type: array
disableHTTP2:
description: Disable HTTP/2 for connections with backend servers.
type: boolean
forwardingTimeouts:
description: Timeouts for requests forwarded to the backend servers.
properties:
dialTimeout:
anyOf:
- type: integer
- type: string
description: The amount of time to wait until a connection to
a backend server can be established. If zero, no timeout exists.
x-kubernetes-int-or-string: true
idleConnTimeout:
anyOf:
- type: integer
- type: string
description: The maximum period for which an idle HTTP keep-alive
connection will remain open before closing itself.
x-kubernetes-int-or-string: true
responseHeaderTimeout:
anyOf:
- type: integer
- type: string
description: The amount of time to wait for a server's response
headers after fully writing the request (including its body,
if any). If zero, no timeout exists.
x-kubernetes-int-or-string: true
type: object
insecureSkipVerify:
description: Disable SSL certificate verification.
type: boolean
maxIdleConnsPerHost:
description: If non-zero, controls the maximum idle (keep-alive) to
keep per-host. If zero, DefaultMaxIdleConnsPerHost is used.
type: integer
peerCertURI:
description: Defines the URI used to match against SAN URIs during
the server's certificate verification.
type: string
rootCAsSecrets:
description: Add cert file for self-signed certificate.
items:
type: string
type: array
serverName:
description: ServerName used to contact the server.
type: string
type: object
required:
- metadata
- spec
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []

View File

@ -0,0 +1,90 @@
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.4.1
creationTimestamp: null
name: tlsoptions.traefik.containo.us
spec:
group: traefik.containo.us
names:
kind: TLSOption
listKind: TLSOptionList
plural: tlsoptions
singular: tlsoption
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: TLSOption is a specification for a TLSOption resource.
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this representation
of an object. Servers should convert recognized schemas to the latest
internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: TLSOptionSpec configures TLS for an entry point.
properties:
alpnProtocols:
items:
type: string
type: array
cipherSuites:
items:
type: string
type: array
clientAuth:
description: ClientAuth defines the parameters of the client authentication
part of the TLS connection, if any.
properties:
clientAuthType:
description: ClientAuthType defines the client authentication
type to apply.
enum:
- NoClientCert
- RequestClientCert
- RequireAnyClientCert
- VerifyClientCertIfGiven
- RequireAndVerifyClientCert
type: string
secretNames:
description: SecretName is the name of the referenced Kubernetes
Secret to specify the certificate details.
items:
type: string
type: array
type: object
curvePreferences:
items:
type: string
type: array
maxVersion:
type: string
minVersion:
type: string
preferServerCipherSuites:
type: boolean
sniStrict:
type: boolean
type: object
required:
- metadata
- spec
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []

View File

@ -0,0 +1,62 @@
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.4.1
creationTimestamp: null
name: tlsstores.traefik.containo.us
spec:
group: traefik.containo.us
names:
kind: TLSStore
listKind: TLSStoreList
plural: tlsstores
singular: tlsstore
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: TLSStore is a specification for a TLSStore resource.
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this representation
of an object. Servers should convert recognized schemas to the latest
internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: TLSStoreSpec configures a TLSStore resource.
properties:
defaultCertificate:
description: DefaultCertificate holds a secret name for the TLSOption
resource.
properties:
secretName:
description: SecretName is the name of the referenced Kubernetes
Secret to specify the certificate details.
type: string
required:
- secretName
type: object
required:
- defaultCertificate
type: object
required:
- metadata
- spec
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []

View File

@ -0,0 +1,268 @@
apiVersion: apiextensions.k8s.io/v1
kind: CustomResourceDefinition
metadata:
annotations:
controller-gen.kubebuilder.io/version: v0.4.1
creationTimestamp: null
name: traefikservices.traefik.containo.us
spec:
group: traefik.containo.us
names:
kind: TraefikService
listKind: TraefikServiceList
plural: traefikservices
singular: traefikservice
scope: Namespaced
versions:
- name: v1alpha1
schema:
openAPIV3Schema:
description: TraefikService is the specification for a service (that an IngressRoute
refers to) that is usually not a terminal service (i.e. not a pod of servers),
as opposed to a Kubernetes Service. That is to say, it usually refers to
other (children) services, which themselves can be TraefikServices or Services.
properties:
apiVersion:
description: 'APIVersion defines the versioned schema of this representation
of an object. Servers should convert recognized schemas to the latest
internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources'
type: string
kind:
description: 'Kind is a string value representing the REST resource this
object represents. Servers may infer this from the endpoint the client
submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds'
type: string
metadata:
type: object
spec:
description: ServiceSpec defines whether a TraefikService is a load-balancer
of services or a mirroring service.
properties:
mirroring:
description: Mirroring defines a mirroring service, which is composed
of a main load-balancer, and a list of mirrors.
properties:
kind:
enum:
- Service
- TraefikService
type: string
maxBodySize:
format: int64
type: integer
mirrors:
items:
description: MirrorService defines one of the mirrors of a Mirroring
service.
properties:
kind:
enum:
- Service
- TraefikService
type: string
name:
description: Name is a reference to a Kubernetes Service
object (for a load-balancer of servers), or to a TraefikService
object (service load-balancer, mirroring, etc). The differentiation
between the two is specified in the Kind field.
type: string
namespace:
type: string
passHostHeader:
type: boolean
percent:
type: integer
port:
anyOf:
- type: integer
- type: string
x-kubernetes-int-or-string: true
responseForwarding:
description: ResponseForwarding holds configuration for
the forward of the response.
properties:
flushInterval:
type: string
type: object
scheme:
type: string
serversTransport:
type: string
sticky:
description: Sticky holds the sticky configuration.
properties:
cookie:
description: Cookie holds the sticky configuration based
on cookie.
properties:
httpOnly:
type: boolean
name:
type: string
sameSite:
type: string
secure:
type: boolean
type: object
type: object
strategy:
type: string
weight:
description: Weight should only be specified when Name references
a TraefikService object (and to be precise, one that embeds
a Weighted Round Robin).
type: integer
required:
- name
type: object
type: array
name:
description: Name is a reference to a Kubernetes Service object
(for a load-balancer of servers), or to a TraefikService object
(service load-balancer, mirroring, etc). The differentiation
between the two is specified in the Kind field.
type: string
namespace:
type: string
passHostHeader:
type: boolean
port:
anyOf:
- type: integer
- type: string
x-kubernetes-int-or-string: true
responseForwarding:
description: ResponseForwarding holds configuration for the forward
of the response.
properties:
flushInterval:
type: string
type: object
scheme:
type: string
serversTransport:
type: string
sticky:
description: Sticky holds the sticky configuration.
properties:
cookie:
description: Cookie holds the sticky configuration based on
cookie.
properties:
httpOnly:
type: boolean
name:
type: string
sameSite:
type: string
secure:
type: boolean
type: object
type: object
strategy:
type: string
weight:
description: Weight should only be specified when Name references
a TraefikService object (and to be precise, one that embeds
a Weighted Round Robin).
type: integer
required:
- name
type: object
weighted:
description: WeightedRoundRobin defines a load-balancer of services.
properties:
services:
items:
description: Service defines an upstream to proxy traffic.
properties:
kind:
enum:
- Service
- TraefikService
type: string
name:
description: Name is a reference to a Kubernetes Service
object (for a load-balancer of servers), or to a TraefikService
object (service load-balancer, mirroring, etc). The differentiation
between the two is specified in the Kind field.
type: string
namespace:
type: string
passHostHeader:
type: boolean
port:
anyOf:
- type: integer
- type: string
x-kubernetes-int-or-string: true
responseForwarding:
description: ResponseForwarding holds configuration for
the forward of the response.
properties:
flushInterval:
type: string
type: object
scheme:
type: string
serversTransport:
type: string
sticky:
description: Sticky holds the sticky configuration.
properties:
cookie:
description: Cookie holds the sticky configuration based
on cookie.
properties:
httpOnly:
type: boolean
name:
type: string
sameSite:
type: string
secure:
type: boolean
type: object
type: object
strategy:
type: string
weight:
description: Weight should only be specified when Name references
a TraefikService object (and to be precise, one that embeds
a Weighted Round Robin).
type: integer
required:
- name
type: object
type: array
sticky:
description: Sticky holds the sticky configuration.
properties:
cookie:
description: Cookie holds the sticky configuration based on
cookie.
properties:
httpOnly:
type: boolean
name:
type: string
sameSite:
type: string
secure:
type: boolean
type: object
type: object
type: object
type: object
required:
- metadata
- spec
type: object
served: true
storage: true
status:
acceptedNames:
kind: ""
plural: ""
conditions: []
storedVersions: []

View File

@ -0,0 +1,62 @@
{{/* vim: set filetype=mustache: */}}
{{/*
Expand the name of the chart.
*/}}
{{- define "traefik.name" -}}
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Create chart name and version as used by the chart label.
*/}}
{{- define "traefik.chart" -}}
{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{/*
Create a default fully qualified app name.
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
If release name contains chart name it will be used as a full name.
*/}}
{{- define "traefik.fullname" -}}
{{- if .Values.fullnameOverride -}}
{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" -}}
{{- else -}}
{{- $name := default .Chart.Name .Values.nameOverride -}}
{{- if contains $name .Release.Name -}}
{{- .Release.Name | trunc 63 | trimSuffix "-" -}}
{{- else -}}
{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{/*
The name of the service account to use
*/}}
{{- define "traefik.serviceAccountName" -}}
{{- default (include "traefik.fullname" .) .Values.serviceAccount.name -}}
{{- end -}}
{{/*
Construct the path for the providers.kubernetesingress.ingressendpoint.publishedservice.
By convention this will simply use the <namespace>/<service-name> to match the name of the
service generated.
Users can provide an override for an explicit service they want bound via `.Values.providers.kubernetesIngress.publishedService.pathOverride`
*/}}
{{- define "providers.kubernetesIngress.publishedServicePath" -}}
{{- $defServiceName := printf "%s/%s" .Release.Namespace (include "traefik.fullname" .) -}}
{{- $servicePath := default $defServiceName .Values.providers.kubernetesIngress.publishedService.pathOverride }}
{{- print $servicePath | trimSuffix "-" -}}
{{- end -}}
{{/*
Construct a comma-separated list of whitelisted namespaces
*/}}
{{- define "providers.kubernetesIngress.namespaces" -}}
{{- default .Release.Namespace (join "," .Values.providers.kubernetesIngress.namespaces) }}
{{- end -}}
{{- define "providers.kubernetesCRD.namespaces" -}}
{{- default .Release.Namespace (join "," .Values.providers.kubernetesCRD.namespaces) }}
{{- end -}}

View File

@ -0,0 +1,327 @@
{{- define "traefik.podTemplate" }}
metadata:
annotations:
{{- with .Values.deployment.podAnnotations }}
{{- toYaml . | nindent 8 }}
{{- end }}
{{- if .Values.metrics }}
{{- if .Values.metrics.prometheus }}
prometheus.io/scrape: "true"
prometheus.io/path: "/metrics"
prometheus.io/port: {{ quote (index .Values.ports .Values.metrics.prometheus.entryPoint).port }}
{{- end }}
{{- end }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- with .Values.deployment.podLabels }}
{{- toYaml . | nindent 8 }}
{{- end }}
spec:
{{- with .Values.deployment.imagePullSecrets }}
imagePullSecrets:
{{- toYaml . | nindent 8 }}
{{- end }}
serviceAccountName: {{ include "traefik.serviceAccountName" . }}
terminationGracePeriodSeconds: {{ default 60 .Values.deployment.terminationGracePeriodSeconds }}
hostNetwork: {{ .Values.hostNetwork }}
{{- with .Values.deployment.dnsPolicy }}
dnsPolicy: {{ . }}
{{- end }}
{{- with .Values.deployment.initContainers }}
initContainers:
{{- toYaml . | nindent 6 }}
{{- end }}
{{- if .Values.deployment.shareProcessNamespace }}
shareProcessNamespace: true
{{- end }}
containers:
- image: "{{ .Values.image.name }}:{{ default .Chart.AppVersion .Values.image.tag }}"
imagePullPolicy: {{ .Values.image.pullPolicy }}
name: {{ template "traefik.fullname" . }}
resources:
{{- with .Values.resources }}
{{- toYaml . | nindent 10 }}
{{- end }}
readinessProbe:
httpGet:
path: /ping
port: {{ default .Values.ports.traefik.port .Values.ports.traefik.healthchecksPort }}
failureThreshold: 1
initialDelaySeconds: 10
periodSeconds: 10
successThreshold: 1
timeoutSeconds: 2
livenessProbe:
httpGet:
path: /ping
port: {{ default .Values.ports.traefik.port .Values.ports.traefik.healthchecksPort }}
failureThreshold: 3
initialDelaySeconds: 10
periodSeconds: 10
successThreshold: 1
timeoutSeconds: 2
ports:
{{- range $name, $config := .Values.ports }}
{{- if $config }}
- name: {{ $name | quote }}
containerPort: {{ $config.port }}
{{- if $config.hostPort }}
hostPort: {{ $config.hostPort }}
{{- end }}
{{- if $config.hostIP }}
hostIP: {{ $config.hostIP }}
{{- end }}
protocol: {{ default "TCP" $config.protocol | quote }}
{{- end }}
{{- end }}
{{- with .Values.securityContext }}
securityContext:
{{- toYaml . | nindent 10 }}
{{- end }}
volumeMounts:
- name: {{ .Values.persistence.name }}
mountPath: {{ .Values.persistence.path }}
{{- if .Values.persistence.subPath }}
subPath: {{ .Values.persistence.subPath }}
{{- end }}
- name: tmp
mountPath: /tmp
{{- $root := . }}
{{- range .Values.volumes }}
- name: {{ tpl (.name) $root }}
mountPath: {{ .mountPath }}
readOnly: true
{{- end }}
{{- if .Values.experimental.plugins.enabled }}
- name: plugins
mountPath: "/plugins-storage"
{{- end }}
{{- if .Values.additionalVolumeMounts }}
{{- toYaml .Values.additionalVolumeMounts | nindent 10 }}
{{- end }}
args:
{{- with .Values.globalArguments }}
{{- range . }}
- {{ . | quote }}
{{- end }}
{{- end }}
{{- range $name, $config := .Values.ports }}
{{- if $config }}
- "--entrypoints.{{$name}}.address=:{{ $config.port }}/{{ default "tcp" $config.protocol | lower }}"
{{- end }}
{{- end }}
- "--api.dashboard=true"
- "--ping=true"
{{- if .Values.metrics }}
{{- if .Values.metrics.datadog }}
- "--metrics.datadog=true"
- "--metrics.datadog.address={{ .Values.metrics.datadog.address }}"
{{- end }}
{{- if .Values.metrics.influxdb }}
- "--metrics.influxdb=true"
- "--metrics.influxdb.address={{ .Values.metrics.influxdb.address }}"
- "--metrics.influxdb.protocol={{ .Values.metrics.influxdb.protocol }}"
{{- end }}
{{- if .Values.metrics.prometheus }}
- "--metrics.prometheus=true"
- "--metrics.prometheus.entrypoint={{ .Values.metrics.prometheus.entryPoint }}"
{{- if .Values.metrics.prometheus.addRoutersLabels }}
- "--metrics.prometheus.addRoutersLabels=true"
{{- end }}
{{- end }}
{{- if .Values.metrics.statsd }}
- "--metrics.statsd=true"
- "--metrics.statsd.address={{ .Values.metrics.statsd.address }}"
{{- end }}
{{- end }}
{{- if .Values.tracing }}
{{- if .Values.tracing.instana }}
- "--tracing.instana=true"
{{- end }}
{{- end }}
{{- if .Values.providers.kubernetesCRD.enabled }}
- "--providers.kubernetescrd"
{{- if .Values.providers.kubernetesCRD.labelSelector }}
- "--providers.kubernetescrd.labelSelector={{ .Values.providers.kubernetesCRD.labelSelector }}"
{{- end }}
{{- if .Values.providers.kubernetesCRD.ingressClass }}
- "--providers.kubernetescrd.ingressClass={{ .Values.providers.kubernetesCRD.ingressClass }}"
{{- end }}
{{- if .Values.providers.kubernetesCRD.allowCrossNamespace }}
- "--providers.kubernetescrd.allowCrossNamespace=true"
{{- end }}
{{- if .Values.providers.kubernetesCRD.allowExternalNameServices }}
- "--providers.kubernetescrd.allowExternalNameServices=true"
{{- end }}
{{- end }}
{{- if .Values.providers.kubernetesIngress.enabled }}
- "--providers.kubernetesingress"
{{- if .Values.providers.kubernetesIngress.allowExternalNameServices }}
- "--providers.kubernetesingress.allowExternalNameServices=true"
{{- end }}
{{- if and .Values.service.enabled .Values.providers.kubernetesIngress.publishedService.enabled }}
- "--providers.kubernetesingress.ingressendpoint.publishedservice={{ template "providers.kubernetesIngress.publishedServicePath" . }}"
{{- end }}
{{- if .Values.providers.kubernetesIngress.labelSelector }}
- "--providers.kubernetesingress.labelSelector={{ .Values.providers.kubernetesIngress.labelSelector }}"
{{- end }}
{{- end }}
{{- if .Values.experimental.kubernetesGateway.enabled }}
- "--providers.kubernetesgateway"
- "--experimental.kubernetesgateway"
{{- end }}
{{- if .Values.experimental.http3.enabled }}
- "--experimental.http3=true"
{{- end }}
{{- if and .Values.rbac.enabled .Values.rbac.namespaced }}
{{- if .Values.providers.kubernetesCRD.enabled }}
- "--providers.kubernetescrd.namespaces={{ template "providers.kubernetesCRD.namespaces" . }}"
{{- end }}
{{- if .Values.providers.kubernetesIngress.enabled }}
- "--providers.kubernetesingress.namespaces={{ template "providers.kubernetesIngress.namespaces" . }}"
{{- end }}
{{- end }}
{{- range $entrypoint, $config := $.Values.ports }}
{{- if $config.redirectTo }}
{{- $toPort := index $.Values.ports $config.redirectTo }}
- "--entrypoints.{{ $entrypoint }}.http.redirections.entryPoint.to=:{{ $toPort.exposedPort }}"
- "--entrypoints.{{ $entrypoint }}.http.redirections.entryPoint.scheme=https"
{{- end }}
{{- if $config.tls }}
{{- if $config.tls.enabled }}
- "--entrypoints.{{ $entrypoint }}.http.tls=true"
{{- if $config.tls.options }}
- "--entrypoints.{{ $entrypoint }}.http.tls.options={{ $config.tls.options }}"
{{- end }}
{{- if $config.tls.certResolver }}
- "--entrypoints.{{ $entrypoint }}.http.tls.certResolver={{ $config.tls.certResolver }}"
{{- end }}
{{- if $config.tls.domains }}
{{- range $index, $domain := $config.tls.domains }}
{{- if $domain.main }}
- "--entrypoints.{{ $entrypoint }}.http.tls.domains[{{ $index }}].main={{ $domain.main }}"
{{- end }}
{{- if $domain.sans }}
- "--entrypoints.{{ $entrypoint }}.http.tls.domains[{{ $index }}].sans={{ join "," $domain.sans }}"
{{- end }}
{{- end }}
{{- end }}
{{- if $config.http3 }}
{{- if semverCompare ">=2.6.0" (default $.Chart.AppVersion $.Values.image.tag)}}
- "--entrypoints.{{ $entrypoint }}.http3.advertisedPort={{ default $config.port $config.exposedPort }}"
{{- else }}
- "--entrypoints.{{ $entrypoint }}.enableHTTP3=true"
{{- end }}
{{- end }}
{{- end }}
{{- end }}
{{- end }}
{{- with .Values.logs }}
{{- if .general.format }}
- "--log.format={{ .general.format }}"
{{- end }}
{{- if ne .general.level "ERROR" }}
- "--log.level={{ .general.level | upper }}"
{{- end }}
{{- if .access.enabled }}
- "--accesslog=true"
{{- if .access.format }}
- "--accesslog.format={{ .access.format }}"
{{- end }}
{{- if .access.bufferingsize }}
- "--accesslog.bufferingsize={{ .access.bufferingsize }}"
{{- end }}
{{- if .access.filters }}
{{- if .access.filters.statuscodes }}
- "--accesslog.filters.statuscodes={{ .access.filters.statuscodes }}"
{{- end }}
{{- if .access.filters.retryattempts }}
- "--accesslog.filters.retryattempts"
{{- end }}
{{- if .access.filters.minduration }}
- "--accesslog.filters.minduration={{ .access.filters.minduration }}"
{{- end }}
{{- end }}
- "--accesslog.fields.defaultmode={{ .access.fields.general.defaultmode }}"
{{- range $fieldname, $fieldaction := .access.fields.general.names }}
- "--accesslog.fields.names.{{ $fieldname }}={{ $fieldaction }}"
{{- end }}
- "--accesslog.fields.headers.defaultmode={{ .access.fields.headers.defaultmode }}"
{{- range $fieldname, $fieldaction := .access.fields.headers.names }}
- "--accesslog.fields.headers.names.{{ $fieldname }}={{ $fieldaction }}"
{{- end }}
{{- end }}
{{- end }}
{{- if .Values.pilot.enabled }}
- "--pilot.token={{ .Values.pilot.token }}"
{{- end }}
{{- if hasKey .Values.pilot "dashboard" }}
- "--pilot.dashboard={{ .Values.pilot.dashboard }}"
{{- end }}
{{- with .Values.additionalArguments }}
{{- range . }}
- {{ . | quote }}
{{- end }}
{{- end }}
{{- with .Values.env }}
env:
{{- toYaml . | nindent 10 }}
{{- end }}
{{- with .Values.envFrom }}
envFrom:
{{- toYaml . | nindent 10 }}
{{- end }}
{{- if .Values.deployment.additionalContainers }}
{{- toYaml .Values.deployment.additionalContainers | nindent 6 }}
{{- end }}
volumes:
- name: {{ .Values.persistence.name }}
{{- if .Values.persistence.enabled }}
persistentVolumeClaim:
claimName: {{ default (include "traefik.fullname" .) .Values.persistence.existingClaim }}
{{- else }}
emptyDir: {}
{{- end }}
- name: tmp
emptyDir: {}
{{- $root := . }}
{{- range .Values.volumes }}
- name: {{ tpl (.name) $root }}
{{- if eq .type "secret" }}
secret:
secretName: {{ tpl (.name) $root }}
{{- else if eq .type "configMap" }}
configMap:
name: {{ tpl (.name) $root }}
{{- end }}
{{- end }}
{{- if .Values.deployment.additionalVolumes }}
{{- toYaml .Values.deployment.additionalVolumes | nindent 8 }}
{{- end }}
{{- if .Values.experimental.plugins.enabled }}
- name: plugins
emptyDir: {}
{{- end }}
{{- with .Values.affinity }}
affinity:
{{- toYaml . | nindent 8 }}
{{- end }}
{{- with .Values.tolerations }}
tolerations:
{{- toYaml . | nindent 8 }}
{{- end }}
{{- with .Values.nodeSelector }}
nodeSelector:
{{- toYaml . | nindent 8 }}
{{- end }}
{{- if .Values.priorityClassName }}
priorityClassName: {{ .Values.priorityClassName }}
{{- end }}
{{- with .Values.podSecurityContext }}
securityContext:
{{- toYaml . | nindent 8 }}
{{- end }}
{{ end -}}

View File

@ -0,0 +1,41 @@
{{- if and .Values.deployment.enabled (eq .Values.deployment.kind "DaemonSet") -}}
{{- with .Values.additionalArguments -}}
{{- range . -}}
{{- if contains ".acme." . -}}
{{- fail (printf "ACME functionality is not supported when running Traefik as a DaemonSet") -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{- if eq (default .Chart.AppVersion .Values.image.tag) "latest" }}
{{- fail "\n\n ERROR: latest tag should not be used" }}
{{- end }}
---
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- with .Values.deployment.labels }}
{{- toYaml . | nindent 4 }}
{{- end }}
annotations:
{{- with .Values.deployment.annotations }}
{{- toYaml . | nindent 4 }}
{{- end }}
spec:
selector:
matchLabels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
updateStrategy:
type: RollingUpdate
rollingUpdate:
maxUnavailable: {{ .Values.rollingUpdate.maxUnavailable }}
minReadySeconds: {{ .Values.deployment.minReadySeconds }}
template: {{ template "traefik.podTemplate" . }}
{{- end -}}

View File

@ -0,0 +1,28 @@
{{- if .Values.ingressRoute.dashboard.enabled -}}
apiVersion: traefik.containo.us/v1alpha1
kind: IngressRoute
metadata:
name: {{ template "traefik.fullname" . }}-dashboard
annotations:
helm.sh/hook: "post-install,post-upgrade"
{{- with .Values.ingressRoute.dashboard.annotations }}
{{- toYaml . | nindent 4 }}
{{- end }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- with .Values.ingressRoute.dashboard.labels }}
{{- toYaml . | nindent 4 }}
{{- end }}
spec:
entryPoints:
- traefik
routes:
- match: PathPrefix(`/dashboard`) || PathPrefix(`/api`)
kind: Rule
services:
- name: api@internal
kind: TraefikService
{{- end -}}

View File

@ -0,0 +1,48 @@
{{- if and .Values.deployment.enabled (eq .Values.deployment.kind "Deployment") -}}
{{- if gt (int .Values.deployment.replicas) 1 -}}
{{- with .Values.additionalArguments -}}
{{- range . -}}
{{- if contains ".acme." . -}}
{{- fail (printf "You can not enable acme if you set more than one traefik replica") -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{- end -}}
{{- if eq (default .Chart.AppVersion .Values.image.tag) "latest" }}
{{- fail "\n\n ERROR: latest tag should not be used" }}
{{- end }}
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- with .Values.deployment.labels }}
{{- toYaml . | nindent 4 }}
{{- end }}
annotations:
{{- with .Values.deployment.annotations }}
{{- toYaml . | nindent 4 }}
{{- end }}
spec:
{{- if not .Values.autoscaling.enabled }}
replicas: {{ default 1 .Values.deployment.replicas }}
{{- end }}
selector:
matchLabels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
strategy:
type: RollingUpdate
rollingUpdate:
{{- with .Values.rollingUpdate }}
{{- toYaml . | nindent 6 }}
{{- end }}
minReadySeconds: {{ .Values.deployment.minReadySeconds }}
template: {{ template "traefik.podTemplate" . }}
{{- end -}}

View File

@ -0,0 +1,25 @@
{{- if .Values.experimental.kubernetesGateway.enabled }}
---
apiVersion: gateway.networking.k8s.io/v1alpha2
kind: Gateway
metadata:
name: traefik-gateway
namespace: {{ default .Release.Namespace .Values.experimental.kubernetesGateway.namespace }}
spec:
gatewayClassName: traefik
listeners:
- name: web
port: {{ .Values.ports.web.port }}
protocol: HTTP
{{- if .Values.experimental.kubernetesGateway.certificate }}
- name: websecure
port: {{ $.Values.ports.websecure.port }}
protocol: HTTPS
tls:
certificateRefs:
- name: {{ .Values.experimental.kubernetesGateway.certificate.name }}
group: {{ .Values.experimental.kubernetesGateway.certificate.group }}
kind: {{ .Values.experimental.kubernetesGateway.certificate.kind }}
{{- end }}
{{- end }}

View File

@ -0,0 +1,9 @@
{{- if .Values.experimental.kubernetesGateway.enabled }}
---
apiVersion: gateway.networking.k8s.io/v1alpha2
kind: GatewayClass
metadata:
name: traefik
spec:
controllerName: traefik.io/gateway-controller
{{- end }}

View File

@ -0,0 +1,20 @@
{{- if .Values.autoscaling.enabled }}
apiVersion: autoscaling/v2beta1
kind: HorizontalPodAutoscaler
metadata:
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
spec:
scaleTargetRef:
apiVersion: apps/v1
kind: Deployment
name: {{ template "traefik.fullname" . }}
minReplicas: {{ .Values.autoscaling.minReplicas }}
maxReplicas: {{ .Values.autoscaling.maxReplicas }}
metrics:
{{ toYaml .Values.autoscaling.metrics | indent 4 }}
{{- end }}

View File

@ -0,0 +1,23 @@
{{- if and .Values.ingressClass.enabled (semverCompare ">=2.3.0" (default .Chart.AppVersion .Values.image.tag)) -}}
{{- if .Capabilities.APIVersions.Has "networking.k8s.io/v1/IngressClass" }}
apiVersion: networking.k8s.io/v1
{{- else if .Capabilities.APIVersions.Has "networking.k8s.io/v1beta1/IngressClass" }}
apiVersion: networking.k8s.io/v1beta1
{{- else if or (eq .Values.ingressClass.fallbackApiVersion "v1beta1") (eq .Values.ingressClass.fallbackApiVersion "v1") }}
apiVersion: {{ printf "networking.k8s.io/%s" .Values.ingressClass.fallbackApiVersion }}
{{- else }}
{{- fail "\n\n ERROR: You must have at least networking.k8s.io/v1beta1 to use ingressClass" }}
{{- end }}
kind: IngressClass
metadata:
annotations:
ingressclass.kubernetes.io/is-default-class: {{ .Values.ingressClass.isDefaultClass | quote }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
name: {{ template "traefik.fullname" . }}
spec:
controller: traefik.io/ingress-controller
{{- end }}

View File

@ -0,0 +1,22 @@
{{- if .Values.podDisruptionBudget.enabled -}}
apiVersion: policy/v1beta1
kind: PodDisruptionBudget
metadata:
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
spec:
selector:
matchLabels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- if .Values.podDisruptionBudget.minAvailable }}
minAvailable: {{ .Values.podDisruptionBudget.minAvailable }}
{{- end }}
{{- if .Values.podDisruptionBudget.maxUnavailable }}
maxUnavailable: {{ .Values.podDisruptionBudget.maxUnavailable }}
{{- end }}
{{- end -}}

View File

@ -0,0 +1,26 @@
{{- if and .Values.persistence.enabled (not .Values.persistence.existingClaim) -}}
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: {{ template "traefik.fullname" . }}
annotations:
{{- with .Values.persistence.annotations }}
{{ toYaml . | nindent 4 }}
{{- end }}
helm.sh/resource-policy: keep
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
spec:
accessModes:
- {{ .Values.persistence.accessMode | quote }}
resources:
requests:
storage: {{ .Values.persistence.size | quote }}
{{- if .Values.persistence.storageClass }}
storageClassName: {{ .Values.persistence.storageClass | quote }}
{{- end }}
{{- end -}}

View File

@ -0,0 +1,96 @@
{{- if and .Values.rbac.enabled (not .Values.rbac.namespaced) -}}
kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
rules:
- apiGroups:
- ""
resources:
- services
- endpoints
- secrets
verbs:
- get
- list
- watch
- apiGroups:
- extensions
- networking.k8s.io
resources:
- ingresses
- ingressclasses
verbs:
- get
- list
- watch
- apiGroups:
- extensions
- networking.k8s.io
resources:
- ingresses/status
verbs:
- update
- apiGroups:
- traefik.containo.us
resources:
- ingressroutes
- ingressroutetcps
- ingressrouteudps
- middlewares
- middlewaretcps
- tlsoptions
- tlsstores
- traefikservices
- serverstransports
verbs:
- get
- list
- watch
{{- if .Values.podSecurityPolicy.enabled }}
- apiGroups:
- policy
resourceNames:
- {{ template "traefik.fullname" . }}
resources:
- podsecuritypolicies
verbs:
- use
{{- end -}}
{{- if .Values.experimental.kubernetesGateway.enabled }}
- apiGroups:
- ""
resources:
- namespaces
verbs:
- list
- watch
- apiGroups:
- gateway.networking.k8s.io
resources:
- gatewayclasses
- gateways
- httproutes
- tcproutes
- tlsroutes
verbs:
- get
- list
- watch
- apiGroups:
- gateway.networking.k8s.io
resources:
- gatewayclasses/status
- gateways/status
- httproutes/status
- tcproutes/status
- tlsroutes/status
verbs:
- update
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,19 @@
{{- if and .Values.rbac.enabled (not .Values.rbac.namespaced) }}
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: {{ template "traefik.fullname" . }}
subjects:
- kind: ServiceAccount
name: {{ include "traefik.serviceAccountName" . }}
namespace: {{ .Release.Namespace }}
{{- end -}}

View File

@ -0,0 +1,68 @@
{{- if .Values.podSecurityPolicy.enabled }}
---
apiVersion: policy/v1beta1
kind: PodSecurityPolicy
metadata:
annotations:
seccomp.security.alpha.kubernetes.io/allowedProfileNames: runtime/default
seccomp.security.alpha.kubernetes.io/defaultProfileName: runtime/default
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
spec:
privileged: false
allowPrivilegeEscalation: false
requiredDropCapabilities:
- ALL
{{- if not .Values.securityContext.runAsNonRoot }}
allowedCapabilities:
- NET_BIND_SERVICE
{{- end }}
hostNetwork: {{ .Values.hostNetwork }}
hostIPC: false
hostPID: false
fsGroup:
{{- if .Values.securityContext.runAsNonRoot }}
ranges:
- max: 65535
min: 1
rule: MustRunAs
{{- else }}
rule: RunAsAny
{{- end }}
{{- if .Values.hostNetwork }}
hostPorts:
- max: 65535
min: 1
{{- end }}
readOnlyRootFilesystem: true
runAsUser:
{{- if .Values.securityContext.runAsNonRoot }}
rule: MustRunAsNonRoot
{{- else }}
rule: RunAsAny
{{- end }}
seLinux:
rule: RunAsAny
supplementalGroups:
{{- if .Values.securityContext.runAsNonRoot }}
ranges:
- max: 65535
min: 1
rule: MustRunAs
{{- else }}
rule: RunAsAny
{{- end }}
volumes:
- configMap
- downwardAPI
- secret
- emptyDir
- projected
{{- if .Values.persistence.enabled }}
- persistentVolumeClaim
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,64 @@
{{- if and .Values.rbac.enabled .Values.rbac.namespaced }}
kind: Role
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
rules:
- apiGroups:
- ""
resources:
- services
- endpoints
- secrets
verbs:
- get
- list
- watch
- apiGroups:
- extensions
- networking.k8s.io
resources:
- ingresses
verbs:
- get
- list
- watch
- apiGroups:
- extensions
- networking.k8s.io
resources:
- ingresses/status
verbs:
- update
- apiGroups:
- traefik.containo.us
resources:
- ingressroutes
- ingressroutetcps
- ingressrouteudps
- middlewares
- middlewaretcps
- tlsoptions
- tlsstores
- traefikservices
- serverstransports
verbs:
- get
- list
- watch
{{- if .Values.podSecurityPolicy.enabled }}
- apiGroups:
- extensions
resourceNames:
- {{ template "traefik.fullname" . }}
resources:
- podsecuritypolicies
verbs:
- use
{{- end -}}
{{- end -}}

View File

@ -0,0 +1,19 @@
{{- if and .Values.rbac.enabled .Values.rbac.namespaced }}
kind: RoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: {{ template "traefik.fullname" . }}
subjects:
- kind: ServiceAccount
name: {{ include "traefik.serviceAccountName" . }}
namespace: {{ .Release.Namespace }}
{{- end -}}

View File

@ -0,0 +1,15 @@
{{- if not .Values.serviceAccount.name -}}
kind: ServiceAccount
apiVersion: v1
metadata:
name: {{ include "traefik.serviceAccountName" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
annotations:
{{- with .Values.serviceAccountAnnotations }}
{{- toYaml . | nindent 4 }}
{{- end }}
{{- end -}}

View File

@ -0,0 +1,135 @@
{{- if .Values.service.enabled -}}
{{ $tcpPorts := dict }}
{{ $udpPorts := dict }}
{{- range $name, $config := .Values.ports }}
{{- if or $config.http3 (eq (toString $config.protocol) "UDP") }}
{{ $_ := set $udpPorts $name $config }}
{{- end }}
{{- if eq (toString (default "TCP" $config.protocol)) "TCP" }}
{{ $_ := set $tcpPorts $name $config }}
{{- end }}
{{- end }}
apiVersion: v1
kind: List
metadata:
name: {{ template "traefik.fullname" . }}
items:
{{- if $tcpPorts }}
- apiVersion: v1
kind: Service
metadata:
name: {{ template "traefik.fullname" . }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- with .Values.service.labels }}
{{- toYaml . | nindent 8 }}
{{- end }}
annotations:
{{- with (merge .Values.service.annotationsTCP .Values.service.annotations) }}
{{- toYaml . | nindent 8 }}
{{- end }}
spec:
{{- $type := default "LoadBalancer" .Values.service.type }}
type: {{ $type }}
{{- with .Values.service.spec }}
{{- toYaml . | nindent 6 }}
{{- end }}
selector:
app.kubernetes.io/name: {{ template "traefik.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
ports:
{{- range $name, $config := $tcpPorts }}
{{- if $config.expose }}
- port: {{ default $config.port $config.exposedPort }}
name: {{ $name }}
targetPort: {{ $name | quote }}
protocol: TCP
{{- if $config.nodePort }}
nodePort: {{ $config.nodePort }}
{{- end }}
{{- end }}
{{- end }}
{{- if eq $type "LoadBalancer" }}
{{- with .Values.service.loadBalancerSourceRanges }}
loadBalancerSourceRanges:
{{- toYaml . | nindent 6 }}
{{- end -}}
{{- end -}}
{{- with .Values.service.externalIPs }}
externalIPs:
{{- toYaml . | nindent 6 }}
{{- end -}}
{{- if .Values.service.ipFamilyPolicy }}
ipFamilyPolicy: {{ .Values.service.ipFamilyPolicy }}
{{- end }}
{{- with .Values.service.ipFamilies }}
ipFamilies:
{{- toYaml . | nindent 6 }}
{{- end -}}
{{- end }}
{{- if $udpPorts }}
- apiVersion: v1
kind: Service
metadata:
name: {{ template "traefik.fullname" . }}-udp
labels:
app.kubernetes.io/name: {{ template "traefik.name" . }}
helm.sh/chart: {{ template "traefik.chart" . }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- with .Values.service.labels }}
{{- toYaml . | nindent 8 }}
{{- end }}
annotations:
{{- with (merge .Values.service.annotationsUDP .Values.service.annotations) }}
{{- toYaml . | nindent 8 }}
{{- end }}
spec:
{{- $type := default "LoadBalancer" .Values.service.type }}
type: {{ $type }}
{{- with .Values.service.spec }}
{{- toYaml . | nindent 6 }}
{{- end }}
selector:
app.kubernetes.io/name: {{ template "traefik.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
ports:
{{- range $name, $config := $udpPorts }}
{{- if $config.expose }}
- port: {{ default $config.port $config.exposedPort }}
name: {{ $name }}
# Due to https://github.com/kubernetes/kubernetes/issues/58477 it is not possible
# to define the HTTP/3 UDP port as a containerPort. TCP and UDP containerPort will have
# the same value which will break the chart upgrade.
targetPort: {{ if $config.http3 }}{{ $config.port }}{{ else }}{{ $name | quote }}{{ end }}
protocol: UDP
{{- if $config.nodePort }}
nodePort: {{ $config.nodePort }}
{{- end }}
{{- end }}
{{- end }}
{{- if eq $type "LoadBalancer" }}
{{- with .Values.service.loadBalancerSourceRanges }}
loadBalancerSourceRanges:
{{- toYaml . | nindent 6 }}
{{- end -}}
{{- end -}}
{{- with .Values.service.externalIPs }}
externalIPs:
{{- toYaml . | nindent 6 }}
{{- end -}}
{{- if .Values.service.ipFamilyPolicy }}
ipFamilyPolicy: {{ .Values.service.ipFamilyPolicy }}
{{- end }}
{{- with .Values.service.ipFamilies }}
ipFamilies:
{{- toYaml . | nindent 6 }}
{{- end -}}
{{- end }}
{{- end -}}

View File

@ -0,0 +1,14 @@
{{- range $name, $config := .Values.tlsOptions }}
apiVersion: traefik.containo.us/v1alpha1
kind: TLSOption
metadata:
name: {{ $name }}
labels:
app.kubernetes.io/name: {{ template "traefik.name" $ }}
helm.sh/chart: {{ template "traefik.chart" $ }}
app.kubernetes.io/managed-by: {{ $.Release.Service }}
app.kubernetes.io/instance: {{ $.Release.Name }}
spec:
{{- toYaml $config | nindent 2 }}
---
{{- end -}}

View File

@ -0,0 +1,480 @@
# Default values for Traefik
image:
name: traefik
# defaults to appVersion
tag: ""
pullPolicy: IfNotPresent
#
# Configure the deployment
#
deployment:
enabled: true
# Can be either Deployment or DaemonSet
kind: Deployment
# Number of pods of the deployment (only applies when kind == Deployment)
replicas: 1
# Amount of time (in seconds) before Kubernetes will send the SIGKILL signal if Traefik does not shut down
terminationGracePeriodSeconds: 60
# The minimum number of seconds Traefik needs to be up and running before the DaemonSet/Deployment controller considers it available
minReadySeconds: 0
# Additional deployment annotations (e.g. for jaeger-operator sidecar injection)
annotations: {}
# Additional deployment labels (e.g. for filtering deployment by custom labels)
labels: {}
# Additional pod annotations (e.g. for mesh injection or prometheus scraping)
podAnnotations: {}
# Additional Pod labels (e.g. for filtering Pod by custom labels)
podLabels: {}
# Additional containers (e.g. for metric offloading sidecars)
additionalContainers: []
# https://docs.datadoghq.com/developers/dogstatsd/unix_socket/?tab=host
# - name: socat-proxy
# image: alpine/socat:1.0.5
# args: ["-s", "-u", "udp-recv:8125", "unix-sendto:/socket/socket"]
# volumeMounts:
# - name: dsdsocket
# mountPath: /socket
# Additional volumes available for use with initContainers and additionalContainers
additionalVolumes: []
# - name: dsdsocket
# hostPath:
# path: /var/run/statsd-exporter
# Additional initContainers (e.g. for setting file permission as shown below)
initContainers: []
# The "volume-permissions" init container is required if you run into permission issues.
# Related issue: https://github.com/traefik/traefik/issues/6972
# - name: volume-permissions
# image: busybox:1.31.1
# command: ["sh", "-c", "chmod -Rv 600 /data/*"]
# volumeMounts:
# - name: data
# mountPath: /data
# Use process namespace sharing
shareProcessNamespace: false
# Custom pod DNS policy. Apply if `hostNetwork: true`
# dnsPolicy: ClusterFirstWithHostNet
# Additional imagePullSecrets
imagePullSecrets: []
# - name: myRegistryKeySecretName
# Pod disruption budget
podDisruptionBudget:
enabled: false
# maxUnavailable: 1
# maxUnavailable: 33%
# minAvailable: 0
# minAvailable: 25%
# Use ingressClass. Ignored if Traefik version < 2.3 / kubernetes < 1.18.x
ingressClass:
# true is not unit-testable yet, pending https://github.com/rancher/helm-unittest/pull/12
enabled: false
isDefaultClass: false
# Use to force a networking.k8s.io API Version for certain CI/CD applications. E.g. "v1beta1"
fallbackApiVersion: ""
# Activate Pilot integration
pilot:
enabled: false
token: ""
# Toggle Pilot Dashboard
# dashboard: false
# Enable experimental features
experimental:
http3:
enabled: false
plugins:
enabled: false
kubernetesGateway:
enabled: false
# certificate:
# group: "core"
# kind: "Secret"
# name: "mysecret"
# By default, Gateway would be created to the Namespace you are deploying Traefik to.
# You may create that Gateway in another namespace, setting its name below:
# namespace: default
# Create an IngressRoute for the dashboard
ingressRoute:
dashboard:
enabled: true
# Additional ingressRoute annotations (e.g. for kubernetes.io/ingress.class)
annotations: {}
# Additional ingressRoute labels (e.g. for filtering IngressRoute by custom labels)
labels: {}
rollingUpdate:
maxUnavailable: 1
maxSurge: 1
#
# Configure providers
#
providers:
kubernetesCRD:
enabled: true
allowCrossNamespace: false
allowExternalNameServices: false
# ingressClass: traefik-internal
# labelSelector: environment=production,method=traefik
namespaces: []
# - "default"
kubernetesIngress:
enabled: true
allowExternalNameServices: false
# labelSelector: environment=production,method=traefik
namespaces: []
# - "default"
# IP used for Kubernetes Ingress endpoints
publishedService:
enabled: false
# Published Kubernetes Service to copy status from. Format: namespace/servicename
# By default this Traefik service
# pathOverride: ""
#
# Add volumes to the traefik pod. The volume name will be passed to tpl.
# This can be used to mount a cert pair or a configmap that holds a config.toml file.
# After the volume has been mounted, add the configs into traefik by using the `additionalArguments` list below, eg:
# additionalArguments:
# - "--providers.file.filename=/config/dynamic.toml"
# - "--ping"
# - "--ping.entrypoint=web"
volumes: []
# - name: public-cert
# mountPath: "/certs"
# type: secret
# - name: '{{ printf "%s-configs" .Release.Name }}'
# mountPath: "/config"
# type: configMap
# Additional volumeMounts to add to the Traefik container
additionalVolumeMounts: []
# For instance when using a logshipper for access logs
# - name: traefik-logs
# mountPath: /var/log/traefik
# Logs
# https://docs.traefik.io/observability/logs/
logs:
# Traefik logs concern everything that happens to Traefik itself (startup, configuration, events, shutdown, and so on).
general:
# By default, the logs use a text format (common), but you can
# also ask for the json format in the format option
# format: json
# By default, the level is set to ERROR. Alternative logging levels are DEBUG, PANIC, FATAL, ERROR, WARN, and INFO.
level: ERROR
access:
# To enable access logs
enabled: false
# By default, logs are written using the Common Log Format (CLF).
# To write logs in JSON, use json in the format option.
# If the given format is unsupported, the default (CLF) is used instead.
# format: json
# To write the logs in an asynchronous fashion, specify a bufferingSize option.
# This option represents the number of log lines Traefik will keep in memory before writing
# them to the selected output. In some cases, this option can greatly help performances.
# bufferingSize: 100
# Filtering https://docs.traefik.io/observability/access-logs/#filtering
filters: {}
# statuscodes: "200,300-302"
# retryattempts: true
# minduration: 10ms
# Fields
# https://docs.traefik.io/observability/access-logs/#limiting-the-fieldsincluding-headers
fields:
general:
defaultmode: keep
names: {}
# Examples:
# ClientUsername: drop
headers:
defaultmode: drop
names: {}
# Examples:
# User-Agent: redact
# Authorization: drop
# Content-Type: keep
metrics:
# datadog:
# address: 127.0.0.1:8125
# influxdb:
# address: localhost:8089
# protocol: udp
prometheus:
entryPoint: metrics
# addRoutersLabels: true
# statsd:
# address: localhost:8125
tracing: {}
# instana:
# enabled: true
globalArguments:
- "--global.checknewversion"
- "--global.sendanonymoususage"
#
# Configure Traefik static configuration
# Additional arguments to be passed at Traefik's binary
# All available options available on https://docs.traefik.io/reference/static-configuration/cli/
## Use curly braces to pass values: `helm install --set="additionalArguments={--providers.kubernetesingress.ingressclass=traefik-internal,--log.level=DEBUG}"`
additionalArguments: []
# - "--providers.kubernetesingress.ingressclass=traefik-internal"
# - "--log.level=DEBUG"
# Environment variables to be passed to Traefik's binary
env: []
# - name: SOME_VAR
# value: some-var-value
# - name: SOME_VAR_FROM_CONFIG_MAP
# valueFrom:
# configMapRef:
# name: configmap-name
# key: config-key
# - name: SOME_SECRET
# valueFrom:
# secretKeyRef:
# name: secret-name
# key: secret-key
envFrom: []
# - configMapRef:
# name: config-map-name
# - secretRef:
# name: secret-name
# Configure ports
ports:
# The name of this one can't be changed as it is used for the readiness and
# liveness probes, but you can adjust its config to your liking
traefik:
port: 9000
# Use hostPort if set.
# hostPort: 9000
#
# Use hostIP if set. If not set, Kubernetes will default to 0.0.0.0, which
# means it's listening on all your interfaces and all your IPs. You may want
# to set this value if you need traefik to listen on specific interface
# only.
# hostIP: 192.168.100.10
# Override the liveness/readiness port. This is useful to integrate traefik
# with an external Load Balancer that performs healthchecks.
# healthchecksPort: 9000
# Defines whether the port is exposed if service.type is LoadBalancer or
# NodePort.
#
# You SHOULD NOT expose the traefik port on production deployments.
# If you want to access it from outside of your cluster,
# use `kubectl port-forward` or create a secure ingress
expose: false
# The exposed port for this service
exposedPort: 9000
# The port protocol (TCP/UDP)
protocol: TCP
web:
port: 8000
# hostPort: 8000
expose: true
exposedPort: 80
# The port protocol (TCP/UDP)
protocol: TCP
# Use nodeport if set. This is useful if you have configured Traefik in a
# LoadBalancer
# nodePort: 32080
# Port Redirections
# Added in 2.2, you can make permanent redirects via entrypoints.
# https://docs.traefik.io/routing/entrypoints/#redirection
# redirectTo: websecure
websecure:
port: 8443
# hostPort: 8443
expose: true
exposedPort: 443
# The port protocol (TCP/UDP)
protocol: TCP
# nodePort: 32443
# Enable HTTP/3.
# Requires enabling experimental http3 feature and tls.
# Note that you cannot have a UDP entrypoint with the same port.
# http3: true
# Set TLS at the entrypoint
# https://doc.traefik.io/traefik/routing/entrypoints/#tls
tls:
enabled: false
# this is the name of a TLSOption definition
options: ""
certResolver: ""
domains: []
# - main: example.com
# sans:
# - foo.example.com
# - bar.example.com
metrics:
port: 9100
# hostPort: 9100
# Defines whether the port is exposed if service.type is LoadBalancer or
# NodePort.
#
# You may not want to expose the metrics port on production deployments.
# If you want to access it from outside of your cluster,
# use `kubectl port-forward` or create a secure ingress
expose: false
# The exposed port for this service
exposedPort: 9100
# The port protocol (TCP/UDP)
protocol: TCP
# TLS Options are created as TLSOption CRDs
# https://doc.traefik.io/traefik/https/tls/#tls-options
# Example:
# tlsOptions:
# default:
# sniStrict: true
# preferServerCipherSuites: true
# foobar:
# curvePreferences:
# - CurveP521
# - CurveP384
tlsOptions: {}
# Options for the main traefik service, where the entrypoints traffic comes
# from.
service:
enabled: true
type: LoadBalancer
# Additional annotations applied to both TCP and UDP services (e.g. for cloud provider specific config)
annotations: {}
# Additional annotations for TCP service only
annotationsTCP: {}
# Additional annotations for UDP service only
annotationsUDP: {}
# Additional service labels (e.g. for filtering Service by custom labels)
labels: {}
# Additional entries here will be added to the service spec.
# Cannot contain type, selector or ports entries.
spec: {}
# externalTrafficPolicy: Cluster
# loadBalancerIP: "1.2.3.4"
# clusterIP: "2.3.4.5"
loadBalancerSourceRanges: []
# - 192.168.0.1/32
# - 172.16.0.0/16
externalIPs: []
# - 1.2.3.4
# One of SingleStack, PreferDualStack, or RequireDualStack.
# ipFamilyPolicy: SingleStack
# List of IP families (e.g. IPv4 and/or IPv6).
# ref: https://kubernetes.io/docs/concepts/services-networking/dual-stack/#services
# ipFamilies:
# - IPv4
# - IPv6
## Create HorizontalPodAutoscaler object.
##
autoscaling:
enabled: false
# minReplicas: 1
# maxReplicas: 10
# metrics:
# - type: Resource
# resource:
# name: cpu
# targetAverageUtilization: 60
# - type: Resource
# resource:
# name: memory
# targetAverageUtilization: 60
# Enable persistence using Persistent Volume Claims
# ref: http://kubernetes.io/docs/user-guide/persistent-volumes/
# After the pvc has been mounted, add the configs into traefik by using the `additionalArguments` list below, eg:
# additionalArguments:
# - "--certificatesresolvers.le.acme.storage=/data/acme.json"
# It will persist TLS certificates.
persistence:
enabled: false
name: data
# existingClaim: ""
accessMode: ReadWriteOnce
size: 128Mi
# storageClass: ""
path: /data
annotations: {}
# subPath: "" # only mount a subpath of the Volume into the pod
# If hostNetwork is true, runs traefik in the host network namespace
# To prevent unschedulabel pods due to port collisions, if hostNetwork=true
# and replicas>1, a pod anti-affinity is recommended and will be set if the
# affinity is left as default.
hostNetwork: false
# Whether Role Based Access Control objects like roles and rolebindings should be created
rbac:
enabled: true
# If set to false, installs ClusterRole and ClusterRoleBinding so Traefik can be used across namespaces.
# If set to true, installs namespace-specific Role and RoleBinding and requires provider configuration be set to that same namespace
namespaced: false
# Enable to create a PodSecurityPolicy and assign it to the Service Account via RoleBinding or ClusterRoleBinding
podSecurityPolicy:
enabled: false
# The service account the pods will use to interact with the Kubernetes API
serviceAccount:
# If set, an existing service account is used
# If not set, a service account is created automatically using the fullname template
name: ""
# Additional serviceAccount annotations (e.g. for oidc authentication)
serviceAccountAnnotations: {}
resources: {}
# requests:
# cpu: "100m"
# memory: "50Mi"
# limits:
# cpu: "300m"
# memory: "150Mi"
affinity: {}
# # This example pod anti-affinity forces the scheduler to put traefik pods
# # on nodes where no other traefik pods are scheduled.
# # It should be used when hostNetwork: true to prevent port conflicts
# podAntiAffinity:
# requiredDuringSchedulingIgnoredDuringExecution:
# - labelSelector:
# matchExpressions:
# - key: app.kubernetes.io/name
# operator: In
# values:
# - {{ template "traefik.name" . }}
# topologyKey: kubernetes.io/hostname
nodeSelector: {}
tolerations: []
# Pods can have priority.
# Priority indicates the importance of a Pod relative to other Pods.
priorityClassName: ""
# Set the container security context
# To run the container with ports below 1024 this will need to be adjust to run as root
securityContext:
capabilities:
drop: [ALL]
readOnlyRootFilesystem: true
runAsGroup: 65532
runAsNonRoot: true
runAsUser: 65532
podSecurityContext:
fsGroup: 65532

View File

@ -0,0 +1,23 @@
# Patterns to ignore when building packages.
# This supports shell glob matching, relative path matching, and
# negation (prefixed with !). Only one pattern per line.
.DS_Store
# Common VCS dirs
.git/
.gitignore
.bzr/
.bzrignore
.hg/
.hgignore
.svn/
# Common backup files
*.swp
*.bak
*.tmp
*.orig
*~
# Various IDEs
.project
.idea/
*.tmproj
.vscode/

View File

@ -0,0 +1,12 @@
annotations:
catalog.cattle.io/certified: partner
catalog.cattle.io/display-name: OpenZiti Service-Hosting
catalog.cattle.io/release-name: ziti-host
apiVersion: v2
appVersion: 0.24.12
description: Host NetFoundry services with a single replica pod
icon: https://partner-charts.rancher.io/assets/logos/ziti-host.png
kubeVersion: '>= 1.20'
name: ziti-host
type: application
version: 1.5.1

View File

@ -0,0 +1,7 @@
# OpenZiti Service-Hosting Deployment for Kubernetes
[OpenZiti](https://ziti.dev) makes it easy to embed Zero Trust, programmable networking directly into your app. With Ziti you can have Zero Trust, high performance networking on any Internet connection, without VPNs!
You will need an enrollment token from your Ziti network to install this chart. Then you may control access to your Rancher cluster workloads by assigning services to the enrolled edge identity in your Ziti network dashboard.
This chart installs a Ziti edge tunneler in a namespace of your cluster. Like all edge identities in a Ziti network, this tunneler too will need an identity. You will need to create the identity and paste its enrollment token when you install this chart. If you haven't already created your network you can do so for free with [the self-hosted quickstarts](https://openziti.github.io/) or take [the managed route with NetFoundry Teams](https://netfoundry.io/) (free tier).

View File

@ -0,0 +1,7 @@
questions:
- variable: enrollmentToken
required: true
type: string
label: Ziti identity enrollment token
description: Paste the one-time enrollment token which is a JSON web token from the controller
group: "Global Settings"

View File

@ -0,0 +1,2 @@
1. This deployment does not provide an ingress / server port, only egress from the pod to any `serverEgress` destinations you configure in a NetFoundry network e.g. https://kubernetes.default.svc:443:
export POD_NAME=$(kubectl get pods --namespace {{ .Release.Namespace }} -l "app.kubernetes.io/name={{ include "ziti-host.name" . }},app.kubernetes.io/instance={{ .Release.Name }}" -o jsonpath="{.items[0].metadata.name}")

View File

@ -0,0 +1,63 @@
{{/*
Expand the name of the chart.
*/}}
{{- define "ziti-host.name" -}}
{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }}
{{- end }}
{{/*
Create a default fully qualified app name.
We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec).
If release name contains chart name it will be used as a full name.
*/}}
{{- define "ziti-host.fullname" -}}
{{- if .Values.fullnameOverride }}
{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }}
{{- else }}
{{- $name := default .Chart.Name .Values.nameOverride }}
{{- if contains $name .Release.Name }}
{{- .Release.Name | trunc 63 | trimSuffix "-" }}
{{- else }}
{{- printf "%s-%s" .Release.Name $name | trunc 63 | trimSuffix "-" }}
{{- end }}
{{- end }}
{{- end }}
{{/*
Create chart name and version as used by the chart label.
*/}}
{{- define "ziti-host.chart" -}}
{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }}
{{- end }}
{{/*
Common labels
*/}}
{{- define "ziti-host.labels" -}}
helm.sh/chart: {{ include "ziti-host.chart" . }}
{{ include "ziti-host.selectorLabels" . }}
{{- if .Chart.AppVersion }}
app.kubernetes.io/version: {{ .Chart.AppVersion | quote }}
{{- end }}
app.kubernetes.io/managed-by: {{ .Release.Service }}
{{- end }}
{{/*
Selector labels
*/}}
{{- define "ziti-host.selectorLabels" -}}
app.kubernetes.io/name: {{ include "ziti-host.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
{{- end }}
{{/*
Create the name of the service account to use
*/}}
{{- define "ziti-host.serviceAccountName" -}}
{{- if .Values.serviceAccount.create }}
{{- default (include "ziti-host.fullname" .) .Values.serviceAccount.name }}
{{- else }}
{{- default "default" .Values.serviceAccount.name }}
{{- end }}
{{- end }}

Some files were not shown because too many files have changed in this diff Show More