Repository navigation
docs(skills): name the ctx.email.send and ctx.activity.append body doors in the data-hooks reference - #33078
Conversation
…ors in the data-hooks reference The sandbox ctx table and the capability list name both doors; a hook body cannot be granted email.send, and an activity entry commits or rolls back with the write that runs the body. Growth paid by same-file restatement cuts. Co-Authored-By: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01L9qibzqxVnBg8FjZXM1fQu
|
domain:skills#2 · os-tesla · session_01L9qibvXzthnUYrxzphgFgW Contract reviewServed-tier: PR #33078 for card #33033, rules face ( ① Derived judgments
② Semver level
③ Boundary flags
④ Design judgment
Deleted lines:
Tried to break it:
Findings:
No must-fix. S1 and S2 each earn a delta review of their fix by this reviewer. N1 to N3 need none. Implemented-by: VERDICT: PASS |
…tion refusals; async bullet drops mail Review r1 S1/S2 and N1: the activity.append row says type is the app's own value (a SYS_ACTIVITY_PLATFORM_TYPES value is 403 and aborts the write under onError abort) and that the call stays outside ctx.api.transaction (409). The async bullet no longer suggests mail from a hook. The changeset carries the two declaration lines. Growth paid by cutting the What Are Hooks bullet list, which restates the Before vs After table. Co-Authored-By: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01L9qibzqxVnBg8FjZXM1fQu
|
domain:skills#2 · os-tesla · session_01L9qibvXzthnUYrxzphgFgW Contract reviewServed-tier: Delta review, round 2, of PR #33078 for card #33033. This head is one commit on top of ① Derived judgments
② Semver level
③ Boundary flags
④ Design judgment
Tried to break the moved text:
Round 1 nits N2 and N3 are unchanged text and stay as recorded. No new finding. No must-fix and no should-fix. The round ends here. Implemented-by: VERDICT: PASS |
|
domain:skills#2 · os-tesla · session_01L9qibvXzthnUYrxzphgFgW 席位核对 · ACCEPT · 2026-11-13T10:11ZHead-sha:
|
Requested by Tesla · project thread
Fixes #33033
Clause-②: no
Metadata-protocol: none
维护者速读
objectstack-data技能的data-hooks.md现在点名 feat(runtime): a script body sends mail and adds a timeline entry through platform doors that stamp who sent it #32966 发布的两个脚本体入口:沙箱ctx表加ctx.email/ctx.activity两行,「Capabilities — the complete list」加email.send/activity.append两行,并把过时的「exactly five」改为「exactly seven」(HookBodyCapability在 main 上是七个值)。email.send(解析与绑定时拒收),记录变更时的邮件走 action、job 或 flow;activity.append随运行脚本体的那次写入一起提交或回滚;type只能用应用自己的值(平台类型 403 拒收),且不得在ctx.api.transaction内调用(409)。另把「async 钩子用于发邮件」改为「发通知」,免得与新规则矛盾。skills/objectstack-data/references/data-hooks.md第 355–356 行(ctx表两行)、第 426–436 行(能力表两行 + seven),第 197 行(async 用途)。node scripts/check-skills-token-ratchet.mjs | grep data-hooks,预期10007 / 10011且退出 0。skills/**(Tier H)。契约复审在现 head 已 PASS(r1 评论 6849613993,r2 增量 6849985798,Head-shadc05d1b0a91dd4c9d89f6fe6b558114e54f03818),请以 os-zhuang 批准。⛔ 18.4.0 合并冻结中([sweep] v18.4.0 release test sweep #32908 6848983225):本 PR 带 changeset,批准后请勿入队,席位在解冻后落地。What changes
ctxtable:ctx.email({ send }, gated byemail.send, not in a hook body) andctx.activity({ append }, gated byactivity.append).HookBodyCapabilityonmainb232220 listsapi.read,api.write,api.transaction,crypto.uuid,log,email.send,activity.append), plus two rows:email.send:ctx.email.send({ to, subject, text }), mail via the mail service with sender, user and organization stamped (BodyMailSendInputSchema); not in a hook body, refused at parse and at bind, because a message cannot be taken back if the hook's write rolls back; mail on a record change goes through an action, a job or a flow.activity.append:ctx.activity.append({ object, recordId, type, summary }), one record-timeline entry with actor and origin stamped (BodyActivityAppendInputSchema); commits or rolls back with the write that runs the body.typeis the app's own, never aSYS_ACTIVITY_PLATFORM_TYPESvalue (403PERMISSION_DENIED, aborting the write underonError: 'abort'), and the call is never made insidectx.api.transaction(409RESOURCE_CONFLICT).asyncsection: "Sending emails/notifications" → "Sending notifications", so no line sends an author to mail from a hook.mainb232220:packages/spec/src/data/hook-body-doors.zod.ts(both input schemas and their descriptions),packages/spec/src/data/hook-body.zod.ts(HookBodyCapabilityJSDoc),packages/spec/src/data/hook.zod.tsrefuseHookBodyMailGrant(parse-side refusal; its block comment names the bind-side refusal inhookBodyRunnerFactory),content/docs/automation/hook-bodies.mdxrows for both doors,content/docs/kernel/runtime-services/email-service.mdx. The skill text claims nothing those do not say; the required input keys named are the schema's required keys (textstands for "textorhtml").bodyvshandlertable's "Ships as" row and the paragraph after the table ("Because abodyis pure metadata …") — both restate the Shape/Status rows and the section intro;wherequery shape and theupdate({ id, … })pattern" — the linked section already titles both;ctxtable;api.read/api.write" sentence — the callout at the top of the same## Hook Context APIsection links the sandbox section, and the capability table states the tokens.Tests
Teaching text only; no tested behaviour changed, so no ablation.
Acceptance notes
skills/**):skills/objectstack-data/references/data-hooks.mdlines 953 → 943, tokens 9987 → 10007 (ceiling 10011) at head dc05d1b.Verification
Gates: CI on dc05d1b 44 check-runs, 28 success, 16 skipped, 0 failed; local derived list at e7336ef, skill-text gates re-run on dc05d1b
node scripts/pm/dispatch-gates.mjs --commands(45 commands) pluspnpm check:changeset-fixed(roster under.changeset, flagged by the derivation).@objectstack/lint...built first forcheck:doc-formula-expressions.mainb232220 merged before opening: no-op. Skill-text gates re-run on e7336ef, each exit 0:check-skills-token-ratchet(10007 / 10011), speccheck:skill-refs, speccheck:skill-docs,check:skill-identifier-liveness,check:skill-links.check:skill-refs/check:skill-docs, skill identifier liveness, skill links, doc authoring, changeset gates, closing-keyword parity, …).check:dual-build-cjs-loads,check:lean-entry-closure. The diff is one markdown file and a changeset, which cannot move built dists; CI'sBuild Coreran both on dc05d1b: success.Generated by Claude Code
🤖 Generated with Claude Code
https://claude.ai/code/session_01L9qibzqxVnBg8FjZXM1fQu