Skip to content

helm: validate values with a schema, render-time guards, and helm tests - #26

Open
David Larsen (dc-larsen) wants to merge 1 commit into
mainfrom
helm-values-validation
Open

helm: validate values with a schema, render-time guards, and helm tests#26
David Larsen (dc-larsen) wants to merge 1 commit into
mainfrom
helm-values-validation

Conversation

@dc-larsen

@dc-larsen David Larsen (dc-larsen) commented Sep 1, 2026

Copy link
Copy Markdown

A recent enterprise rollout lost days to three misconfigurations this chart accepted without complaint:

  1. Indentation accident. A values file where the pathRouting: block lost its indentation, so YAML parsed pathRouting: null and the children (enabled, domain, routes, ...) became top-level keys. Helm ignored them, the firewall deployed with zero routes, and every request 404'd.
  2. Dead config. A top-level env: block no template reads, holding the API token.
  3. Wrong Redis endpoint shape. An ElastiCache cluster-mode configuration endpoint (clustercfg.*) in redis.host. The firewall's Redis client is single-endpoint and cannot follow MOVED redirects, so caching fails at runtime while the deployment looks healthy.

What's added

  • values.schema.json (draft-07) covering every top-level key, validated on install/upgrade/lint/template. Root and structured sections reject unknown keys; Kubernetes passthrough maps (annotations, resources, affinity, tolerations, extraConfig, ...) remain free-form.
  • Render-time guards (templates/validations.yaml): path routing enabled with no route source (inline routes, routesFile, or private-registry auto-discovery), clustercfg.* Redis hosts, and missing socket.apiToken/socket.existingSecret all fail with actionable messages.
  • helm test pod: /health returns 200 with "Health OK", egress + TLS to the Socket API (expects exactly 401 from /v0/quota, honoring socket.apiUrl), redis_available 1 via /metrics when Redis is enabled, and Host-header route matching for the first path route.
  • NOTES warnings for socket.failOpen=true (packages pass unscanned when the API is unreachable) and internet-facing ALB ingress with no client auth gate (open proxy).
  • README "Validating Your Configuration" section.

Breaking change

Unknown top-level values keys now fail validation instead of being silently ignored. This is deliberate; use extraConfig for raw socket.yml passthrough. Chart version bumped to 0.12.0.

Validation

helm lint (default and --strict) passes; all three bundled examples lint and template cleanly; regression fixtures for each failure mode fail with the intended errors; render-diff against main with default values shows the new test pod as the only change.


Note

Medium Risk
The breaking schema strictness can fail existing upgrades that relied on ignored top-level keys; otherwise changes are chart-only validation and test hooks with no runtime firewall logic changes.

Overview
Helm chart 0.12.0 adds layered configuration validation and post-deploy checks so misconfigurations fail before or right after install instead of silently breaking production traffic.

A new values.schema.json validates types on install/upgrade/lint/template and rejects unknown top-level keys (breaking change: stray keys like mis-indented pathRouting children or unused env: blocks no longer pass; use extraConfig for raw socket.yml). templates/validations.yaml adds cross-field fail guards: path routing enabled with no routes/routesFile/private-registry discovery, clustercfg.* Redis hosts, and missing socket.apiToken / socket.existingSecret.

helm test runs a hook pod that checks health, Socket API egress (401 on /v0/quota), optional redis_available via /metrics, and path-route Host matching. NOTES.txt now warns on socket.failOpen and internet-facing ALB without client auth, and points operators at helm test. README documents the three validation layers.

Reviewed by Cursor Bugbot for commit b0eccdb. Configure here.

Three failure modes this chart previously accepted silently:

- A values file where an indentation accident turns a section (e.g.
  pathRouting) into null and promotes its children to top-level keys.
  The stray keys were ignored and the firewall deployed with zero
  routes, returning 404 for all traffic.
- Dead config: top-level keys no template reads (e.g. an env: block
  holding an API token).
- An ElastiCache cluster-mode configuration endpoint (clustercfg.*) in
  redis.host, which the firewall's single-endpoint Redis client cannot
  use (no MOVED-redirect support).

What's added:

- values.schema.json (draft-07) covering every top-level key, with
  additionalProperties: false at the root and in structured sections.
  Kubernetes passthrough maps (annotations, resources, affinity,
  tolerations, extraConfig, ...) stay free-form. Validated against the
  chart defaults and all bundled examples.
- templates/validations.yaml render-time guards: pathRouting enabled
  with no route source, clustercfg.* Redis endpoints, and missing
  socket.apiToken/existingSecret all fail with actionable messages.
  Guards are no-ops under helm lint (lint mode) and enforce on
  install/upgrade/template.
- helm test pod (templates/tests/): checks the /health endpoint,
  egress + TLS to the Socket API (expects exactly 401 from /v0/quota),
  redis_available via /metrics when Redis is enabled, and Host-header
  route matching for the first pathRouting route.
- NOTES.txt warnings for socket.failOpen=true and for internet-facing
  ALB ingress with no client auth gate (open proxy).
- README section on the validation layers and the strictness change.

Breaking change: unknown top-level values keys now fail instead of
being ignored. Use extraConfig for raw socket.yml passthrough.

@cursor cursor Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Cursor Bugbot has reviewed your changes using high effort and found 1 potential issue.

Fix All in Cursor

Bugbot Autofix is ON. A cloud agent has been kicked off to fix the reported issue.

Comment @cursor review or bugbot run to trigger another review on this PR

Reviewed by Cursor Bugbot for commit b0eccdb. Configure here.

echo " outbound HTTPS to {{ $apiUrl }} to fetch package verdicts."
fail "Socket API returned HTTP ${code} (expected exactly 401 — an unauthenticated 401 proves egress and TLS work)."
fi
echo " OK (HTTP 401 — egress and TLS to the Socket API verified)"

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

API test ignores egress settings

Medium Severity

Check 2 curls socket.apiUrl from the test pod and requires exactly HTTP 401. It does not use socket.outboundProxy, socket.apiSslCaCert, or socket.apiSslVerify, so a working firewall behind a corporate proxy or custom CA still fails helm test.

Fix in Cursor Fix in Web

Reviewed by Cursor Bugbot for commit b0eccdb. Configure here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants