I a have a couple of charts for different products. In the first one a helper was written to build out the repo, image name and tag/version. This works but as the other Chart is quite different I've gone through a simpler approach but it does not work. I get the error,
error calling include: template: MYChart/templates/_helpers.tpl:94:28: executing "getImageName" at <.Values.registryName>: nil pointer evaluating interface {}.registryName
This is the helper.
{{/*
This allows us to not have image: .Values.xxxx.ssss/.Values.xxx.xxx:.Values.ssss
in every single template.
*/}}
{{- define "imageName" -}}
{{- $registryName := .Values.registryName -}}
{{- $imageName := .Values.imageName -}}
{{- $tag := .Chart.AppVersion -}}
{{- printf "%s/%s:%s" $registryName $imageName $tag -}}
{{- end -}}
These are the values
registry:
registryName: "index.docker.io/myrepo"
image_Name: "myimage"
Calling a value like the above in a _helper.tpl should work, there are plenty of examples that use this approach. What am I missing?
The template file :
{{- $root := . -}}
{{- $FullChartName := include "myapp.fullname" . -}}
{{- $ChartName := include "myapp.name" . -}}
{{- range $worker, $parameter := .Values.workerPods }}
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: {{ $parameter.name }}-worker
spec:
replicas: {{ $parameter.replicas }}
selector:
matchLabels:
app.kubernetes.io/name: {{ $parameter.name }}-worker
app.kubernetes.io/instance: {{ $root.Release.Name }}
template:
metadata:
labels:
app.kubernetes.io/name: {{ $parameter.name }}-worker
app.kubernetes.io/instance: {{ $root.Release.Name }}
autoscale: "true"
annotations:
{{- if $root.Values.worker.annotations }}
{{ toYaml $root.Values.worker.annotations | indent 8 }}
{{- end }}
spec:
imagePullSecrets:
- name: myapp-registry-credentials
containers:
- name: {{ $parameter.name }}-worker
image: {{ template "imageName" . }}
imagePullPolicy: {{ $root.Values.worker.image.pullPolicy }}
command: ["/bin/sh"]
args: ["-c", "until /usr/bin/pg_isready -h $DATABASE_HOST; do sleep 2; done; bundle exec rake jobs:work"]
{{- range $container, $containerResources := $root.Values.containers }}
{{- if eq $container $parameter.size }}
resources:
{{- toYaml $containerResources.resources | nindent 12 }}
{{- end }}
{{- end }}
envFrom:
- configMapRef:
name: common-env
- secretRef:
name: myapp-secrets
volumeMounts:
- name: mnt-data
mountPath: "/mnt/data"
volumes:
- name: mnt-data
persistentVolumeClaim:
claimName: myapp-pvc
{{- with $root.Values.nodeSelector }}
nodeSelector:
{{- toYaml . | nindent 8 }}
{{- end }}
{{- with $root.Values.affinity }}
affinity:
{{- toYaml . | nindent 8 }}
{{- end }}
{{- with $root.Values.tolerations }}
tolerations:
{{- toYaml . | nindent 8 }}
{{- end }}
{{- end }}
I also tried this approach and added the following to the Chart.yaml
but got a similar error, I'll be honest and wasn't sure this would even work but would be interested to hear other's thoughts.
annotations:
image: "myimage"
registry: "index.docker.io/myrepo"
And the helper looked like this.
{{/*
This allows us to not have image: .Values.xxxx.ssss/.Values.xxx.xxx:.Values.ssss
in every single template.
*/}}
{{- define "imageName" -}}
{{- $registryName := .Chart.Annotations.registry -}}
{{- $imageName := .Chart.Annotations.image -}}
{{- $tag := .Chart.AppVersion -}}
{{- printf "%s/%s:%s" $registryName $imageName $tag -}}
{{- end -}}
You're calling the template with the wrong parameter. Reducing the Helm template file to the bare minimum to demonstrate this:
The standard Go
text/template
range
statement rebinds the.
variable (I believe to the same thing as$parameter
). So then when you call theimageName
template, its parameter isn't the Helm root value but rather the block from the values file;.Values
is undefined and returnsnil
; and then.Values.registryName
is a lookup onnil
which produces the error you see.One standard workaround to this is to save
.
to a variable outside therange
loop and use that variable everywhere you would have used.
. And in fact you already do this, the$root.Values.worker...
reference in the following line should work correctly. You just need to change this at the point of call: