Helm Values
Overview
Holos makes it easier to integrate multiple Helm charts together. Holos adds valuable capabilities to Helm and Kustomize.
- Inject the same value into two or more charts to integrate them safer than Helm alone.
- Add strong type checking and validation of constraints for Helm input values.
- Implementation of the rendered manifests pattern.
We'll manage the prometheus and blackbox Helm Charts in this tutorial.
Unfortunately, the upstream values.yaml
files are misconfigured by default.
Prometheus tries to connect to Blackbox at the wrong host and port.
Holos and CUE makes it easy to fix this problem by integrating them correctly. The integrated charts will stay in lock step over time.
The Code
Generating the structure
Use holos
to generate a minimal platform directory structure. First, create
and cd into a blank directory. Then use the holos init platform
command.
mkdir holos-helm-values-tutorial
cd holos-helm-values-tutorial
holos init platform v1alpha5
Make a commit to track changes.
git init . && git add . && git commit -m initial
Managing the Components
Create the prometheus
and blackbox
component directories, then add each of
the following file contents.
mkdir -p components/prometheus components/blackbox
touch components/prometheus/prometheus.cue
touch components/blackbox/blackbox.cue
- prometheus.cue
- blackbox.cue
components/prometheus/prometheus.cue
package holos
// Produce a helm chart build plan.
holos: Helm.BuildPlan
Helm: #Helm & {
Chart: {
name: "prometheus"
version: "25.27.0"
repository: {
name: "prometheus-community"
url: "https://prometheus-community.github.io/helm-charts"
}
}
}
components/blackbox/blackbox.cue
package holos
// Produce a helm chart build plan.
holos: Helm.BuildPlan
Helm: #Helm & {
Chart: {
name: "prometheus-blackbox-exporter"
version: "9.0.1"
repository: {
name: "prometheus-community"
url: "https://prometheus-community.github.io/helm-charts"
}
}
}
Integrating the Components
Integrate the components with the platform by adding the following file to the platform directory.
touch platform/prometheus.cue
package holos
Platform: Components: {
prometheus: {
name: "prometheus"
path: "components/prometheus"
}
blackbox: {
name: "blackbox"
path: "components/blackbox"
}
}
Render the platform.
- Command
- Output
holos render platform ./platform
cached prometheus-blackbox-exporter 9.0.1
rendered blackbox in 3.825430417s
cached prometheus 25.27.0
rendered prometheus in 4.840089667s
rendered platform in 4.840137792s
Commit the results.
- Command
- Output
git add . && git commit -m 'add blackbox and prometheus'
[main b5df111] add blackbox and prometheus
5 files changed, 1550 insertions(+)
create mode 100644 components/blackbox/blackbox.cue
create mode 100644 components/prometheus/prometheus.cue
create mode 100644 deploy/components/blackbox/blackbox.gen.yaml
create mode 100644 deploy/components/prometheus/prometheus.gen.yaml
create mode 100644 platform/prometheus.cue
Importing Helm Values
Holos renders the helm charts with their default values. We can import these default values into CUE so we can easily work with them as structured data instead of text markup.
holos cue import \
--package holos \
--path 'Helm: Values:' \
--outfile components/prometheus/values.cue \
components/prometheus/vendor/25.27.0/prometheus/values.yaml
holos cue import \
--package holos \
--path 'Helm: Values:' \
--outfile components/blackbox/values.cue \
components/blackbox/vendor/9.0.1/prometheus-blackbox-exporter/values.yaml
These command convert the YAML data into CUE code and nest the values under the
Values
field of the Holos
struct.
CUE unifies values.cue
with the other *.cue
files in the same directory.
Render the platform and commit the results.
- Command
- Output
holos render platform ./platform
rendered blackbox in 365.936792ms
rendered prometheus in 371.855875ms
rendered platform in 372.109916ms
- Command
- Output
git add . && git commit -m 'import values'
[main 52e90ea] import values
2 files changed, 1815 insertions(+)
create mode 100644 components/blackbox/values.cue
create mode 100644 components/prometheus/values.cue
Managing Common Configuration
Define a structure to hold the configuration values we want both helm charts to
use. We add this configuration to the components
directory so it's in scope
for all components.
touch components/blackbox.cue
package holos
// Schema Definition
#Blackbox: {
// host constrained to a lower case dns label
host: string & =~"^[a-z0-9]([a-z0-9-]{0,61}[a-z0-9])?$"
// port constrained to a valid range
port: int & >0 & <=65535
}
// Concrete values must validate against the schema.
Blackbox: #Blackbox & {
host: "blackbox"
port: 9115
}
- CUE loads and unifies all
*.cue
files from the root directory containingcue.mod
to the leaf component path directory. - CUE validates types and constraints. Validation with CUE is better than languages with only type checking.
Add and commit the configuration.
- Command
- Output
git add . && git commit -m 'add blackbox configuration'
[main 1adcd08] add blackbox configuration
1 file changed, 15 insertions(+)
create mode 100644 components/blackbox.cue
Referring to Common Configuration
Referencing common configuration from multiple components is easy and safe with Holos and CUE.
Patch the two values.cue
files, or edit them by hand, to reference
Blackbox.host
and Blackbox.port
.
- Command
- values.patch
- Output
patch -p1 < values.patch
--- a/components/blackbox/values.cue
+++ b/components/blackbox/values.cue
@@ -1,6 +1,8 @@
package holos
Helm: Values: {
+ fullnameOverride: Blackbox.host
+
global: {
//# Global image registry to use if it needs to be overriden for some specific use cases (e.g local registries, custom images, ...)
//#
@@ -192,7 +194,7 @@ Helm: Values: {
annotations: {}
labels: {}
type: "ClusterIP"
- port: 9115
+ port: Blackbox.port
ipDualStack: {
enabled: false
ipFamilies: ["IPv6", "IPv4"]
--- a/components/prometheus/values.cue
+++ b/components/prometheus/values.cue
@@ -1083,7 +1083,7 @@ Helm: Values: {
target_label: "__param_target"
}, {
target_label: "__address__"
- replacement: "blackbox"
+ replacement: "\(Blackbox.host):\(Blackbox.port)"
}, {
source_labels: ["__param_target"]
target_label: "instance"
patching file 'components/blackbox/values.cue'
patching file 'components/prometheus/values.cue'
Both charts now use the same values in lock step. Holos and CUE integrate them safely and easily.
Remove the patch file, then commit the changes.
- Command
- Output
rm values.patch
git add . && git commit -m 'integrate blackbox and prometheus together'
[main 4221803] integrate blackbox and prometheus together
2 files changed, 4 insertions(+), 2 deletions(-)
Reviewing Changes
Holos makes it easy to see and review platform wide changes. Render the platform to see how both prometheus and blackbox change in lock step.
- Command
- Output
holos render platform ./platform
rendered blackbox in 374.810666ms
rendered prometheus in 382.899334ms
rendered platform in 383.270625ms
Changes are easily visible with version control.
- Command
- Output
git diff
diff --git a/deploy/components/blackbox/blackbox.gen.yaml b/deploy/components/blackbox/blackbox.gen.yaml
index 3db20cd..5336f44 100644
--- a/deploy/components/blackbox/blackbox.gen.yaml
+++ b/deploy/components/blackbox/blackbox.gen.yaml
@@ -7,7 +7,7 @@ metadata:
app.kubernetes.io/name: prometheus-blackbox-exporter
app.kubernetes.io/version: v0.25.0
helm.sh/chart: prometheus-blackbox-exporter-9.0.1
- name: prometheus-blackbox-exporter
+ name: blackbox
namespace: default
---
apiVersion: v1
@@ -31,7 +31,7 @@ metadata:
app.kubernetes.io/name: prometheus-blackbox-exporter
app.kubernetes.io/version: v0.25.0
helm.sh/chart: prometheus-blackbox-exporter-9.0.1
- name: prometheus-blackbox-exporter
+ name: blackbox
namespace: default
---
apiVersion: v1
@@ -43,7 +43,7 @@ metadata:
app.kubernetes.io/name: prometheus-blackbox-exporter
app.kubernetes.io/version: v0.25.0
helm.sh/chart: prometheus-blackbox-exporter-9.0.1
- name: prometheus-blackbox-exporter
+ name: blackbox
namespace: default
spec:
ports:
@@ -65,7 +65,7 @@ metadata:
app.kubernetes.io/name: prometheus-blackbox-exporter
app.kubernetes.io/version: v0.25.0
helm.sh/chart: prometheus-blackbox-exporter-9.0.1
- name: prometheus-blackbox-exporter
+ name: blackbox
namespace: default
spec:
replicas: 1
@@ -119,8 +119,8 @@ spec:
name: config
hostNetwork: false
restartPolicy: Always
- serviceAccountName: prometheus-blackbox-exporter
+ serviceAccountName: blackbox
volumes:
- configMap:
- name: prometheus-blackbox-exporter
+ name: blackbox
name: config
diff --git a/deploy/components/prometheus/prometheus.gen.yaml b/deploy/components/prometheus/prometheus.gen.yaml
index 9e02bce..ab638f0 100644
--- a/deploy/components/prometheus/prometheus.gen.yaml
+++ b/deploy/components/prometheus/prometheus.gen.yaml
@@ -589,7 +589,7 @@ data:
- source_labels:
- __address__
target_label: __param_target
- - replacement: blackbox
+ - replacement: blackbox:9115
target_label: __address__
- source_labels:
- __param_target
From the diff we know this change will:
- Reconfigure the blackbox exporter host from
prometheus-blackbox-exporter
toblackbox
. - Have no effect on the blackbox service port. It was already using the default 9115.
- Reconfigure prometheus to query the blackbox exporter at the correct host and
port,
blackbox:9115
.
Without this change prometheus incorrectly assumed blackbox was listening at
blackbox
on port 80
when it was actually listening at
prometheus-blackbox-exporter
port 9115
. Going forward, changing the
blackbox host or port will reconfigure both charts correctly.
Commit the changes and move on to deploying them.
- Command
- Output
git add . && git commit -m 'render integrated blackbox and prometheus manifests'
[main 67efe0d] render integrated blackbox and prometheus manifests
2 files changed, 7 insertions(+), 7 deletions(-)
Trying Locally
Optionally apply the manifests Holos rendered to a Local Cluster.
Next Steps
In this tutorial we learned how Holos makes it easier to holistically integrate the prometheus and blackbox charts so they're configured in lock step with each other. If we relied on Helm alone, there is no good way to configure both charts to use the same service endpoint.