Setting nested data structures from helm command line? - kubernetes-helm

I'm installing the prometheus-redis-exporter Helm chart. Its Deployment object has a way to inject annotations:
# deployment.yaml
...
template:
metadata:
annotations:
{{ toYaml .Values.annotations | indent 8 }}
Typically if I was providing a values file, I could just do this:
# values.yaml
annotations:
foo: bar
bash: baz
And then install the chart with:
helm install --values values.yaml
However, in some cases it is more simple for me to specify these values on the command line with --set instead, I'm just not sure how I would specify a nested set like that.
How can I set the above annotations object when installing a helm chart on the commandline:
helm install --set <what_goes_here>

The helm docu has a section The Format and Limitations of --set, which contains what you are looking for.
--set outer.inner=value results in:
outer:
inner: value
Therefore your whole helm command looks like this:
helm install --set annotations.foo=bar,annotations.bash=baz stable/prometheus-redis-exporter

Just to add, if you are looking to override a key with a "." in the key name, add a back slash ("\") before the ".".
for example, with values (taken from grafana):
grafana.ini:
server:
root_url: https://my.example.com
To edit the root_url value we would pass
--set grafana\.ini.server.root_url=https://your.example.com

Related

Helm - documentation specification for very unusual and not regular Kubernetes YAML format

on microsoft docs I found that I should define this Helm YAML file for creating Kubernetes Ingress Controller:
controller:
service:
loadBalancerIP: 10.240.0.42
annotations:
service.beta.kubernetes.io/azure-load-balancer-internal: "true"
So you can easily notice it DOES NOT have usual Kubernetes apiVersion and kind specification.
and after, on the same link that I need to execute the helm command to create Ingress:
helm install nginx-ingress ingress-nginx/ingress-nginx \
-f internal-ingress.yaml \
..............
As you see - suggested Helm file is not very usual, but I would like to stick to those official Microsoft instructions!
Again, it does not have specification for creating Ingress Controller using the regular apiVersion and kind notation like on many links and examples that can be found on the internet.
https://github.com/helm/charts/blob/master/stable/nginx-ingress/templates/controller-service.yaml
https://kubernetes.github.io/ingress-nginx/user-guide/exposing-tcp-udp-services/
Can I set custom ports for a Kubernetes ingress to listen on besides 80 / 443?
So I really feel very very confused!!! Can you please help me on this - I need to set it's Port but I really could not find specification documentation and examples for this one YAML Microsoft example which actually works!!!
controller:
service:
loadBalancerIP: 10.240.0.42
annotations:
service.beta.kubernetes.io/azure-load-balancer-internal: "true"
Where and how I can find correct syntax how I can "translate" regular "apiVersion" and "kind" specification into this?
Why they are making confusion in this way with this different format???
Please help! Thanks
The -f does not set a "manifest" as stated in the Microsoft docs. As per helm install --help:
-f, --values strings specify values in a YAML file
or a URL (can specify multiple)
The default values file contains the values to be passed into the chart.
User-supplied values with -f are merged with the default value files to generate the final manifest. The precedence order is:
The values.yaml file in the chart
If this is a subchart, the values.yaml file of a parent chart
A values file if passed into helm install or helm upgrade with the -f flag (helm install -f myvals.yaml ./mychart)
Individual parameters passed with --set (such as helm install --set foo=bar ./mychart)
The list above is in order of specificity: values.yaml is the default, which can be overridden by a parent chart's values.yaml, which can in turn be overridden by a user-supplied values file, which can in turn be overridden by --set parameters.
What are you doing is overriding the controller value on top of the default values file. You can find the original/default values for the ingress-nginx chart here.

kube helm charts - multiple values files

it might be simple question but can't find anywhere if it's duable;
Is it possible to have values files for helm charts (stable/jenkins let's say) and have two different values files for it?
I would like in values_a.yaml have some values like these:
master:
componentName: "jenkins-master"
image: "jenkins/jenkins"
tag: "lts"
...
password: {{ .Values.secrets.masterPassword }}
and in the values_b.yaml - which will be encrypted with AWS KMS
secrets:
masterPassword: xxx
the above code doesn't work and wanted to know, as you can put those vars in kube manifests like it
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ .Values.config.name }}
namespace: {{ .Values.config.namespace }}
...
can they be somehow passed to other values files
EDIT:
If it was possible I would just put the
master:
password: xxx
in values_b.yaml but vars cannot be duplicated, and the official helm chart expects the master.password val from that file - so has to somehow pass it there but in encrypted way
I'm not quite sure but this feature of helm might help you.
Helm gives you the functionality to pass custom Values.yaml which have higher precedence over the fields of the main Values.yaml while performing helm install or helm upgrade.
For Helm 3
$ helm install <name> ./mychart -f myValues.yaml
For Helm 2
$ helm install --name <name> ./mychart --values myValues.yaml
The valid answer is from David Maze in the comments of the response of Kamol Hasan.
You can use multiple -f or --values options: helm install ... -f
values_a.yaml -f values_b.yaml. But you can't use templating in any
Helm values file unless the chart specifically supports it (using the
tpl function).
If you use multiple -f then latest value files override earlier ones.

