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
spec: an API-backed datasource's external block names a declared connector instance and borrows its credential (D7, ruling 6486136301) — epic #27261 P2 #27742
epic:#27261#1 · marchtian · session_017ihL2c5z3q4h8inrn5kwqV
Filing gate: ③ maintainer-directed — 田騏 at 2026-10-29T21:58Z 「现在启动全部 P2」 (epic comment 6509296853, D1 amended), at 2026-10-29T21:59Z 「OData 驱动 只做 v4」 (6509311454), at 2026-10-29T22:01Z 「同意」 (generic P2 parts open source in this repository; vendor-specific drivers such as Salesforce stay out of it).
Ruling-ref: 6486145005 (#27299, Tier B = declarative OData) · 6486136301 (#27298, D7) · 6471382887 (#27261 D1–D6)
Dedupe (open AND closed): "OData datasource driver $metadata import connector credential external datasource" → 5 hits, none this work (#27298 is the ruled decision card).
Reader: the epic PM (#27261) dispatches it in the epic subtree.
type: Feature
为什么: SAP / Dynamics 365 都用 OAuth2;一次授权让流程动作和虚拟对象读数共用,重连一次两边都恢复。这是 D7 裁决。
注意: 改已发布 spec,落地前需 Fable 完整复审与契约复审,Tier H 需您批准。
需要您做的: 合并前批准。
Task
One optional member of the datasource external block naming a connector instance (Metadata-protocol: added); refused at build when the instance is not declared; mutually exclusive with credentialsRef (or the precedence named and pinned).
ADR-0015 amendment note for D7, and §4 item 8 of the epic's design as amended (credentials through credentialsRef, or a declared connector instance for an API-backed datasource).
Execution identity unchanged: ADR-0143 Q1 = A (organization-shared); object permissions and RLS stay the only gate on what a user sees.
Clause-②: yes · Metadata-protocol: added (minor). Touches packages/spec/src/**: full Fable review and a CONTRACT_REVIEW_TIER record before landing; Tier H.
epic:#27261#1 · marchtian · session_017ihL2c5z3q4h8inrn5kwqV
Claim: PM loop round 8 2026-10-29T22:11Z
Session: session_017ihL2c5z3q4h8inrn5kwqV (epic PM); implementing card thread session_017ihL2eRfGhMmx9N4rdwNtG
Account: marchtian
Branch: claude/project-thread-15sb9m (the card thread's platform-assigned branch — measured platform exception to claude/issue-<n>-<slug>)
Worktree: objectstack-issue-27742
Domain: domain:spec
Seat: epic:#27261#1 (epic PM; no domain:* seat). Maintainer order, 田騏 2026-10-29T21:58Z: 「现在启动全部 P2」 (D7, ruling 6486136301, letter A)
File surface: packages/spec/src/data/datasource.zod.ts (one optional external member naming a connector instance) and the build-time reference check, their tests, docs/adr/0015-external-datasource-federation.md (the D7 amendment note), generated references the spec change re-records, .changeset/** (stop on breach; explain in the report)
Container & model: S, mode:thread, model: default tier (dispatch-gates --tier: no path-derived mandate), effort: high
Clause-②: yes
Metadata-protocol: added
Responsibility: ruling 6486136301 on #27298 (D7), filed by the maintainer's P2 start on epic #27261
Thread-read: none
Premise: holds — on origin/main a datasource's credentials come only from external.credentialsRef; no datasource key names a connector instance.
Serial constraints: #27746 (runtime seam) is Blocked-by this card. Contract face (published spec, Clause-②: yes, an ADR): the PR body says "Fable review owed"; it needs a full Fable review, a CONTRACT_REVIEW_TIER record PASS and the maintainer's approval (Tier H) before it lands.
{
"issue": 27742,
"status": "done",
"branch": "claude/project-thread-15sb9m",
"pr": "https://github.com/objectstack-ai/objectstack/pull/27783",
"session": "session_017ihL2eRfGhMmx9N4rdwNtG",
"premise_still_valid": true,
"summary": "ExternalDatasourceSettingsSchema gains optional `connector` (snake_case name of a declared connector instance whose credential an API-backed datasource borrows, ADR-0015 amendment D7 / ruling 6486136301). DatasourceSchema refuses it beside a bound credentialsRef (exclusive, not precedence), on a built-in DRIVER_VOCABULARY driver (prescribes credentialsRef) and on a managed plugin-driver datasource (prescribes schemaMode external); validateCrossReferences gains collectDatasourceConnectorErrors, refusing at defineStack / os validate (STACK_CROSS_REFERENCE_INVALID 422) a name with no connectors entry, an entry with no provider, or an instance with no auth / auth none. ADR-0015 gets a D7 amendment note answering the ruling's open reading (the (organization, connector instance) binding fits an environment-level datasource under #27230 S1: one organization per environment means exactly one connection; a no-organization read takes ADR-0143 D4's exactly-one rule, fail-closed otherwise). Liveness row `planned` (runtime half is #27746), credential-name ratchet allow-lists the key with its reason, changeset minor.",
"tests": "On eda26e3c under os-verify-lock: `pnpm --filter @objectstack/spec test` Test Files 756 passed (756), Tests 22468 passed | 1 todo, command-exit 0 (4m15s); `pnpm --filter @objectstack/spec typecheck` command-exit 0 (1m22s). New: src/stack-datasource-connector.test.ts (8 cases) and the external.connector block in src/data/datasource.test.ts (11 cases). Ablations via scripts/ablation-replace.mjs (mutation landed, restored, git diff HEAD empty): removing the collectDatasourceConnectorErrors call (blob c8cc7c644281 to e0bfdb0f2204) gives stack test 5 failed / 3 passed (controls green); disabling the parse-refusal guard (blob e0f177402a59 to 1090eb4caaf4) gives 4 failed / 7 passed. First full spec run caught the credential-name ratchet (metadata-credential-fields.test.ts) flagging datasource:external.connector; allow-listed with a reason, re-run green.",
"gates": "Local, eda26e3c (after one merge of origin/main): dispatch-gates --commands derived 111 families; 105 exit 0 first pass, 6 exit 3 (plugin-teardown fixture, lint build, built dists) each re-run exit 0 after its prerequisite; `dispatch-gates --ran`: 111 derived, 111 run, 0 NOT-MEASURED, 0 UNRUN. spec check:generated 14/14 up to date. PR check-runs: in_progress at report time (not waited, per contract).",
"dogfood_battery": "n/a — no `!` in the PR title and no (narrowing) arm",
"mcp_calls": "6 — mcp__github__issue_read x5 (#27742 body, #27742 comments x2, #27298 comments, #27230), mcp__github__pull_request_read x1 (#27658 body as a template); no write tool",
"api_writes": "2 relay writes as objectstack-fleet[bot]: pr_create (draft #27783, assignees marchtian mirrored from the card) and this os-dev-report comment; plus git push of the branch",
"open_questions": [],
"out_of_scope_findings": [
"carrier: #27746 · noted, not filed — no runtime reads external.connector until the runtime half lands; it should ship in the same release (liveness row planned, changeset says so)",
"carrier: #27746 · noted, not filed — a runtime-created (Studio) datasource never passes defineStack, so the instance-declared check must also run at the runtime's boot/save seams",
"carrier: epic PM (#27261) · noted, not filed — the epic body §4 item 8 amendment per the ruling is the epic PM's edit",
"carrier: PM (Skills-docs follow-up owed) · skills/objectstack-data/rules/datasources.md, content/docs/data-modeling/virtual-objects.mdx, content/docs/data-modeling/external-datasources.mdx still teach credentialsRef as the only channel; teach external.connector with or after #27746",
"carrier: none · noted, not filed — no scripts/adr-anchors file added (not on the claim's file surface); both refusal sites cite ADR-0015 D7 in comments"
]
}
PR #27783 merged through the queue as b373263195 on 2026-10-30T01:37:25Z (head 400e1b09; contract review PASS 6511230689 + delta PASS 6511651329 at CONTRACT_REVIEW_TIER, which also served as the full review of the spec and ADR change; seat ACCEPT 6511694932; Tier H APPROVED by os-zhuang). The datasource external block accepts connector, which names a declared connector instance to borrow its credential (D7). It is exclusive with credentialsRef and refused on built-in drivers and managed datasources. ADR-0015 carries the D7 note. Follow-ons: the runtime half #27746 (PR #27819, same release; it flips the liveness row to live), the composed counterpart #27803, and skills and docs #27786.
Activity
objectstack-fleet commentedon Oct 29, 2026
epic:#27261#1 · marchtian · session_017ihL2c5z3q4h8inrn5kwqV
Claim: PM loop round 8 2026-10-29T22:11Z
Session:
session_017ihL2c5z3q4h8inrn5kwqV(epic PM); implementing card threadsession_017ihL2eRfGhMmx9N4rdwNtGAccount:
marchtianBranch:
claude/project-thread-15sb9m(the card thread's platform-assigned branch — measured platform exception toclaude/issue-<n>-<slug>)Worktree:
objectstack-issue-27742Domain:
domain:specSeat:
epic:#27261#1(epic PM; nodomain:*seat). Maintainer order, 田騏 2026-10-29T21:58Z: 「现在启动全部 P2」 (D7, ruling 6486136301, letter A)File surface:
packages/spec/src/data/datasource.zod.ts(one optionalexternalmember naming a connector instance) and the build-time reference check, their tests,docs/adr/0015-external-datasource-federation.md(the D7 amendment note), generated references the spec change re-records,.changeset/**(stop on breach; explain in the report)Container & model:
S,mode:thread,model: default tier (dispatch-gates --tier: no path-derived mandate),effort: highClause-②: yes
Metadata-protocol: added
Responsibility: ruling 6486136301 on #27298 (D7), filed by the maintainer's P2 start on epic #27261
Thread-read: none
Premise: holds — on
origin/maina datasource's credentials come only fromexternal.credentialsRef; no datasource key names a connector instance.Serial constraints: #27746 (runtime seam) is Blocked-by this card. Contract face (published spec,
Clause-②: yes, an ADR): the PR body says "Fable review owed"; it needs a full Fable review, aCONTRACT_REVIEW_TIERrecord PASS and the maintainer's approval (Tier H) before it lands.objectstack-fleet commentedon Oct 29, 2026
os-dev-report
{ "issue": 27742, "status": "done", "branch": "claude/project-thread-15sb9m", "pr": "https://github.com/objectstack-ai/objectstack/pull/27783", "session": "session_017ihL2eRfGhMmx9N4rdwNtG", "premise_still_valid": true, "summary": "ExternalDatasourceSettingsSchema gains optional `connector` (snake_case name of a declared connector instance whose credential an API-backed datasource borrows, ADR-0015 amendment D7 / ruling 6486136301). DatasourceSchema refuses it beside a bound credentialsRef (exclusive, not precedence), on a built-in DRIVER_VOCABULARY driver (prescribes credentialsRef) and on a managed plugin-driver datasource (prescribes schemaMode external); validateCrossReferences gains collectDatasourceConnectorErrors, refusing at defineStack / os validate (STACK_CROSS_REFERENCE_INVALID 422) a name with no connectors entry, an entry with no provider, or an instance with no auth / auth none. ADR-0015 gets a D7 amendment note answering the ruling's open reading (the (organization, connector instance) binding fits an environment-level datasource under #27230 S1: one organization per environment means exactly one connection; a no-organization read takes ADR-0143 D4's exactly-one rule, fail-closed otherwise). Liveness row `planned` (runtime half is #27746), credential-name ratchet allow-lists the key with its reason, changeset minor.", "tests": "On eda26e3c under os-verify-lock: `pnpm --filter @objectstack/spec test` Test Files 756 passed (756), Tests 22468 passed | 1 todo, command-exit 0 (4m15s); `pnpm --filter @objectstack/spec typecheck` command-exit 0 (1m22s). New: src/stack-datasource-connector.test.ts (8 cases) and the external.connector block in src/data/datasource.test.ts (11 cases). Ablations via scripts/ablation-replace.mjs (mutation landed, restored, git diff HEAD empty): removing the collectDatasourceConnectorErrors call (blob c8cc7c644281 to e0bfdb0f2204) gives stack test 5 failed / 3 passed (controls green); disabling the parse-refusal guard (blob e0f177402a59 to 1090eb4caaf4) gives 4 failed / 7 passed. First full spec run caught the credential-name ratchet (metadata-credential-fields.test.ts) flagging datasource:external.connector; allow-listed with a reason, re-run green.", "gates": "Local, eda26e3c (after one merge of origin/main): dispatch-gates --commands derived 111 families; 105 exit 0 first pass, 6 exit 3 (plugin-teardown fixture, lint build, built dists) each re-run exit 0 after its prerequisite; `dispatch-gates --ran`: 111 derived, 111 run, 0 NOT-MEASURED, 0 UNRUN. spec check:generated 14/14 up to date. PR check-runs: in_progress at report time (not waited, per contract).", "dogfood_battery": "n/a — no `!` in the PR title and no (narrowing) arm", "mcp_calls": "6 — mcp__github__issue_read x5 (#27742 body, #27742 comments x2, #27298 comments, #27230), mcp__github__pull_request_read x1 (#27658 body as a template); no write tool", "api_writes": "2 relay writes as objectstack-fleet[bot]: pr_create (draft #27783, assignees marchtian mirrored from the card) and this os-dev-report comment; plus git push of the branch", "open_questions": [], "out_of_scope_findings": [ "carrier: #27746 · noted, not filed — no runtime reads external.connector until the runtime half lands; it should ship in the same release (liveness row planned, changeset says so)", "carrier: #27746 · noted, not filed — a runtime-created (Studio) datasource never passes defineStack, so the instance-declared check must also run at the runtime's boot/save seams", "carrier: epic PM (#27261) · noted, not filed — the epic body §4 item 8 amendment per the ruling is the epic PM's edit", "carrier: PM (Skills-docs follow-up owed) · skills/objectstack-data/rules/datasources.md, content/docs/data-modeling/virtual-objects.mdx, content/docs/data-modeling/external-datasources.mdx still teach credentialsRef as the only channel; teach external.connector with or after #27746", "carrier: none · noted, not filed — no scripts/adr-anchors file added (not on the claim's file surface); both refusal sites cite ADR-0015 D7 in comments" ] }objectstack-fleet commentedon Oct 30, 2026
epic:#27261#1 · marchtian · session_017ihL2c5z3q4h8inrn5kwqV
Landed · 2026-10-30T01:39Z
PR #27783 merged through the queue as
b373263195on 2026-10-30T01:37:25Z (head400e1b09; contract review PASS 6511230689 + delta PASS 6511651329 atCONTRACT_REVIEW_TIER, which also served as the full review of the spec and ADR change; seat ACCEPT 6511694932; Tier H APPROVED byos-zhuang). The datasourceexternalblock acceptsconnector, which names a declared connector instance to borrow its credential (D7). It is exclusive withcredentialsRefand refused on built-in drivers and managed datasources. ADR-0015 carries the D7 note. Follow-ons: the runtime half #27746 (PR #27819, same release; it flips the liveness row tolive), the composed counterpart #27803, and skills and docs #27786.