Nine ExternalSecrets are permanently failing against deleted SSM keys #766
Labels
No labels
burndown-2026-06
burndown-2026-08
autonomy
async-consult
autonomy
epic
autonomy
headless
autonomy
live-collab
coherence-core
priority
P0
priority
P1
priority
P2
priority
P3
priority
P4
qa-fixture
role/advocate
role/director
role/exec
role/frontend
role/gamedev
role/human
role/platform
role/qa
role/science
role/sysadmin
state
ambient
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Dependencies
No dependencies set
Reference
coilyco-flight-deck/infrastructure#766
Loading…
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Nine
ExternalSecretobjects on kai-server are stuck inSecretSyncedError,each retrying continuously (observed counts 654 to 1610 and climbing). Every one
points at an SSM key that no longer exists.
Why this is not cosmetic
The
Secreteach one targets still exists, aged 56 to 478 days. Workloadsare running on that stale material right now, so nothing is visibly broken. What
is broken is the ability to ever refresh it.
Secretobjects is deleted, or its namespace recreated, theworkload cannot come back. There is no path to resynthesise the value.
the recent Warning volume on the cluster and buries real signal.
Most pointed example:
StatefulSet default/null-dbis Running 1/1 and takesPOSTGRES_PASSWORDfrom the stalenull-dbSecret (78d). A live Postgres whosepassword is unrotatable and unrecoverable.
The nine, grouped by what to do
Declared in this repo, so fix the declaration
external-secrets/github-pat- key/github/pat(missing). Declared indeploy/externalsecret.yml. Secret is 478d old.
forgejo/forgejo-tap-writer-secrets- keys/forgejo/api-token(missing) and/forgejo/coilyco-ops/ci-release-token(exists). Declared indeploy/forgejo-runner-tap-writer.yml.
/forgejo/coilyco-ops/api-tokendoes exist, so this looks like a leftoverfrom the coilyco-ops token-family migration and the fix is likely a one-line
repath. Its
StatefulSet forgejo-runner-tap-writeris scaled to 0, so thebreakage is latent rather than active, and would surface the first time
anyone scales it up.
Declared nowhere, so orphaned cluster state to delete
kubectl applynever prunes, so these survived the work that removed theirdefinitions. Not in this repo, not in deploy.
coilysiren-eco-app/ts-authkey- key/coilysiren/eco-mcp/ts-authkey.coilysiren-eco-app/coilysiren-eco-app-sentry- key/sentry-dsn/eco-mcp-app.Both use retired
eco-mcpnaming and are leftovers from the predecessornamespaces that coilyco-bridge/deploy#101 replaced. The eco-app manifest that is
actually deployed declares neither. Related: infrastructure#627 owns deleting
the predecessor workloads.
default/ts-authkey- key/coilysiren/eco-mcp/ts-authkey. Same retired path.Live tailscale consumers use per-service paths such as
/coilysiren/playwright-mcp/ts-authkey, which sync fine.default/null-db- key/coilysiren/backend/db-password. Has a runningconsumer, see above. Needs a decision, not a blind delete.
default/null-datastore-token- key/coilysiren/backend/datastore-token.default/null-sentry- key/sentry-dsn/eco-mcp-app.default/docker-registry- key/github/pat. Secret is 476d old, from theGitHub-era pull-secret setup.
Distinct missing keys
Six, several shared by two consumers:
/github/pat/sentry-dsn/eco-mcp-app/coilysiren/eco-mcp/ts-authkey/coilysiren/backend/db-password/coilysiren/backend/datastore-token/forgejo/api-tokenSuggested order
forgejo-tap-writer-secrets, because the correct key demonstrably exists andit is a real runner that will fail when next scaled up.
coilysiren-eco-appanddefaultorphans, which are almost certainlydeletions but each needs its consumer checked first.
null-dblast and deliberately, since a running database depends on it andthe question is whether the
null-*stack should still exist at all.github-patanddocker-registry, both GitHub-era and likely retiredwholesale.
Each deletion is a live cluster mutation, so this wants an attended operator
rather than an unattended run.
Correction on
forgejo-tap-writer-secrets: this is not a repathI guessed "one-line repath" in the description. Wrong. The repo declaration is
already correct. Both keys it names exist in SSM:
/forgejo/runner-registration-tokenEXISTS/forgejo/coilyco-ops/tap-bump-tokenEXISTSThe live object is the stale one. It still carries the pre-migration spec, so
nothing needs editing. The manifest simply was never applied.
What the drift actually is
e0e1de3(2026-07-09) "fix: remove admin PAT from runner pods" rewrote thisrunner to stop minting a registration token with a site-admin PAT inside the
pod, using a pre-minted bounded token instead. That commit has been on
mainfor a month and never reached the cluster. The live object dates from
2026-06-06.
So this is an unapplied security fix, not a broken key. Server-side dry-run
diff of
deploy/forgejo-runner-tap-writer.ymlagainst live:ExternalSecret
/forgejo/api-token->/forgejo/runner-registration-tokenapi-token->runner-token/forgejo/coilyco-ops/ci-release-token->/forgejo/coilyco-ops/tap-bump-tokenforce-sync: repoint-a8d7dedannotation, evidence of anearlier attempt to fix this by forcing a resync rather than applying
StatefulSet
/api/v1/admin/runners/registration-tokenusingAPI_TOKENAPI_TOKEN/api-token->RUNNER_TOKEN/runner-tokenreplicas: 0->1Live exposure today is low: the pod count is zero and
/forgejo/api-tokenwasdeleted from SSM, so the admin PAT is not merely unused but gone. The cluster
object is just describing a design that no longer exists.
The one consequence to decide
Applying converges to declared desired state, which includes starting the
tap-writer runner for the first time since it was scaled down. That is the repo's
intent (
replicas: 1), and it should now succeed where it previously could not,because the token it needs exists. Rollback is
kubectl scale --replicas=0 statefulset/forgejo-runner-tap-writer -n forgejo.Applying the ExternalSecret alone would silence the error without starting
anything, but would leave the StatefulSet on the old admin-PAT spec, so the
security fix would stay unapplied. Not recommended as an end state.
Resolved. Zero ExternalSecrets are failing on kai-server.
All 100, every one synced. The
defaultnamespace, called out here specifically, now holds exactly one ExternalSecret (eco-admin-token) and it is healthy.I did not establish how they were resolved, only that they are. The consumers appear to have been deleted rather than repointed: the three named in the sibling issue #589 all return
NotFound, and/github/patdoes not exist in SSM either. So the drift was cleaned up from the consumer side at some point and nothing recorded it here.This and #766 or #809 (whichever you are not reading) shared 12 rare identifiers in a duplicate scan, which is how the pair surfaced. Closing both.