Skip to content

feat(spec)!: datasource 死键归零 —— 退役 retryPolicy / healthCheck / external 两键(#4583 批 B/C/D) - #4629

Merged
os-zhuang merged 1 commit into
mainfrom
claude/auth-gate-disconnect-issues-6wz8ew
Aug 2, 2026
Merged

feat(spec)!: datasource 死键归零 —— 退役 retryPolicy / healthCheck / external 两键(#4583 批 B/C/D)#4629
os-zhuang merged 1 commit into
mainfrom
claude/auth-gate-disconnect-issues-6wz8ew

Conversation

@os-zhuang

Copy link
Copy Markdown
Contributor

#4583批 B/C/D,也是最后一批。批 A(capabilities)已由 #4601 合并。

合并后 datasource 的活性账本死键归零 —— 它当初以 20 条 dead 被纳入治理,是所有受治理类型里比例最高的一个。

九个键,全部 remove 而非 enforce

不是因为"用得少",而是因为每一个都已经有另一套 live 机制在做它看起来在配置的那件事:

真正在工作的是什么
retryPolicy.{maxRetries,baseDelayMs,maxDelayMs,backoffMultiplier}连接失败走 datasource 连接服务的启动策略(降级启动 / bootCritical fail-fast)。它不按计划重试,所以 maxRetries: 5 从来没改变过任何行为
healthCheck.{enabled,intervalMs,timeoutMs}从来没有调度过探测循环,enabled: true 什么也没启用。存活是 driver handle 的 ping() / checkHealth()按需探测,Setup 的「测试连接」调的就是它
external.label联邦块从来没有自己的显示名,Setup 渲染的是顶层label。showcase 两个都声明了,现在只留会显示的那个
external.requirePermission没有任何鉴权检查读过它。联邦数据的访问由普通对象权限集 + RLS 管,和 managed datasource 完全一样。声明一个从不被要求的权限,正是 ADR-0049 要消除的假合规形状

retryPolicy 的报错刻意不提供改名建议

这是 #4488 点名的、这个类型里最险的一个陷阱,而它是命名碰撞而非行为疑问:

hook.retryPolicyjob.retryPolicy是真被强制执行的。但它们是另一个类型上的另一个键,延迟拼作 backoffMs,不是 baseDelayMs

而这个拼写不一致本身,就是"没人读 datasource 那个"的证据 —— 全仓没有任何代码同时读两种拼写。

所以:conversion 只碰 datasources,schema 的报错把这个区别讲清楚而不是给一个改名,并且有测试钉住报错文案必须同时包含backoffMshook/job。一条把作者引向"另一个类型的同名键"的处方,比没有处方更糟。

为什么是一个 commit 而不是三个

三批共用同一条 ADR-0087 conversiondatasource-inert-blocks-removed,多键移除的 house style,surface/ 承载四个子句)、同一份账本、同一行 README、同一批重新生成的产物 —— 拆开的话每个中间 commit 都过不了自己的闸门。三个 changeset 保留了 issue 要求的发布说明粒度。

conversion 里有一处值得看:external.* 是嵌套键,而 stripKeys 只处理顶层,所以 apply() 单独下钻一层并 copy-on-write(expectedNotices: 4,嵌套的两个也各算一条)。

验证

  • 四个新增拒绝测试retryPolicy / healthCheck / external.label / external.requirePermission 各自被拒;healthCheck 那条还断言报错提到 ping|checkHealth提到 checkIntervalMs(后者是唯一的周期性 datasource 定时器,检查的是schema 漂移而非存活,不能混淆)
  • 回归钉hook.retryPolicy / job.retryPolicy 仍正常 parse,showcase 的 jobs/hooks 未受影响
  • 全仓 pnpm build / test132/132 全绿)/ typecheck / lint
  • 七道闸门全绿:check:generatedcheck:livenesscheck:empty-statecheck:variant-docscheck:strictness-ledgercheck:i18ncheck-slot-lookup-ratchet
  • strictness 账本站点数 8 → 6,data/ 段 164 → 162
  • ⛔ 未触碰 content/docs/releases/

