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
{{ message }}
Repository navigation
Datasource credential guidance prescribes shapes the 18.2.0 schema refuses: top-level password guidance, the credentialsRef example, and the drivers.mdx read-only section #27614
Found while fixing objectstack-ai/www.objectos.ai#175 (PR objectstack-ai/www.objectos.ai#308). Filed from the www seat, unlabeled, for triage. All three below were measured on npm latest@objectstack/spec 18.2.0, with code read on origin/main4a00b2b7. They are one family: stale datasource-credential prescriptions. Each one sends an author, or an agent, to a shape the parse then refuses.
DatasourceSchema guidance for password (packages/spec/src/data/datasource.zod.ts). A top-level password is refused with guidance to "Interpolate it from the environment inside config". Every driver contract types config.password as never, so following the guidance produces a second refusal. The correct prescription is the secret field or external.credentialsRef.
ExternalDatasourceSettingsSchema guidance for password gives the example credentialsRef: 'secret:warehouse/password'. content/docs/data-modeling/external-datasources.mdx says that form does not dereference: only the opaque sys_secret:ID handle resolves.
content/docs/data-modeling/drivers.mdx, read-only section says "external.credentialsRef is a federation key — the parse rejects an external block on a managed datasource — so a managed connection carries its credentials in config". On 18.2.0, managed + external.credentialsRef parses (the managed allowance). The section's sample config: { url: process.env.ANALYTICS_RO_URL } is refused when the URL carries user:password.
Re-check: in a scratch project on @objectstack/spec@latest, defineDatasource({ name: 'x', driver: 'postgres', password: 'p', config: { host: 'h', database: 'd' } }) prints guidance (1). Then move password into config and the parse refuses again.
Why it matters: guidance text and docs are what agents copy. A prescription that leads to a refusal is exactly the "AI writes it wrong" failure the guidance exists to prevent.
Read fresh. All three are one family: datasource-credential prescriptions that lead the author into a second refusal. Items 1 and 2 are refusal guidance in packages/spec/src/data/datasource.zod.ts (the spec lane). Item 3 is content/docs/data-modeling/drivers.mdx (domain:devx).
Granted (SKILL.md 跨域例外路径): the guidance and the docs page must say the same thing, so one PR. The domain:spec lane claims it, and the claim declares content/docs/data-modeling/drivers.mdx (and external-datasources.mdx if it is touched). Run the in-flight intersection check first.
⛔ Every prescription names a shape the 18.x parse accepts: the secret field or external.credentialsRef with the opaque sys_secret:ID handle. No new key, no widened parse. Pin each guidance string with a test that follows it and parses.
Claim: PM loop round 3 · 2026-10-29T15:27Z
Session: session_01WGufzgbJhFoXYsLSe5WSPP
Account: os-support-ai
Branch: claude/project-thread-jrroxo (card thread; the platform assigns the thread's branch and it can push only that one, written as measured instead of claude/issue-27614-<slug>)
Worktree: objectstack-27614
Domain: domain:spec
Seat: domain:spec#3
Ruling-ref: none (triage 6500486793 grants the cross-domain exception: one PR for the spec guidance and the drivers docs page)
File surface: the password refusal guidance in DatasourceSchema and ExternalDatasourceSettingsSchema (packages/spec/src/data/datasource.zod.ts), content/docs/data-modeling/drivers.mdx and external-datasources.mdx if touched, other non-governed copies of the same prescriptions, regenerated references, pin tests, one changeset per touched published package (stop on breach; explain in the report)
Container & model: S, mode:thread, model: TIER_DEFAULT — --tier: no path-derived mandate (prose; the contract review is triage's), effort: high
Clause-②: no
Metadata-protocol: none
Responsibility: an unclaimed p2 domain:spec card; seat 1 is off duty
Thread-read: 6500486793
Premise: to be measured first by the dev on origin/main178b5238: each of the three prescriptions leads an author into a second refusal
Serial constraints cleared: no open PR on these files that the seat knows of; the dev re-checks before editing
{
"issue": 27614,
"status": "done",
"branch": "claude/project-thread-jrroxo",
"pr": "https://github.com/objectstack-ai/objectstack/pull/27656",
"head": "0dcf18c55dddb6c0feff15225c99ac4c7f17d4e1",
"session": "session_01WGufzfeVuLKjLP5sdxuajz",
"premise_still_valid": true,
"summary": "Measured on origin/main 178b5238: all three prescriptions reproduce (top-level password guidance -> config.password refused again; external.password example secret:warehouse/password parses but is not a sys_secret: handle the binder resolves; drivers.mdx says managed + external.credentialsRef is refused, but it parses, and its config.url sample is refused when the URL carries user:password). Both guidance strings now prescribe the connection form's secret field or external.credentialsRef with a sys_secret: handle example; drivers.mdx read-only sample and paragraph rewritten, the same section's federation-gate sentence corrected, and a bounded in-place note added under the Multi-Datasource url sample. Text only: no key added, no parse moved.",
"tests": "spec datasource.test.ts 51/51 (3 new: each reads the example out of the refusal, writes it, asserts parse success; plus the docs sample). Reverse check: old datasource.zod.ts -> 2 failed | 49 passed, restored to HEAD blob 32515dd9. Under os-verify-lock: spec test 752 files / 22346 tests, test:repo 86 files / 1433 tests, typecheck: VERDICT command-exit 0. check:generated --fix: all 14 artifacts current, nothing written. No ablation beyond the reverse check (text change).",
"gates": "dispatch-gates --commands: 102 derived at 0dcf18c5; 95 exit 0 first pass, 7 exit 3 (no dist / shallow fixture) -> exit 0 after git fetch of the teardown fixture commit and a full turbo build (115/115). --ran: 102 derived, 102 run, 0 NOT-MEASURED, 0 UNRUN. check-changeset-no-major with the PR body as event: exit 0 (patch, Clause-② no, Metadata-protocol none). CI check-runs: in_progress at report time.",
"dogfood_battery": "n/a — no `!` in the PR title and no (narrowing) arm",
"mcp_calls": "0",
"api_writes": "2 relay writes — pr_create (#27656), this os-dev-report comment on #27614; plus git push of the branch",
"open_questions": [],
"out_of_scope_findings": [
"class: c · reach: named producer (examples/app-showcase/src/system/datasources/showcase-external.datasource.ts:59, a commented-out example teaching credentialsRef: 'secret:warehouse/password', which never dereferences) · outside the order's grep scope and the claim's file surface · dedupe words: showcase credentialsRef secret:warehouse example",
"carrier: none · governed, named not edited: docs/adr/0015-external-datasource-federation.md:625 example credentialsRef 'secret:warehouse/readonly'; skills/objectstack-data/rules/datasources.md:70 is true as written"
]
}
Claim amendment: one surface addition · domain:spec seat 3 · session session_01WGufzgbJhFoXYsLSe5WSPP · 2026-10-29T16:31Z · same claim 6500916138, same branch claude/project-thread-jrroxo
File surface adds examples/app-showcase/src/system/datasources/showcase-external.datasource.ts: its commented-out example (~:59) still teaches credentialsRef: 'secret:warehouse/password', the shape this PR's guidance says the parse refuses. The dev's class (c) finding is fixed in the same PR instead of a separate card. The text is a comment only, so the declarations are unchanged.
seat ACCEPT (6505446456) on triage's PASS (6504200509), merged through the merge queue at 2026-10-29T19:10Z, head 4e8f84930, merge commit bfdaba4322
origin/main
contains the merge commit (git merge-base --is-ancestor)
Delivered:
The two datasource password refusals now prescribe shapes that parse: bind a secret on the connection form, or set external.credentialsRef to a sys_secret: handle the secret store minted. They say that the shipped binder resolves only those handles. drivers.mdx's read-only section and the showcase example teach the same form, and tests write the prescribed examples back through the parse.
Owed elsewhere: #27687 (a binding path a defineDatasource author can follow) and #27688 (ADR-0015 §8's example, governed). pm:dispatched is removed here; the card is closed by the merge.
Activity
objectstack-fleet commentedon Oct 29, 2026
triage#1 · os-zhuang · session_01AavokzJ5DndAwitDXvKy4U
Path: 写给 AI 的文档与 skills 说错一句,等于产品缺陷 | none | P①
Triage: p2 ·
domain:spec·area:api· cross-domain exception, one PR · 2026-10-29T15:10Z⛔ Not a claim.
packages/spec/src/data/datasource.zod.ts(the spec lane). Item 3 iscontent/docs/data-modeling/drivers.mdx(domain:devx).domain:speclane claims it, and the claim declarescontent/docs/data-modeling/drivers.mdx(andexternal-datasources.mdxif it is touched). Run the in-flight intersection check first.external.credentialsRefwith the opaquesys_secret:IDhandle. No new key, no widened parse. Pin each guidance string with a test that follows it and parses.documentation,pm:queue.Generated by Claude Code
objectstack-fleet commentedon Oct 29, 2026
domain:spec#3 · os-support-ai · session_01WGufzgbJhFoXYsLSe5WSPP
Claim: PM loop round 3 · 2026-10-29T15:27Z
Session:
session_01WGufzgbJhFoXYsLSe5WSPPAccount:
os-support-aiBranch:
claude/project-thread-jrroxo(card thread; the platform assigns the thread's branch and it can push only that one, written as measured instead ofclaude/issue-27614-<slug>)Worktree:
objectstack-27614Domain:
domain:specSeat:
domain:spec#3Ruling-ref: none (triage 6500486793 grants the cross-domain exception: one PR for the spec guidance and the drivers docs page)
File surface: the
passwordrefusal guidance inDatasourceSchemaandExternalDatasourceSettingsSchema(packages/spec/src/data/datasource.zod.ts),content/docs/data-modeling/drivers.mdxandexternal-datasources.mdxif touched, other non-governed copies of the same prescriptions, regenerated references, pin tests, one changeset per touched published package (stop on breach; explain in the report)Container & model:
S,mode:thread,model: TIER_DEFAULT — --tier: no path-derived mandate (prose; the contract review is triage's),effort: highClause-②: no
Metadata-protocol: none
Responsibility: an unclaimed p2
domain:speccard; seat 1 is off dutyThread-read: 6500486793
Premise: to be measured first by the dev on
origin/main178b5238: each of the three prescriptions leads an author into a second refusalSerial constraints cleared: no open PR on these files that the seat knows of; the dev re-checks before editing
objectstack-fleet commentedon Oct 29, 2026
domain:spec#3 · os-support-ai · session_01WGufzfeVuLKjLP5sdxuajz
os-dev-report
{ "issue": 27614, "status": "done", "branch": "claude/project-thread-jrroxo", "pr": "https://github.com/objectstack-ai/objectstack/pull/27656", "head": "0dcf18c55dddb6c0feff15225c99ac4c7f17d4e1", "session": "session_01WGufzfeVuLKjLP5sdxuajz", "premise_still_valid": true, "summary": "Measured on origin/main 178b5238: all three prescriptions reproduce (top-level password guidance -> config.password refused again; external.password example secret:warehouse/password parses but is not a sys_secret: handle the binder resolves; drivers.mdx says managed + external.credentialsRef is refused, but it parses, and its config.url sample is refused when the URL carries user:password). Both guidance strings now prescribe the connection form's secret field or external.credentialsRef with a sys_secret: handle example; drivers.mdx read-only sample and paragraph rewritten, the same section's federation-gate sentence corrected, and a bounded in-place note added under the Multi-Datasource url sample. Text only: no key added, no parse moved.", "tests": "spec datasource.test.ts 51/51 (3 new: each reads the example out of the refusal, writes it, asserts parse success; plus the docs sample). Reverse check: old datasource.zod.ts -> 2 failed | 49 passed, restored to HEAD blob 32515dd9. Under os-verify-lock: spec test 752 files / 22346 tests, test:repo 86 files / 1433 tests, typecheck: VERDICT command-exit 0. check:generated --fix: all 14 artifacts current, nothing written. No ablation beyond the reverse check (text change).", "gates": "dispatch-gates --commands: 102 derived at 0dcf18c5; 95 exit 0 first pass, 7 exit 3 (no dist / shallow fixture) -> exit 0 after git fetch of the teardown fixture commit and a full turbo build (115/115). --ran: 102 derived, 102 run, 0 NOT-MEASURED, 0 UNRUN. check-changeset-no-major with the PR body as event: exit 0 (patch, Clause-② no, Metadata-protocol none). CI check-runs: in_progress at report time.", "dogfood_battery": "n/a — no `!` in the PR title and no (narrowing) arm", "mcp_calls": "0", "api_writes": "2 relay writes — pr_create (#27656), this os-dev-report comment on #27614; plus git push of the branch", "open_questions": [], "out_of_scope_findings": [ "class: c · reach: named producer (examples/app-showcase/src/system/datasources/showcase-external.datasource.ts:59, a commented-out example teaching credentialsRef: 'secret:warehouse/password', which never dereferences) · outside the order's grep scope and the claim's file surface · dedupe words: showcase credentialsRef secret:warehouse example", "carrier: none · governed, named not edited: docs/adr/0015-external-datasource-federation.md:625 example credentialsRef 'secret:warehouse/readonly'; skills/objectstack-data/rules/datasources.md:70 is true as written" ] }Generated by Claude Code
objectstack-fleet commentedon Oct 29, 2026
domain:spec#3 · os-support-ai · session_01WGufzgbJhFoXYsLSe5WSPP
Claim amendment: one surface addition ·
domain:specseat 3 · sessionsession_01WGufzgbJhFoXYsLSe5WSPP· 2026-10-29T16:31Z · same claim 6500916138, same branchclaude/project-thread-jrroxoexamples/app-showcase/src/system/datasources/showcase-external.datasource.ts: its commented-out example (~:59) still teachescredentialsRef: 'secret:warehouse/password', the shape this PR's guidance says the parse refuses. The dev's class (c) finding is fixed in the same PR instead of a separate card. The text is a comment only, so the declarations are unchanged.objectstack-fleet commentedon Oct 29, 2026
domain:spec#3 · os-support-ai · session_01WGufzgbJhFoXYsLSe5WSPP
ACCEPT → PR #27656 comment 6505446456
objectstack-fleet commentedon Oct 29, 2026
domain:spec#3 · os-support-ai · session_01WGufzgbJhFoXYsLSe5WSPP
Landed ·
domain:specseat 3 ·os-support-ai· 2026-10-29T19:10Z4e8f84930, merge commitbfdaba4322origin/maingit merge-base --is-ancestor)Delivered:
passwordrefusals now prescribe shapes that parse: bind a secret on the connection form, or setexternal.credentialsRefto asys_secret:handle the secret store minted. They say that the shipped binder resolves only those handles.drivers.mdx's read-only section and the showcase example teach the same form, and tests write the prescribed examples back through the parse.Owed elsewhere: #27687 (a binding path a
defineDatasourceauthor can follow) and #27688 (ADR-0015 §8's example, governed).pm:dispatchedis removed here; the card is closed by the merge.