# Fix Helm Errors from Sentry Alerts

Yes. When a Sentry event names a value your Helm chart renders, an agent reproduces it with a helm-unittest case, fixes the template, bumps the chart and opens a PR.

[Run this on Rush](https://cloud.getrush.ai/run/fix-sentry-errors/helm/), in a Project that has your repository.

## What the agent does

The agent reads the alert payload after the prompt, then opens the issue and its latest event through the Sentry connection. A Sentry event comes from the application a chart deploys, not from Helm, so the useful parts are the tags the SDK attached in a cluster: `server_name` as the pod name, `environment`, `release`, and the message itself, such as a connection refused to a service name, an environment variable read as empty, or a flag the binary rejects. The agent decides whether the cause is in the chart at all: when the message names a value, an argument or a hostname the templates render, it continues; when it names application code, it stops and says so.

Then it reads the chart repository. In prometheus-community/helm-charts there are 44 charts under `charts/`, and the agent opens the one the `release` tag names. `charts/kube-prometheus-stack/Chart.yaml` is version 92.10.1 with `appVersion` v0.94.1 and `kubeVersion` `>=1.25.0-0`, a `values.yaml` of 6218 lines, templates grouped under `templates/alertmanager/`, `templates/prometheus/`, `templates/prometheus-operator/`, `templates/grafana/`, `templates/exporters/` and `templates/thanos-ruler/` with `_helpers.tpl`, dependencies on `kube-state-metrics` 8.6.0, `prometheus-node-exporter` 4.60.0, `grafana` 14.0.1 and `prometheus-windows-exporter` `0.12.*`, and 29 `helm-unittest` files under `unittests/`. A smaller chart like `charts/prometheus-node-exporter`, version 4.60.0 with `appVersion` 1.12.1, has fourteen templates and three unittest files, one of which checks that the `--path.udev.data` argument is rendered for app versions from 1.4.0 and omitted below it, with `image.tag` variants including digests. The agent finds the template and the value behind the event's message by rendering the chart with `helm template` and the values the release used, and grepping the output for the string in the event.

The test comes before the fix. `.github/linters/ct.yaml` runs `helm unittest --strict --file 'unittests/**/*.yaml'` on every changed chart, so the agent adds a case to the matching suite, or a new `unittests/<component>/<topic>_test.yaml` in the same shape as `unittests/route_test.yaml`: a `suite`, the `templates` it renders, `set` values, and `asserts` such as `equal`, `contains`, `notExists` and `hasDocuments`. The case sets the values from the event and asserts the manifest the application should have received, so it fails on the current template with the wrong argument, hostname or environment variable. Then the agent changes the template or the default in `values.yaml`, keeping the chart's helper style from `_helpers.tpl`, and bumps `version` in `Chart.yaml` the way `CONTRIBUTING.md` requires: a patch for a fix, a major with an `Upgrading` note in the chart README when a default changes in a way users must act on.

The checks are the ones `.github/workflows/ci.yaml` runs, with Helm v4.3.1, chart-testing v3.15.0, `helm-unittest` 1.2.1 and `helm-values-schema-json` 2.6.0: `ct lint --config .github/linters/ct.yaml` for the changed chart, which also runs the chart's `ci/lint.sh` when it has one, `helm lint`, and the unittest command above. For `kube-prometheus-stack`, `ci/lint.sh` regenerates CRDs, rules and dashboards from `hack/` and fails if the tree differs, which is why a fix there never edits a generated rule file by hand. The repository's own `AGENTS.md` asks for exactly this shape: one chart, existing template style, focused unittest coverage, a SemVer bump, and the unittest command run before a pull request.

## Start it with one API call

`POST https://api.prix.dev/o/{org}/sessions`

```json
{
  "agent": "claude",
  "input": "A Sentry alert fired for a service deployed by a chart in this Helm repository; its payload follows this prompt. Use the Sentry connection to read the issue, its latest event, its message and the server_name, environment and release tags. First decide whether the cause is in the chart: continue only if the message names a value, argument, hostname or environment variable the chart's templates render, and otherwise stop and report that the fix belongs in the application. In a repository shaped like prometheus-community/helm-charts, open charts/<chart>/ for the chart the release names, render it with helm template and the values the release used, and find the template and value behind the message. Add a helm-unittest case under charts/<chart>/unittests/ in the style of the existing suites, setting those values and asserting the manifest the service should receive, and confirm it fails on the current template. Fix the template or the default in values.yaml in the chart's existing style, bump version in Chart.yaml following SemVer and CONTRIBUTING.md, and add an Upgrading note to the chart README if a default changed. Run helm lint, ct lint --config .github/linters/ct.yaml and helm unittest --strict --file 'unittests/**/*.yaml' charts/<chart> with the Helm, chart-testing and plugin versions .github/workflows/ci.yaml pins. Open a pull request titled [<chart>] <short description> that changes one chart only, links the Sentry issue, quotes the message and the failing test output, and explains the cause. If it does not reproduce in the rendered manifests, stop and report what you tried.\n\nAlert payload:\n{payload}",
  "resources": [
    {
      "url": "https://github.com/your-org/your-app"
    }
  ],
  "connections": [
    "sentry"
  ]
}
```

1. **Get an API key.** In the console, open Settings, then API keys, and create a key for your org. Send it in the Authorization header as a Bearer token.
2. **Send the request.** POST the body in request.json to https://api.prix.dev/o/{org}/sessions, with your repository as the resources URL. The run starts in its own cloud sandbox.
3. **Read what came back.** Follow the run on its live stream or wait for the run.completed webhook, then read the result and its trajectory.

## What comes back

What comes back is a pull request that changes one chart: a template under `charts/<chart>/templates/` or a default in its `values.yaml`, a new or extended file under `charts/<chart>/unittests/`, the `version` line in `Chart.yaml`, and an `Upgrading` section in the chart README when a default moved. Its title follows the `[chart-name] short description` form `REVIEW_GUIDELINES.md` asks for, and the description links the Sentry issue, quotes the message and the tags, shows the unittest case failing before the change and passing after, and gives the `helm lint`, `ct lint` and `helm unittest --strict` results.

Before merging, a maintainer checks that the test sets the values the release actually used rather than defaults, that the version bump matches the change (a patch for a rendering fix, a major when users must change their values), and that generated files under `kube-prometheus-stack` were not edited by hand, since `ci/lint.sh` regenerates them. When the event came from a chart version older than `main` and the template already changed, the description says so and the test pins the current rendering.

## Run it on every Sentry issue alert

Create an alert rule in the Sentry project for the deployed service with a webhook action pointed at a handler on your server, since Sentry signs its own requests and cannot add the `Authorization: Bearer` header a Rush `webhook` trigger needs. The handler places the alert JSON after the prompt and sends this request with the Sentry issue id as `Idempotency-Key`, so a redelivered alert returns the run already started. Because most application errors are not chart errors, expect many runs to end with a short result saying the fix belongs in the application, and no pull request.

Give the API key a webhook URL and Rush POSTs `run.completed` with `session_url` and the result when the turn ends; the handler can comment the pull request link, or the one-line verdict, on the Sentry issue. A chart repository that deploys several services sees several issues, each its own run, up to the key's `max_concurrent`.

## Why run it on Rush?

Tracing a production error back to a chart means rendering the chart with the release's values, finding the one line among thousands of rendered manifests that matches the message, and then proving the fix with the repository's own unittest plugin at the version CI pins. On Rush the agent does that in its own sandbox with Helm v4.3.1, chart-testing v3.15.0 and `helm-unittest` 1.2.1 installed, and hands back a diff that `ct lint` already accepts.

The record is the proof: the Sentry event the agent read, the rendered manifest with the wrong value, the unittest case failing and then passing, and the exact `ct lint` and `helm unittest --strict` output. A maintainer reviews a one-chart change with its evidence, and several alerts across several charts are several sandboxes at once.

## Frequently asked questions

### Sentry reports application errors. How can the fix be in a chart?

Only when the message names something the chart rendered: a service hostname in a connection refused error, an environment variable that arrived empty, a flag the binary rejected at start. The agent checks that first by rendering the chart and grepping for the string, and otherwise reports that the fix belongs in the application and opens no pull request.

### Does it need a Kubernetes cluster?

No. `helm template`, `helm lint`, `ct lint` and `helm unittest` all work on rendered YAML. The repository's integration job runs the `ci/*-values.yaml` files on a kind cluster, which the agent does not do; the description says the fix was proven by rendering and unit tests.

### Will it bump the chart version?

Yes. `CONTRIBUTING.md` requires a SemVer bump for any change, and `REVIEW_GUIDELINES.md` checks for it. A rendering fix is a patch; a changed default that users must react to is a major with an `Upgrading` note in the chart README, and the agent explains which it chose.

### What about charts with generated rules and dashboards?

`kube-prometheus-stack` syncs CRDs, Prometheus rules and Grafana dashboards from upstream through scripts in `hack/`, and `ci/lint.sh` fails if the tree differs from what they produce. The agent never edits those generated files by hand; a fix that would need to is reported as an upstream change.

### Can one run fix two charts?

No. The review guidelines allow one chart per pull request, so the agent scopes the change to the chart the `release` tag names. An event that implicates a subchart, such as `prometheus-node-exporter` inside `kube-prometheus-stack`, is fixed in the subchart's own directory, and the parent's dependency bump is a separate pull request.
