Skip to content

[design] ADR-0104: field runtime value-shape as a first-class contract (spec-owned), typed action handlers, file-as-reference - #3412

Merged
os-zhuang merged 5 commits into
mainfrom
claude/field-value-shape-contract-1z4pil
Jul 24, 2026
Merged

[design] ADR-0104: field runtime value-shape as a first-class contract (spec-owned), typed action handlers, file-as-reference#3412
os-zhuang merged 5 commits into
mainfrom
claude/field-value-shape-contract-1z4pil

Conversation

@os-zhuang

Copy link
Copy Markdown
Contributor

纯设计文档:新增 docs/adr/0104-field-runtime-value-shape-contract.md(Status: Proposed),不含任何代码改动。

背景

#3405 / #3406(内联 lookup 参数的 reference.strip 静默吃掉)修掉的是一个键;这份 ADR 处理它背后的类问题:**字段的运行时值形状(value shape)在整个平台里不是任何人的契约。**代码盘点(全部带 file:line 证据,见 ADR 正文)发现:

  • 值形状知识在 4 处手工重复:record-validator.ts(私有 MULTI_CAPABLE_TYPES,单值 lookup / file / location 等完全不校验,line 341「opaque payloads」)、import-coerce.ts(6 份自己的类型集合)、driver-sql(JSON_COLUMN_TYPES / NUMERIC_SCALAR_TYPES)、verify/read-coercion.ts(只覆盖 3 个类型)。
  • spec 导出的 3 个值 schema 全部无人消费,其中 2 个与实际存储直接矛盾(CurrencyValueSchema{value,currency},实际存裸 number;LocationCoordinatesSchema{latitude,longitude},field-zoo 存 {lat,lng})——正是 ADR-0078 禁止的「导出但惰性」。
  • 动作参数声明(type/required/multiple/accept/maxSize)只喂给客户端弹窗;服务端 handleActions 原样透传 reqBody.params(http-dispatcher.ts:3882,MCP 路径同样),沙箱 input: unknown,handler 注册签名 (ctx: any) => any,现有 handler 全靠裸 as 强转。
  • 文件字段存无 schema 的内联 JSON blob({url,name,size}),完全绕开平台已有的 sys_file 一等文件原语(生命周期 GC、下载鉴权、稳定 /files/:fileId 解析器)——attachment-lifecycle.ts:27-29 自己就写着字段列的引用是 join-row 计数看不见的。后果:无引用完整性、清空字段永久泄漏 blob、非附件文件全部匿名 capability URL、FieldSchema 里连 accept/maxSize 都没有、client.storage.upload() 甚至拿不到 fileId(complete 响应把它丢了)。

决策概要

备注

🤖 Generated with Claude Code

https://claude.ai/code/session_01SHpGw3GBA9aFpfwVArRWfd


Generated by Claude Code

…ract
Design for three coupled gaps with one root cause (the runtime value shape
of a field is nobody's contract):
- D1: spec-owned valueSchemaFor(field) + semantic type classes; converge the
four hand-duplicated type lists (record-validator, import-coerce,
driver-sql, verify); reconcile the three dead value-schema exports; wire
the field-zoo oracle to the contract.
- D2: typed action handlers — declared params validated at REST/MCP dispatch,
typed ctx.params via FieldValue<T>, file params become fileId references.
- D3: file-as-reference — Field.file/image values store sys_file ids instead
of inline {url} blobs, joining the existing lifecycle/GC/authz machinery.
- D4: three-phase rollout (non-breaking convergence -> param enforcement ->
protocol-major file migration).
Generalizes the #3405/#3406 silently-stripped-param incident; relates #3407,
#1878/#1891.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01SHpGw3GBA9aFpfwVArRWfd
@vercel

vercelBot commented Jul 22, 2026

Copy link
Copy Markdown

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

ProjectDeploymentActionsUpdated (UTC)
specReadyReadyPreview, CommentJul 22, 2026 10:06pm

Request Review

@github-actionsgithub-actionsBot added documentation Improvements or additions to documentation size/m labels Jul 22, 2026
claude added 2 commits July 22, 2026 20:52
…get sections
Nine named risks (legacy-row stranding, warn-first rollout, unknown-key
allowlist, GC freeze during migration, public-posture inventory, sub-key
read breakage, external-URL retirement, cross-repo sequencing, spec purity)
and the performance budgets/benchmark gates for each phase, so the phase
PRs inherit them as acceptance items.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01SHpGw3GBA9aFpfwVArRWfd
@os-zhuang
os-zhuang merged commit 8eb2234 into mainJul 24, 2026
20 of 135 checks passed
@os-zhuang
os-zhuang deleted the claude/field-value-shape-contract-1z4pil branch July 24, 2026 11:28
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

documentationImprovements or additions to documentationsize/mtooling

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants

@os-zhuang@claude