315 lines
		
	
	
		
			9.6 KiB
		
	
	
	
		
			Markdown
		
	
	
	
			
		
		
	
	
			315 lines
		
	
	
		
			9.6 KiB
		
	
	
	
		
			Markdown
		
	
	
	
| ## Advanced Features
 | |
| 
 | |
| - [Import Configuration Parameters into Helmfile](#import-configuration-parameters-into-helmfile)
 | |
| - [Deploy Kustomization with Helmfile](#deploy-kustomizations-with-helmfile)
 | |
| - [Adhoc Kustomization of Helm Charts](#adhoc-kustomization-of-helm-charts)
 | |
| - [Adding dependencies without forking the chart](#adding-dependencies-without-forking-the-chart)
 | |
| 
 | |
| ### Import Configuration Parameters into Helmfile
 | |
| 
 | |
| Helmfile integrates [vals]() to import configuration parameters from following backends:
 | |
| 
 | |
| - AWS SSM Parameter Store
 | |
| - AWS SecretsManager
 | |
| - Vault
 | |
| - SOPS
 | |
| 
 | |
| See [Vals "Suported Backends"](https://github.com/variantdev/vals#suported-backends) for the full list of available backends.
 | |
| 
 | |
| This feature was implemented in https://github.com/roboll/helmfile/pull/906.
 | |
| If you're curious how it's designed and how it works, please consult the pull request.
 | |
| 
 | |
| ### Deploy Kustomizations with Helmfile
 | |
| 
 | |
| You can deploy [kustomize](https://github.com/kubernetes-sigs/kustomize) "kustomization"s with Helmfile.
 | |
| 
 | |
| Most of Kustomize operations that is usually done with `kustomize edit` can be done declaratively via Helm values.yaml files.
 | |
| 
 | |
| Under the hood, Helmfile transforms the kustomization into a local chart in a temporary directory so that it can be `helm upgrade --install`ed.
 | |
| 
 | |
| The transformation is done by generating (1)a temporary kustomization from various options and (2)temporary chart from the temporary kustomization.
 | |
| 
 | |
| An example pseudo code for the transformation logic can be written as:
 | |
| 
 | |
| ```console
 | |
| $ TMPCHART=/tmp/sometmpdir
 | |
| $ mkdir -p ${TMPCHART}/templates
 | |
| $ somehow_generate_chart_yaml ${TMPCHART}/Chart.yaml
 | |
| 
 | |
| $ TMPKUSTOMIZATION=/tmp/sometmpdir2
 | |
| $ somehow_generate_temp_kustomization_yaml ${TMPKUSTOMIZATION}/kustomization.yaml
 | |
| $ kustomize build ${TMPKUSTOMIZATION}/kustomization.yaml > ${TMPCHART}/templates/all.yaml
 | |
| ```
 | |
| 
 | |
| Let's say you have a `helmfile.yaml` that looks like the below:
 | |
| 
 | |
| ```yaml
 | |
| releases:
 | |
| - name: myapp
 | |
|   chart: mykustomization
 | |
|   values:
 | |
|   - values.yaml
 | |
| ```
 | |
| 
 | |
| Helmfile firstly generates a temporary `kustomization.yaml` that looks like:
 | |
| 
 | |
| ```yaml
 | |
| bases:
 | |
| - $(ABS_PATH_TO_HELMFILE_YAML}/mykustomization
 | |
| ```
 | |
| 
 | |
| Followed by the below steps:
 | |
| 
 | |
| - Running `kustomize edit set image $IMAGE` for every `$IMAGE` generated from your values.yaml
 | |
| - Running `kustomize edit set nameprefix $NAMEPREFIX` with the nameprefix specified in your values.yaml
 | |
| - Running `kustomize edit set namesuffix $NAMESUFFIX` with the namesuffix specified in your values.yaml
 | |
| - Running `kustomize edit set namespace $NS` with the namespace specified in your values.yaml
 | |
| 
 | |
| A `values.yaml` file for kustomization would look like the below:
 | |
| 
 | |
| ```yaml
 | |
| images:
 | |
| # kustomize edit set image mysql=eu.gcr.io/my-project/mysql@canary
 | |
| - name: mysql
 | |
|   newName: eu.gcr.io/my-project/mysql
 | |
|   newTag: canary
 | |
| # kustomize edit set image myapp=my-registry/my-app@sha256:24a0c4b4a4c0eb97a1aabb8e29f18e917d05abfe1b7a7c07857230879ce7d3d3
 | |
| - name: myapp
 | |
|   digest: sha256:24a0c4b4a4c0eb97a1aabb8e29f18e917d05abfe1b7a7c07857230879ce7d3d3
 | |
|   newName: my-registry/my-app
 | |
| 
 | |
| # kustomize edit set nameprefix foo-
 | |
| namePrefix: foo-
 | |
| 
 | |
| # kustomize edit set namesuffix -bar
 | |
| nameSuffix: -bar
 | |
| 
 | |
| # kustomize edit set namespace myapp
 | |
| namespace: myapp
 | |
| ```
 | |
| 
 | |
| At this point, Helmfile can generate a complete kustomization from the base kustomization you specified in `releases[].chart` of your helmfile.yaml and `values.yaml`,
 | |
| which can be included in the temporary chart.
 | |
| 
 | |
| After all, Helmfile just installs the temporary chart like standard charts, which allows you to manage everything with Helmfile regardless of each app is declared using a Helm chart or a kustomization.
 | |
| 
 | |
| Please also see [test/advanced/helmfile.yaml](https://github.com/helmfile/helmfile/tree/master/test/advanced/helmfile.yaml) for an example of kustomization support and more.
 | |
| 
 | |
| ### Adhoc Kustomization of Helm charts
 | |
| 
 | |
| With Helmfile's integration with Helmfile, not only deploying Kustomization as a Helm chart, you can kustomize charts before installation.
 | |
| 
 | |
| Currently, Helmfile allows you to set the following fields for kustomizing the chart:
 | |
| 
 | |
| - [`releases[].strategicMergePatches`](#strategicmergepatches)
 | |
| - `releases[].jsonPatches`
 | |
| - [`releases[].transformers`](#transformers)
 | |
| 
 | |
| #### `strategicMergePatches`
 | |
| 
 | |
| You can add/update any Kubernetes resource field rendered from a Helm chart by specifying `releases[].strategicMergePatches`:
 | |
| 
 | |
| ```
 | |
| repositories:
 | |
| - name: incubator
 | |
|   url: https://kubernetes-charts-incubator.storage.googleapis.com
 | |
| 
 | |
| releases:
 | |
| - name: raw1
 | |
|   chart: incubator/raw
 | |
|   values:
 | |
|   - resources:
 | |
|     - apiVersion: v1
 | |
|       kind: ConfigMap
 | |
|       metadata:
 | |
|         name: raw1
 | |
|         namespace: default
 | |
|       data:
 | |
|         foo: FOO
 | |
|   strategicMergePatches:
 | |
|     - apiVersion: v1
 | |
|       kind: ConfigMap
 | |
|       metadata:
 | |
|         name: raw1
 | |
|         namespace: default
 | |
|       data:
 | |
|         bar: BAR
 | |
| ```
 | |
| 
 | |
| Running `helmfile template` on the above example results in a ConfigMap called `raw` whose `data` is:
 | |
| 
 | |
| ```yaml
 | |
| foo: FOO
 | |
| bar: BAR
 | |
| ```
 | |
| 
 | |
| Please note that the second `data` field `bar` is coming from the strategic-merge patch defined in the above helmfile.yaml.
 | |
| 
 | |
| There's also `releases[].jsonPatches` that works similarly to `strategicMergePatches` but has additional capability to remove fields.
 | |
| 
 | |
| Please also see [test/advanced/helmfile.yaml](https://github.com/helmfile/helmfile/tree/master/test/advanced/helmfile.yaml) for an example of patching support and more.
 | |
| 
 | |
| #### `transformers`
 | |
| 
 | |
| You can set `transformers` to apply [Kustomize's transformers](https://github.com/kubernetes-sigs/kustomize/blob/master/examples/configureBuiltinPlugin.md#configuring-the-builtin-plugins-instead).
 | |
| 
 | |
| Each item can be a path to a YAML or go template file, or an embedded transformer declaration as a YAML hash.
 | |
| 
 | |
| It's often used to add common labels and annotations to your resources.
 | |
| 
 | |
| In the below example. we add common annotations and labels every resource rendered from the `aws-load-balancer-controller` chart:
 | |
| 
 | |
| ```yaml
 | |
| releases:
 | |
| - name: "aws-load-balancer-controller"
 | |
|   namespace: "kube-system"
 | |
|   forceNamespace: "kube-system"
 | |
|   chart: "center/aws/aws-load-balancer-controller"
 | |
|   transformers:
 | |
|   - apiVersion: builtin
 | |
|     kind: AnnotationsTransformer
 | |
|     metadata:
 | |
|       name: notImportantHere
 | |
|     annotations:
 | |
|       area: 51
 | |
|       greeting: take me to your leader
 | |
|     fieldSpecs:
 | |
|     - path: metadata/annotations
 | |
|       create: true
 | |
|   - apiVersion: builtin
 | |
|     kind: LabelTransformer
 | |
|     metadata:
 | |
|       name: notImportantHere
 | |
|     labels:
 | |
|       foo: bar
 | |
|     fieldSpecs:
 | |
|     - path: metadata/labels
 | |
|       create: true
 | |
| ```
 | |
| 
 | |
| As explained earlier, `transformers` can be not only a list of embedded transformers, but also YAML or go template files, or a mix of those three kinds.
 | |
| 
 | |
| ```yaml
 | |
| transformers:
 | |
| # Embedded transformer
 | |
| - apiVersion: builtin
 | |
|   kind: AnnotationsTransformer
 | |
|   metadata:
 | |
|     name: notImportantHere
 | |
|   annotations:
 | |
|     area: 51
 | |
|     greeting: take me to your leader
 | |
|   fieldSpecs:
 | |
|   - path: metadata/annotations
 | |
|     create: true
 | |
| # YAML file
 | |
| - path/to/transformer.yaml
 | |
| # Go template
 | |
| # The same set of template parameters as release values files templates is available.
 | |
| - path/to/transformer.yaml.gotmpl
 | |
| ```
 | |
| 
 | |
| Please see https://github.com/kubernetes-sigs/kustomize/blob/master/examples/configureBuiltinPlugin.md#configuring-the-builtin-plugins-instead for more information on how to declare transformers.
 | |
| 
 | |
| ### Adding dependencies without forking the chart
 | |
| 
 | |
| With Helmfile, you can add chart dependencies to a Helm chart without forking it.
 | |
| 
 | |
| An example `helmfile.yaml` that adds a `stable/envoy` dependency to the release `foo` looks like the below:
 | |
| 
 | |
| ```
 | |
| repositories:
 | |
| - name: stable
 | |
|   url: https://charts.helm.sh/stable
 | |
| 
 | |
| releases:
 | |
| - name: foo
 | |
|   chart: ./path/to/foo
 | |
|   dependencies:
 | |
|   - chart: stable/envoy
 | |
|     version: 1.5
 | |
| ```
 | |
| 
 | |
| When Helmfile encounters `releases[].dependencies`, it creates a another temporary chart from `./path/to/foo` and adds the following `dependencies` to the `Chart.yaml`, so that you don't need to fork the chart.
 | |
| 
 | |
| ```
 | |
| dependencies:
 | |
| - name: envoy
 | |
|   repo: https://charts.helm.sh/stable
 | |
|   condition: envoy.enabled
 | |
| ```
 | |
| 
 | |
| A Helm chart can have two or more dependencies for the same chart with different `alias`es. To give your dependency an `alias`, defien it like you would do in a standard `Chart.yaml`:
 | |
| 
 | |
| ```
 | |
| repositories:
 | |
| - name: stable
 | |
|   url: https://charts.helm.sh/stable
 | |
| 
 | |
| releases:
 | |
| - name: foo
 | |
|   chart: ./path/to/foo
 | |
|   dependencies:
 | |
|   - chart: stable/envoy
 | |
|     version: 1.5
 | |
|     alias: bar
 | |
|   - chart: stable/envoy
 | |
|     version: 1.5
 | |
|     alias: baz
 | |
| ```
 | |
| 
 | |
| which will tweaks the temporary chart's `Chart.yaml` to have:
 | |
| 
 | |
| 
 | |
| ```
 | |
| dependencies:
 | |
| - alias: bar
 | |
|   name: envoy
 | |
|   repo: https://charts.helm.sh/stable
 | |
|   condition: bar.enabled
 | |
| - alias: baz
 | |
|   name: envoy
 | |
|   repo: https://charts.helm.sh/stable
 | |
|   condition: baz.enabled
 | |
| ```
 | |
| 
 | |
| Please see #649 for more context around this feature.
 | |
| 
 | |
| After the support for adhoc dependency to local chart (#1765),
 | |
| you can even write local file paths relative to `helmfile.yaml` in `chart`:
 | |
| 
 | |
| ```
 | |
| releases:
 | |
| - name: foo
 | |
|   chart: ./path/to/foo
 | |
|   dependencies:
 | |
|   - chart: ./path/to/bar
 | |
| ```
 | |
| 
 | |
| Internally, Helmfile creates another temporary chart from the local chart `./path/to/foo`, and modifies the chart's `Chart.yaml` dependencies to look like:
 | |
| 
 | |
| ```
 | |
| dependencies:
 | |
| - alias: bar
 | |
|   name: bar
 | |
|   repo: file:///abs/path/to/bar
 | |
|   condition: bar.enabled
 | |
| ```
 | |
| 
 | |
| Please read https://github.com/roboll/helmfile/issues/1762#issuecomment-816341251 for more details.
 | |
| 
 | |
| #### OCI chart dependencies
 | |
| 
 | |
| With Helmfile version v0.146.0 or later, you can add OCI chart to chart dependencies.
 | |
| 
 | |
| An example `helmfile.yaml` that adds a OCI chart dependency to the release `foo` looks like the below:
 | |
| 
 | |
| ```
 | |
| releases:
 | |
| - name: foo
 | |
|   chart: ./path/to/foo
 | |
|   dependencies:
 | |
|   - chart: oci://my-oci-registry/helm-repo/envoy
 | |
|     version: 1.5
 | |
| ```
 |