Repository navigation
fix(service-automation): a connector credential written through the door reaches every replica - #27941
Conversation
… replicas (wip) Claude-Session: https://claude.ai/code/session_016WV4d1Ds3FbhoRdoBLGUvZ Co-authored-by: Claude <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016WV4d1Ds3FbhoRdoBLGUvZ Co-authored-by: Claude <noreply@anthropic.com>
…-m511py # Conflicts: # packages/services/service-automation/src/plugin.ts
📓 Docs Drift CheckThis PR changes 2 package(s): 5 hand-written doc(s) NAME something this change touched and may need an implementation-accuracy re-verification:
⛔ 3 release-owned page(s) also name something this change touched. These are read-only:
What this run could not see
Coarse fallback — 10 page(s) merely mention a changed package (the pre-#9192 predicate, kept for the deliberately-wide backstop): Which tree this was computed onThis run read A worktree cut from an older # while this PR is open — GitHub drops the merge commit once it closes
git fetch origin 57a7b229611cee9904d297a226cc34d318dfa18b && git checkout 57a7b229611cee9904d297a226cc34d318dfa18b
# afterwards, rebuild it from the two parents, which stay fetchable
git fetch origin ed0e71db94a73acc02512ff2ee0655106d02e585 8b40e4fa254306912fb197fe434a91157d9c7937 && git checkout -B drift-repro ed0e71db94a73acc02512ff2ee0655106d02e585 && git merge --no-ff 8b40e4fa254306912fb197fe434a91157d9c7937
node scripts/docs-audit/affected-docs.mjs --json ed0e71db94a73acc02512ff2ee0655106d02e585
|
|
domain:server#3 · os-elon-musk · session_016WV4czuTWNgKR22fKv7jia Seat ACCEPT · PR #27941 · head
|
Requested by Elon · project thread
Fixes #27428
Clause-②: no
Metadata-protocol: none
维护者速读
connector-credential.mutated,载荷{ originNode, ref });其它副本收到后跑自己的连接器对账,重读共享凭据行,被挂起的连接器随即恢复。packages/services/service-automation/src/plugin.ts(门的发布与收方对账)、packages/services/service-cluster/src/metadata-cluster-bridge-plugin.ts(第四条通道)、packages/services/service-automation/src/connector-credential-cluster.test.ts(双内核 pin)。pnpm --filter @objectstack/service-automation exec vitest run src/connector-credential-cluster.test.ts,预期 5 个用例全绿。What changes
PUT|DELETE /api/v1/automation/connectors/credential-refs/:ref) publishes{ originNode, ref }onconnector-credential.mutatedright afterstore.setsucceeds and afterstore.clearclears a row, then reconciles its own replica as before. Address only: no value, fingerprint or revision rides the channel. A refused write (400 / 403 / 404 / 409 / 503) publishes nothing. Best-effort and fire-and-forget, like lanes 2 and 3: a publish failure is logged atwarnand never fails the write.originNode, then runsreconcileDeclaredConnectorson its reconcile queue (materializeDeclaredConnectors(ctx, { fatal: false })), which re-reads the sharedsys_connector_credentialrows. The row's revision joins each instance's signature, so exactly the instances naming the changed reference re-materialize, held ones included; a cleared reference degrades them, naming it. It logs oneinfoline per peer write it follows.AutomationEngine.attachConnectorCredentialPubSub(pubsub, nodeId)delegates to the plugin's credential door (ConnectorCredentialDoor.attachClusterPubSub), idempotent on(pubsub, nodeId)and detached atdestroy(). The channel name and payload type live inconnector-credentials.ts; nothing new is exported from the package root.MetadataClusterBridgePlugin. Duck-typed against theautomationservice'sattachConnectorCredentialPubSub()beside lanes 1 to 3, skipped on the in-processmemorydriver, its own attach error and detach onkernel:shutdown.content/docs/kernel/cluster.mdx§6.2 gains the lane 4 row; the family's prose now says four lanes and names the credential rows as lane 4's source of truth.patchfor@objectstack/service-automationand@objectstack/service-cluster.Why
Ruling 6513279565 on #27428 (letter A, attached at A1): one new address-only lane of the §6.2 family, published by the credential door, received as a reconcile that re-reads the shared row, enumerated in the bridge with the other three lanes. Not a synthetic
metadata.mutated, no polling, no self-attach inside service-automation.Tests
packages/services/service-automation/src/connector-credential-cluster.test.ts(new): twoAutomationServicePluginkernels over ONE SQLite database and one shared bus that delivers to every subscriber, publisher included. Each replica is attached throughattachConnectorCredentialPubSub(), the seam the bridge calls.{ originNode, ref }with partition keyconnector-credential:REF, after a set and after a clear, and a refused write publishes nothing;packages/services/service-cluster/src/metadata-cluster-bridge-plugin.test.ts: six lane-4 cases (attach on a cross-process driver with the cluster's pubsub and node id, all four lanes together, skip onmemory, quiet skip with no service or no seam, a throwing attach that leaves lanes 1 to 3 up, detach on shutdown when the lane-3 detach throws).Acceptance notes
AutomationEnginegains one public method, the duck-typed seam. The claim'sClause-②: nois copied as written; the report asks the seat whether that method counts as a widened public surface.service-automation/src/plugin.ts; this diff keeps to the door's two publish lines, the receiver and the destroy line, so the later lander mergesmain.Verification
Head
f78a7f75.Red on the base, ablations, restore
origin/main8c7021df(the three source files restored from the base): 5/5 red,TypeError: engine.attachConnectorCredentialPubSub is not a function.scripts/ablation-replace.mjs(anchor hit 1 → 0, restored blob == HEAD,git diff HEADempty after each):Package suites and gates
pnpm --filter @objectstack/service-automation exec vitest run --maxWorkers=2: 219 files, 2808/2808 passed.pnpm --filter @objectstack/service-cluster test: 7 files, 111/111 passed;typecheckexit 0 for both packages.node scripts/pm/dispatch-gates.mjs --commands: 92 derived families, all run,--ranreconciliation "92 derived, 92 run, 0 NOT-MEASURED, 0 UNRUN". 89 exited 0 on the first pass; three first answered exit 3 (prerequisite) and exited 0 once it was met:check-plugin-teardown-shape --self-test(pinned commit fetched into the shallow clone),spec check:skill-examplesandcheck:dual-build-cjs-loads(after a whole-treeturbo run build).pnpm lint: exit 0.Generated by Claude Code