Skip to content

DroppedFieldsEvent.reason 只有 readonly / readonly_when 两值,写路径上新增的合法剥离对 onFieldsDropped / strictReadonlyWrites 不可见 #6437

Description

@baozhoutao

观察类发现(finding,不入队),来自 #6262 / PR #6433 的实施过程(PD #10)。不是今天用户会撞到的缺陷,是一处「声明的可观测面比实际剥离面窄」的漂移,记录下来免得只活在一条代码注释里。

事实

packages/spec/src/data/data-engine.zod.ts:228 起,DroppedFieldsEventSchema.reason 是闭合枚举:

reason: z.enum(['readonly', 'readonly_when'])

#3407 给这个 seam 的定位是通用的 —— 「写路径上被合法剥掉的、调用方提交过的字段」,因为调用方(典型是 flow 的 update_record 步骤)会逐字段汇报成功,而库里那一列根本没变(#4632 的二等形状:调用方以为落库了,数据库不同意,服务端日志是唯一痕迹)。#5126strictReadonlyWrites 是同一 seam 的响亮那一半:要么静默可观测,要么整笔拒绝。

PR #6433 在 update 的 multi 分支新增了一次剥离(把派发已裁定「不是主键」的 data.id 从 SET 载荷去掉)。它一次调用方提交过的、被引擎合法丢弃的字段,但它既不是 readonly 也不是 readonly_when,所以:

  • onFieldsDropped 监听器收不到这次剥离;
  • strictReadonlyWrites: true 的调用方不会因此被拒,它仍拿到一个成功返回。

PR #6433 里刻意没有硬塞进那两个值里(那会让 reason 说谎),改为记一条 warn,并把理由写在注释里:扩这个词表是 packages/spec 的改动,有 packages/spec/src/api/batch.zod.ts.../api/protocol.zod.ts 两处协议响应消费者,不该搭引擎修复的车。本 issue 就是那条注释的外化。

为什么标 finding 而不是入队

若将来处理,面在哪

  1. packages/spec/src/data/data-engine.zod.ts —— DroppedFieldsEventSchema.reason 枚举 + 其 describe;
  2. packages/spec/src/api/batch.zod.ts / packages/spec/src/api/protocol.zod.ts —— 三处 droppedFields 响应字段的消费者;
  3. packages/objectql/src/engine.ts —— update 的 reportDroppedFields 调用点(by-id 与 multi 各一组),以及 PR fix(objectql): multi update 的 SET 载荷剥掉非 id 的 data.id (#6262) #6433 新增剥离块里那段「刻意不上报」的注释(改了要一并删);
  4. 生成物:packages/spec 的 api-surface / JSON schema 基线随枚举变动重生成。

关联:#3407(onFieldsDropped 的由来)、#5126(strictReadonlyWrites)、#4632(二等形状)、#3042 / #2948(现有两个 reason)、#6262 / PR #6433(触发本条的新剥离)。

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions