Plan user-engine runtime secret custody
This commit is contained in:
parent
26cb011141
commit
8578a0074d
1 changed files with 99 additions and 0 deletions
99
plans/user-engine-openbao-runtime-custody.md
Normal file
99
plans/user-engine-openbao-runtime-custody.md
Normal file
|
|
@ -0,0 +1,99 @@
|
|||
---
|
||||
id: user-engine-openbao-runtime-custody
|
||||
demand_source: net-kingdom/workplans/NK-WP-0023-T05
|
||||
consumer_repo: net-kingdom
|
||||
credential_type: openbao-approle-kv
|
||||
status: proposed
|
||||
created: "2026-07-30"
|
||||
updated: "2026-07-30"
|
||||
---
|
||||
|
||||
# Construction plan: user-engine OpenBao runtime custody
|
||||
|
||||
## 1. Demand
|
||||
|
||||
The live portal edge marker and identity-provisioner service token are
|
||||
bootstrap Kubernetes Secrets without an authoritative rotation source.
|
||||
`user-engine` and `identity-provisioner` need the same runtime behavior with
|
||||
OpenBao as authority and External Secrets Operator as delivery mechanism.
|
||||
|
||||
## 2. Existing-structure survey
|
||||
|
||||
- `Secret/user-engine-runtime` in namespace `user-engine` contains only
|
||||
`proxy-secret`.
|
||||
- `Secret/identity-provisioner-client` in namespace `user-engine` and
|
||||
`Secret/identity-provisioner-token` in namespace `sso` carry the two copies
|
||||
of the provisioner service token.
|
||||
- The applications already consume only Secret references; no code or
|
||||
Deployment interface change is required.
|
||||
- The established `rapp-qonto` bridge proves that railiance01 External Secrets
|
||||
must currently use AppRole against the OpenBao instance on CoulombCore;
|
||||
railiance01 service-account tokens cannot use that instance's Kubernetes
|
||||
auth mount.
|
||||
- Existing activity-core stores and policies are unrelated and must not be
|
||||
widened or reused across this identity boundary.
|
||||
|
||||
## 3. Proposed changes
|
||||
|
||||
| # | Action | Object | Rationale |
|
||||
|---|---|---|---|
|
||||
| 1 | create | KV path `platform/workloads/user-engine/runtime` | One authoritative workload path with fields `PROXY_SECRET` and `PROVISIONER_TOKEN` |
|
||||
| 2 | create | policy `workload-kv-read-user-engine-runtime` | Read and metadata access only to the exact KV v2 path |
|
||||
| 3 | create | AppRoles `external-secrets-user-engine` and `external-secrets-sso-user-engine` | Separate revocable bootstrap identities for the two consuming namespaces |
|
||||
| 4 | deliver | AppRole bootstrap Secrets in `external-secrets` | Write-only Mason delivery; 15-minute tokens, 30-minute maximum, eight uses |
|
||||
| 5 | create | namespace-restricted ClusterSecretStores for `user-engine` and `sso` | Prevent either identity from becoming a general cross-namespace store |
|
||||
| 6 | create | three ExternalSecrets targeting the existing Secret names | Preserve application interfaces while changing authority |
|
||||
| 7 | migrate | existing values into the KV path through a wrapped platform-admin process | Read source and write destination in one process; never return either value |
|
||||
| 8 | verify | metadata, rollout, positive/negative authentication, and rotation rehearsal | Record field names, readiness, denial, and rollout only |
|
||||
| 9 | retire | manual Secret-copy/bootstrap procedure | ExternalSecret becomes the sole writer and rotation path |
|
||||
|
||||
The migration does not mint a new application capability. It moves two
|
||||
existing values into governed custody. Same-cluster Kubernetes auth remains
|
||||
the target after OpenBao moves to reef-railiance.
|
||||
|
||||
## 4. Review and optimization
|
||||
|
||||
- Separate AppRoles avoid widening one namespace identity across `sso` and
|
||||
`user-engine`.
|
||||
- Both policies resolve to one exact path, avoiding duplicate values and
|
||||
divergent rotation.
|
||||
- Existing Secret names and keys remain stable, limiting rollout risk.
|
||||
- A wrapped migration process is required because printing, downloading, or
|
||||
staging either value would create a new disclosure path.
|
||||
- Reversal deletes the ExternalSecrets/stores/AppRoles and restores the
|
||||
protected pre-migration Secret snapshots during the bounded rollback window.
|
||||
- Rotation changes the OpenBao fields, waits for all three ExternalSecrets,
|
||||
and rolls the provisioner and portal together; failed synchronization stops
|
||||
before either Deployment changes.
|
||||
|
||||
## 5. Executive summary
|
||||
|
||||
**One-line ask:** approve moving the existing user-engine edge marker and
|
||||
provisioner token into one exact OpenBao workload path, delivered by two
|
||||
namespace-specific, revocable External Secrets AppRoles.
|
||||
|
||||
**Who gets access:** only External Secrets through
|
||||
`external-secrets-user-engine` and `external-secrets-sso-user-engine`.
|
||||
Application pods continue to receive only their existing namespaced Secrets.
|
||||
|
||||
**To what:** read-only access to exactly
|
||||
`platform/workloads/user-engine/runtime`; no sibling workload or tenant path.
|
||||
|
||||
**For how long:** each AppRole login receives a 15-minute token with a
|
||||
30-minute maximum and eight uses. AppRole secret IDs persist for ESO continuity
|
||||
until rotated or same-cluster Kubernetes auth replaces the bridge.
|
||||
|
||||
**Blast radius:** compromise permits impersonating the internal provisioner
|
||||
client and/or the portal trusted marker, but grants no direct OpenBao sibling
|
||||
read, directory administrator password, user password, MFA seed, or platform
|
||||
role. Revoke both AppRole secret IDs, rotate both runtime values, and roll the
|
||||
two workloads.
|
||||
|
||||
**Cost to reverse:** delete three ExternalSecrets, two stores, two AppRoles,
|
||||
their bootstrap Secrets, and one exact policy/path; restore the protected
|
||||
pre-migration Kubernetes Secret snapshots. No database or identity record
|
||||
changes.
|
||||
|
||||
**Decision needed:** approve as proposed, reject, or return with changes.
|
||||
Approval authorizes custody migration and bounded rotation rehearsal, never
|
||||
printing or otherwise disclosing either value.
|
||||
Loading…
Add table
Add a link
Reference in a new issue