顺带修的两处

  • 一个测试写 external: { label: … } 只是为了让块非空 —— 现在写 external: {},说的就是它本来的意思。
  • CLI 的 lint-liveness-properties.test.ts 按设计跑在真实 shipped 账本上,所以每次删 datasource 账本行都会反转它的一条断言。它在批 A 和这一批各翻了一次,现在收敛成断言零发现,并保留作回归钉:将来若有人重新引入一个 dead+authorWarn 的 datasource 属性,会在这里红,而不是悄悄发出去。

收尾

这批合并后 #4583 四批全部完成,可以关闭。#4584(managed datasource 到底该不该有只读闸门)是批 A 里刻意不就地发明机制而留下的决策位 —— 照 #4479 的先例。


Generated by Claude Code

…nert keys (#4583 B/C/D)
The last nine dead properties on `datasource`, all authorWarn'd, none bridgeable —
each already had a DIFFERENT live mechanism doing the job it appeared to configure:
- `retryPolicy` (4 keys): no connect or query path retried on it. Connection
failure is the boot policy in the datasource connection service (degraded
boot / bootCritical fail-fast), which does not retry on a schedule.
- `healthCheck` (3 keys): nothing scheduled a probe, so `enabled` enabled
nothing. Liveness is probed ON DEMAND via the driver handle's ping() /
checkHealth(). Not to be confused with external.validation.checkIntervalMs,
the one recurring datasource timer, which checks SCHEMA DRIFT.
- `external.label`: the federation block never had a display name of its own;
Setup renders the top-level `label`.
- `external.requirePermission`: no authorization check consulted it. Federated
access is governed by ordinary object permission sets + RLS — naming a
permission that is never required is the false-compliance shape ADR-0049
removes.
The retryPolicy rejection deliberately does NOT offer a rename. hook.retryPolicy
and job.retryPolicy ARE enforced, but they are a different key on a different
type and spell the delay `backoffMs`, not `baseDelayMs` — and that inconsistency
is itself the evidence nothing read the datasource one, since no code reads both
spellings. #4488 named this the sharpest trap in the type; the prescription and a
test both pin it.
Committed as one change rather than three: B/C/D share a single ADR-0087
conversion (house style for multi-key removals — `surface` carries all four
clauses), one ledger, one README row and one set of regenerated artifacts, so
split commits would each fail their own gates. The three changesets keep the
release-note granularity the issue asked for.
Also fixes a test that used `external: { label: … }` only to make the block
non-empty — `external: {}` says what it meant.
datasource liveness ledger: 9 dead -> 0. It was seeded with 20, the highest dead
ratio of any governed type. Strictness-ledger site count 8 -> 6, data/ 164 -> 162.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01E5CYr5SDwe85gH2Jr5KSgu
@vercel

vercelBot commented Aug 2, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

1 Skipped Deployment
ProjectDeploymentActionsUpdated (UTC)
objectstackIgnoredIgnoredAug 2, 2026 12:18pm

Request Review

@os-zhuang
os-zhuang marked this pull request as ready for review August 2, 2026 12:18
@github-actionsgithub-actionsBot added documentation Improvements or additions to documentation protocol:data tests tooling labels Aug 2, 2026
@os-zhuang
os-zhuang enabled auto-merge August 2, 2026 12:18
@github-actions

Copy link
Copy Markdown
Contributor

📓 Docs Drift Check

This PR changes 1 package(s): @objectstack/spec.

107 hand-written doc(s) reference the affected code and may need an implementation-accuracy re-verification:

  • content/docs/ai/agents.mdx(via @objectstack/spec)
  • content/docs/ai/skills-reference.mdx(via @objectstack/spec)
  • content/docs/ai/skills.mdx(via @objectstack/spec)
  • content/docs/api/client-sdk.mdx(via @objectstack/spec)
  • content/docs/api/environment-routing.mdx(via @objectstack/spec)
  • content/docs/api/error-catalog.mdx(via @objectstack/spec)
  • content/docs/api/error-handling-client.mdx(via @objectstack/spec)
  • content/docs/api/error-handling-server.mdx(via @objectstack/spec)
  • content/docs/api/index.mdx(via @objectstack/spec)
  • content/docs/automation/approvals.mdx(via @objectstack/spec)
  • content/docs/automation/connectors.mdx(via @objectstack/spec)
  • content/docs/automation/flows.mdx(via @objectstack/spec)
  • content/docs/automation/hook-bodies.mdx(via packages/spec)
  • content/docs/automation/hooks.mdx(via @objectstack/spec)
  • content/docs/automation/index.mdx(via @objectstack/spec)
  • content/docs/automation/webhooks.mdx(via @objectstack/spec)
  • content/docs/automation/workflows.mdx(via @objectstack/spec)
  • content/docs/concepts/architecture.mdx(via @objectstack/spec)
  • content/docs/concepts/design-principles.mdx(via packages/spec)
  • content/docs/concepts/index.mdx(via @objectstack/spec)
  • content/docs/concepts/metadata-driven.mdx(via @objectstack/spec)
  • content/docs/concepts/metadata-lifecycle.mdx(via packages/spec)
  • content/docs/concepts/north-star.mdx(via packages/spec)
  • content/docs/data-modeling/analytics.mdx(via @objectstack/spec)
  • content/docs/data-modeling/drivers.mdx(via @objectstack/spec)
  • content/docs/data-modeling/external-datasources.mdx(via @objectstack/spec)
  • content/docs/data-modeling/field-types.mdx(via @objectstack/spec)
  • content/docs/data-modeling/fields.mdx(via @objectstack/spec)
  • content/docs/data-modeling/formulas.mdx(via @objectstack/spec)
  • content/docs/data-modeling/index.mdx(via @objectstack/spec)
  • content/docs/data-modeling/objects.mdx(via @objectstack/spec)
  • content/docs/data-modeling/queries.mdx(via @objectstack/spec)
  • content/docs/data-modeling/schema-design.mdx(via @objectstack/spec)
  • content/docs/data-modeling/seed-data.mdx(via @objectstack/spec)
  • content/docs/data-modeling/validation-rules.mdx(via @objectstack/spec)
  • content/docs/data-modeling/validation.mdx(via @objectstack/spec)
  • content/docs/deployment/cli.mdx(via @objectstack/spec)
  • content/docs/deployment/troubleshooting.mdx(via @objectstack/spec)
  • content/docs/deployment/validating-metadata.mdx(via @objectstack/spec)
  • content/docs/getting-started/build-with-claude-code.mdx(via @objectstack/spec)
  • content/docs/getting-started/common-patterns.mdx(via @objectstack/spec)
  • content/docs/getting-started/examples.mdx(via @objectstack/spec)
  • content/docs/getting-started/quick-reference.mdx(via @objectstack/spec)
  • content/docs/getting-started/quick-start.mdx(via @objectstack/spec)
  • content/docs/getting-started/your-first-project.mdx(via @objectstack/spec)
  • content/docs/kernel/cluster.mdx(via @objectstack/spec)
  • content/docs/kernel/contracts/auth-service.mdx(via packages/spec)
  • content/docs/kernel/contracts/cache-service.mdx(via packages/spec)
  • content/docs/kernel/contracts/data-engine.mdx(via @objectstack/spec)
  • content/docs/kernel/contracts/index.mdx(via @objectstack/spec)
  • content/docs/kernel/contracts/metadata-service.mdx(via packages/spec)
  • content/docs/kernel/contracts/storage-service.mdx(via packages/spec)
  • content/docs/kernel/index.mdx(via packages/spec)
  • content/docs/kernel/runtime-services/email-service.mdx(via packages/spec)
  • content/docs/kernel/runtime-services/index.mdx(via packages/spec)
  • content/docs/kernel/runtime-services/queue-service.mdx(via packages/spec)
  • content/docs/kernel/runtime-services/sharing-service.mdx(via packages/spec)
  • content/docs/kernel/runtime-services/sms-service.mdx(via packages/spec)
  • content/docs/kernel/runtime-services/storage-service.mdx(via packages/spec)
  • content/docs/kernel/services-checklist.mdx(via @objectstack/spec)
  • content/docs/kernel/services.mdx(via @objectstack/spec)
  • content/docs/permissions/authorization.mdx(via @objectstack/spec)
  • content/docs/permissions/permission-sets.mdx(via @objectstack/spec)
  • content/docs/permissions/permissions-matrix.mdx(via @objectstack/spec)
  • content/docs/permissions/positions.mdx(via @objectstack/spec)
  • content/docs/permissions/rls.mdx(via @objectstack/spec)
  • content/docs/permissions/sharing-rules.mdx(via @objectstack/spec)
  • content/docs/plugins/adding-a-metadata-type.mdx(via @objectstack/spec)
  • content/docs/plugins/development.mdx(via @objectstack/spec)
  • content/docs/plugins/index.mdx(via @objectstack/spec)
  • content/docs/plugins/packages.mdx(via @objectstack/spec)
  • content/docs/protocol/backward-compatibility.mdx(via @objectstack/spec)
  • content/docs/protocol/diagram.mdx(via packages/spec)
  • content/docs/protocol/kernel/config-resolution.mdx(via @objectstack/spec)
  • content/docs/protocol/kernel/i18n-standard.mdx(via @objectstack/spec)
  • content/docs/protocol/kernel/index.mdx(via @objectstack/spec)
  • content/docs/protocol/kernel/lifecycle.mdx(via @objectstack/spec)
  • content/docs/protocol/kernel/plugin-spec.mdx(via @objectstack/spec)
  • content/docs/protocol/kernel/runtime-capabilities.mdx(via @objectstack/spec)
  • content/docs/protocol/knowledge.mdx(via @objectstack/spec)
  • content/docs/protocol/objectql/index.mdx(via @objectstack/spec)
  • content/docs/protocol/objectql/query-syntax.mdx(via @objectstack/spec)
  • content/docs/protocol/objectql/schema.mdx(via @objectstack/spec)
  • content/docs/protocol/objectql/security.mdx(via packages/spec)
  • content/docs/protocol/objectql/state-machine.mdx(via @objectstack/spec)
  • content/docs/protocol/objectui/actions.mdx(via @objectstack/spec)
  • content/docs/protocol/objectui/concept.mdx(via @objectstack/spec)
  • content/docs/protocol/objectui/index.mdx(via @objectstack/spec)
  • content/docs/protocol/objectui/layout-dsl.mdx(via @objectstack/spec)
  • content/docs/protocol/objectui/record-alert.mdx(via @objectstack/spec)
  • content/docs/protocol/objectui/widget-contract.mdx(via @objectstack/spec)
  • content/docs/releases/implementation-status.mdx(via @objectstack/spec)
  • content/docs/releases/index.mdx(via @objectstack/spec)
  • content/docs/releases/v12.mdx(via @objectstack/spec)
  • content/docs/releases/v13.mdx(via @objectstack/spec)
  • content/docs/releases/v16.mdx(via @objectstack/spec)
  • content/docs/releases/v17.mdx(via @objectstack/spec)
  • content/docs/releases/v9.mdx(via @objectstack/spec)
  • content/docs/ui/actions.mdx(via @objectstack/spec)
  • content/docs/ui/create-vs-edit-form.mdx(via @objectstack/spec)
  • content/docs/ui/dashboards.mdx(via @objectstack/spec)
  • content/docs/ui/forms.mdx(via @objectstack/spec)
  • content/docs/ui/index.mdx(via @objectstack/spec)
  • content/docs/ui/public-data-collection.mdx(via @objectstack/spec)
  • content/docs/ui/setup-app.mdx(via @objectstack/spec)
  • content/docs/ui/translations.mdx(via @objectstack/spec)
  • content/docs/ui/views.mdx(via @objectstack/spec)

Advisory only. To re-verify, run the docs-accuracy-audit workflow scoped to these files:
node scripts/docs-audit/affected-docs.mjs origin/main → pass the list as args.docs.

Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

documentationImprovements or additions to documentationprotocol:datasize/mteststooling

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants

@os-zhuang@claude