You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Split from #7852. Once #8064 lands (a real tenant-DB-credential secret type + revoke path on the main app's broker), control-plane's TenantProvisioningDriver.injectSecrets/revokeSecrets (control-plane/src/tenant-provisioning-driver.ts) can be implemented for real. control-plane/'s own Worker has no D1 binding of its own — src/orb/broker.ts is 100% D1-bound — and there is no Worker-to-Worker service-binding precedent anywhere in this repo (confirmed: zero services: entries in any wrangler.jsonc). The established pattern to reuse instead is the one self-hosted containers already use: POST /v1/internal/orb/enrollments to mint an enrollment, POST /v1/orb/token to exchange it — the same two-step HTTP call, just from a different physical caller (control-plane's Worker instead of a self-hosted container).
Separately: provisionTenant (control-plane/src/provisioning.ts) already captures provisionDatabase's real connection details (#7653) into its own result, but currently discards them before calling injectSecrets — that function's own header comment already flags this as a known, deliberate gap left for this issue to close.
Area
control-plane/src/tenant-provisioning-driver.ts, control-plane/src/provisioning.ts, a new control-plane/src/secret-driver.ts (or similar name).
Proposal
Widen whatever's needed (TenantProvisioningRequest, or injectSecrets's own parameter list) so provisionTenant's already-captured database: DatabaseConnectionDetails actually reaches injectSecrets, instead of being silently dropped as it is today.
Implement a real secret driver mirroring the existing withRealDatabaseDriver/withRealContainerDriver composition pattern: injectSecrets calls the main app's admin-authenticated HTTP endpoints to store the tenant's DB credential under Add a tenant-DB-credential secret type + generic revoke path to src/orb/broker.ts #8064's new secret type; revokeSecrets calls its revoke path.
Never log, return in an error message, or otherwise surface the raw secret value outside the broker's own storage.
Deliverables
provisionTenant threads provisionDatabase's real connection details into injectSecrets.
control-plane/src/neon-database-driver.ts (the "real driver calls out over HTTP" shape to mirror)
control-plane/src/driver-factory.ts (withRealDatabaseDriver/withRealContainerDriver — the composition pattern to extend)
src/api/routes.ts (POST /v1/orb/token, POST /v1/internal/orb/enrollments — the existing routes to call)
Boundaries
Control-plane wiring only — does not implement the broker-side secret type/revoke mechanism itself (#8064, separate, blocking this one). Does not touch container creation (#7851, already shipped) or database provisioning (#7653, already shipped).
maintainer-only — handles real tenant secrets in transit, not a first-pass contributor task.
Problem
Split from #7852. Once #8064 lands (a real tenant-DB-credential secret type + revoke path on the main app's broker), control-plane's
TenantProvisioningDriver.injectSecrets/revokeSecrets(control-plane/src/tenant-provisioning-driver.ts) can be implemented for real.control-plane/'s own Worker has no D1 binding of its own —src/orb/broker.tsis 100% D1-bound — and there is no Worker-to-Worker service-binding precedent anywhere in this repo (confirmed: zeroservices:entries in anywrangler.jsonc). The established pattern to reuse instead is the one self-hosted containers already use:POST /v1/internal/orb/enrollmentsto mint an enrollment,POST /v1/orb/tokento exchange it — the same two-step HTTP call, just from a different physical caller (control-plane's Worker instead of a self-hosted container).Separately:
provisionTenant(control-plane/src/provisioning.ts) already capturesprovisionDatabase's real connection details (#7653) into its own result, but currently discards them before callinginjectSecrets— that function's own header comment already flags this as a known, deliberate gap left for this issue to close.Area
control-plane/src/tenant-provisioning-driver.ts,control-plane/src/provisioning.ts, a newcontrol-plane/src/secret-driver.ts(or similar name).Proposal
TenantProvisioningRequest, orinjectSecrets's own parameter list) soprovisionTenant's already-captureddatabase: DatabaseConnectionDetailsactually reachesinjectSecrets, instead of being silently dropped as it is today.withRealDatabaseDriver/withRealContainerDrivercomposition pattern:injectSecretscalls the main app's admin-authenticated HTTP endpoints to store the tenant's DB credential under Add a tenant-DB-credential secret type + generic revoke path to src/orb/broker.ts #8064's new secret type;revokeSecretscalls its revoke path.Deliverables
provisionTenantthreadsprovisionDatabase's real connection details intoinjectSecrets.injectSecrets/revokeSecretscalling the main app's broker HTTP endpoints (admin-token-authenticated, Add a tenant-DB-credential secret type + generic revoke path to src/orb/broker.ts #8064's new secret type).Resources
control-plane/src/neon-database-driver.ts(the "real driver calls out over HTTP" shape to mirror)control-plane/src/driver-factory.ts(withRealDatabaseDriver/withRealContainerDriver— the composition pattern to extend)src/api/routes.ts(POST /v1/orb/token,POST /v1/internal/orb/enrollments— the existing routes to call)Boundaries
Control-plane wiring only — does not implement the broker-side secret type/revoke mechanism itself (#8064, separate, blocking this one). Does not touch container creation (#7851, already shipped) or database provisioning (#7653, already shipped).
maintainer-only — handles real tenant secrets in transit, not a first-pass contributor task.