From 5dd33ddd0142131fd30b43bbcec7d749ec4285b1 Mon Sep 17 00:00:00 2001 From: Claude Date: Mon, 17 Aug 2026 07:32:32 +0000 Subject: [PATCH] docs(data): accept-and-document mongo/turso passthrough secrets with no binder slot Adds a "Secret-shaped keys with no binder slot: accepted at-rest risk" subsection to the database drivers guide, naming the five keys the datasource secret binder has no slot for -- mongo's options.proxyPassword, options.tlsCertificateKeyFilePassword, options.key, options.passphrase, and turso's encryptionKey. States plainly that they are writable and stored at rest in sys_metadata as plain text, that read-side redaction (#9040, shipped) is the only protection today, and records the restart condition: the first real deployment needing an authenticated SOCKS5 proxy or a passphrase- protected key converts this into the binder-slot programme (Option A). Maintainer ruling 2026-08-17 03:19Z (issue comment 5311378700): Option B, accept-and-document. No runtime code changed; Option A (binder slots) and Option C (publish-door refusal) stay explicitly out of scope. Fixes #9124 --- content/docs/data-modeling/drivers.mdx | 40 ++++++++++++++++++++++++++ 1 file changed, 40 insertions(+) diff --git a/content/docs/data-modeling/drivers.mdx b/content/docs/data-modeling/drivers.mdx index af27d75d9b..dd077ec253 100644 --- a/content/docs/data-modeling/drivers.mdx +++ b/content/docs/data-modeling/drivers.mdx @@ -164,6 +164,46 @@ which the Studio connection form renders — so the form offers exactly the fiel the validator accepts. +### Secret-shaped keys with no binder slot: accepted at-rest risk + +The datasource secret binder injects exactly **one** secret per datasource — +the login password, resolved through `external.credentialsRef` (or the +connection form's password field) into `sys_secret` at connect time. A small +number of other config keys are secret-shaped too, but the binder has no +second slot to put them in, and the client library that owns them — not +ObjectStack — is what makes them secrets: + +| Driver | Key | What it carries | +| :--- | :--- | :--- | +| `mongo` \| `mongodb` | `options.proxyPassword` | SOCKS5 proxy password | +| `mongo` \| `mongodb` | `options.tlsCertificateKeyFilePassword` | TLS key-file passphrase | +| `mongo` \| `mongodb` | `options.key` | TLS private key material (PEM) | +| `mongo` \| `mongodb` | `options.passphrase` | TLS key passphrase | +| `turso` \| `libsql` | `encryptionKey` | AES-256 key for the local database file | + +Unlike `password` / `authToken` (typed `never` in their schemas — the parse +refuses them outright), these five keys are **writable**: the parse accepts +them, and they are stored **at rest in `sys_metadata` as plain text**, right +alongside the rest of the datasource row. The protection that exists today is +on the READ side only — every one of them is stripped before a datasource +record is ever served back over the admin API or shown in the Setup UI +(`PASSTHROUGH_SECRET_PATHS` / `STILL_WRITABLE_CREDENTIAL_KEYS` in +`datasource-credential-redaction.ts`, shipped in +[#9040](https://github.com/objectstack-ai/objectstack/issues/9040)). That stops the value +round-tripping through a read; it is not encryption at rest, and an operator +with direct access to the metadata store can still read the plain-text value. + + +**This is a deliberate, documented trade-off ([#9124](https://github.com/objectstack-ai/objectstack/issues/9124)), not an oversight.** +The binder has exactly one named slot. Refusing these five keys at write time +would remove the only way to configure an authenticated SOCKS5 proxy or a +passphrase-protected TLS key — a capability the client genuinely honours, with +no working refusal remedy. **Restart condition:** the first real deployment +that needs an authenticated proxy or a passphrase-protected key converts this +into named binder-slot support — one mechanism covering all five keys — rather +than the current per-key accept-and-document posture. + + ## Startup: a driver that cannot connect aborts the boot `ObjectQLEngine.init()` connects every registered driver during kernel