Use values-production.yaml instead of values.yaml for Helm Dependencies

I am creating a helm chart that uses multiple dependencies. For some of those dependencies I would like to use their values-production.yaml instead of the default values.yaml. I have tried adding a tag section to the dependencies to call the production values but that doesn't seem to work. For example the redis chart has production-values.yaml and values.yaml. Is there a way for me to use the production-values within my chart's dependencies?
Eg my helm Chart.yaml looks like:
apiVersion: v2
name: parentChart
...
dependencies:
- name: redis
version: 10.5.3
repository: "#stable"
tags:
- prd-values
There are two ways to provide your values file.
helm install -f myvals.yaml ./mychart
helm install --set foo=bar ./mychart
The order of specificity: values.yaml is the default, which can be overridden by a parent chart’s values.yaml, which can in turn be overridden by a user-supplied values file, which can in turn be overridden by --set parameters.
This means if you have same values in your values.yaml and values-production.yaml then only values-production.yaml will be used as it will overwrite the fields in values.yaml.

Set extraEnvs ingress variable

I'm trying to use extraEnv property in order to add additional environment variables to set in the pod using helm charts.
I have a values.yaml file that includes:
controller:
service:
loadBalancerIP:
extraEnvs:
- name: ev1
value:
- name: ev2
value
first I've set the loadBalancerIP the following way:
helm template path/charts/ingress --set nginx-ingress.controller.service.loadBalancerIP=1.1.1.1 --output-dir .
In order to set extraEnvs values I've tried to use the same logic by doing:
helm template path/charts/ingress --set nginx-ingress.controller.service.loadBalancerIP=1.1.1.1 --set nginx-ingress.controller.extraEnvs[0].value=valueEnv1--set nginx.controller.extraEnvs[1].value=valueEnv2--output-dir .
But it doesn't work. I looked for the right way to set those variables but couldn't find anything.
Helm --set has some limitations.
Your best option is to avoid using the --set, and use the --values flag with your values.yaml file instead:
helm template path/charts/ingress \
--values=values.yaml
If you want to use --set anyway, the equivalent command should have this notation:
helm template path/charts/ingress \
--set=controller.service.loadBalancerIP=1.1.1.1 \
--set=controller.extraEnvs[0].name=ev1,controller.extraEnvs[0].value=valueEnv1 \
--set=controller.extraEnvs[1].name=ev2,controller.extraEnvs[1].value=valueEnv2 \
--output-dir .

How to reference a custom value file for sub-charts in helm?

I have been implementing helm sub-chart by referring helm sub chart documentation. According to the documentation it worked for me. This works fine with default value files. But when I try to refer my own value file, the values are not there in the configmap.
My value file is values.staging.yaml.
eg :-
config.yaml in mysubchart
apiVersion: v1
kind: ConfigMap
metadata:
name: {{ .Release.Name }}-configmap
data:
salad: {{ .Values.dessert }}
values.staging.yaml in mysubchart
dessert: banana
values.yaml in mysubchart
dessert: cake
Only 'cake' is referenced as the value. I need to reference banana as the value.
I have tried following commands.
helm install --dry-run --debug mychart --values mychart/charts/mysubchart/values.staging.yaml
helm install --dry-run --debug --name mychart mychart -f mychart/charts/mysubchart/values.staging.yaml
helm install --name mychart mychart -f mychart/charts/mysubchart/values.staging.yaml
In each instance the configmap does not refer the value in the values.staging.yaml.
Is there a way to do this?
Thank you .!
As described in Overriding Values of a Child Chart in your link, you need to wrap the subchart values in a key matching the name of the subchart.
Any values file you pass with helm install -f is always interpreted at the top level, even if it's physically located in a subchart's directory. A typical values file could look like
mysubchart:
dessert: banana