Repository navigation
Commit 178b523
fix(app-shell): Studio API tab example body leaves out owner_id and optional references (#27613)
<!-- claude-projects-attribution: {"github_login":"os-bill"} -->
_Requested by **Bill** · [project
thread](https://claude.ai/code/project/chan_016iMXWSZDzqWRWvWzdNo8wg?thread=cmsg_016iMXWSZDzqWRWvWzdNo8wgDiLk5zdcKrMuPQwcCm6WjS)_
## 维护者速读
- 改了什么:Studio 对象「API」标签页的示例请求体不再放 `owner_id`
和可选的引用字段;必填引用字段改成一眼就能认出的占位符(尖括号包住的 `id of a showcase_project record`)。
- 为什么改:原来每个引用字段都填 `"related_record_id"`,这个 id 不对应任何记录,复制出来的新建/更新 cURL
在几乎所有对象上都被 400 `reference_not_found` 拒掉。
- 风险与回滚:只改示例体的生成,不碰任何写入路径;可选字段仍在体下方的提示里列名。回滚即还原 `ObjectApiPanel.tsx`
一个文件。
- 先看:`ObjectApiPanel.tsx` 的 `buildExampleBody`(哪些字段进体)→ 同文件
`referencePlaceholderFor`(必填引用的占位符)→ 钉住测试新增的 objectstack#27490 一节。
- 两分钟验证:`pnpm --dir ui exec vitest run
packages/app-shell/src/views/studio-design/ObjectApiPanel.exampleBody-11803.test.tsx`,预期
13 个测试全绿。
- 需要你做的:无,席位落地。
Fixes #27490
Clause-②: no
Metadata-protocol: none
## What changes
`ui/packages/app-shell/src/views/studio-design/ObjectApiPanel.tsx`,
`buildExampleBody` and the reference branch of `exampleElementFor`:
- **Optional fields that never join the body:** a field the platform
adds (`system: true`, such as `owner_id`, which the platform fills in
when it is left out), and a reference field (`REFERENCE_VALUE_TYPES`:
`lookup`, `master_detail`, `user`, `tree`). Both come from the field
metadata the draft already carries; there is no list of field names.
They are still named in the panel's "Optional fields not shown" note, so
every writable field is either in the body or named.
- **A required reference** stays in the body, since a create without it
is refused. Its value is now the text `id of a TARGET record` wrapped in
angle brackets, the target read through the spec's `referenceTargetOf`
(so a `user` field names `sys_user`), the same angle-bracket form as the
cURL's token placeholder. Before, it was `"related_record_id"`, which
reads like a working value.
- Unchanged: the other sample values, required-first order, the cap of
eight, and one body for both Create and Update (no second generator).
The previous "own fields before platform fields" ordering is now a
stronger rule: platform fields are never shown when optional.
## Tests
`ObjectApiPanel.exampleBody-11803.test.tsx` (the existing pin) is
extended with a `objectstack#27490` describe block of 5 tests. Its
oracle is the write path's own reference check:
`assertReferencesResolve` in `@objectstack/objectql` resolves a supplied
value only on a field that `referenceTargetOf` answers a target for. So
for every key of the shown body the test asserts
`referenceTargetOf(def)` is undefined (nothing for that check to refuse)
and the value still parses under `valueSchemaFor(def, 'stored')`.
- owner_id is left out even when the body has room, and is named in the
note.
- When no writable field is shown, the body block still renders (an
empty body) with the note naming the fields left out. Before, the block
and its note were hidden for an empty body; with owner_id now never
shown, an object whose writable fields are all optional references would
otherwise lose the note.
- Every optional reference is left out, on the showcase Account and on
the field zoo without its one required reference.
- A required reference shows the placeholder naming its target
(`showcase_project`; `sys_user` for a `user` field).
- The copied Create (POST) and Update (PATCH) cURL carry the shown body
and no `owner_id`.
Two existing tests are adjusted, not weakened: the per-type zoo test
reads a reference type's value shape with the field marked required (an
optional one is no longer in the body), and the multi-value test marks
`f_lookups` required for the same reason.
<details><summary>Test and ablation readings (head 8e49824)</summary>
- `pnpm --dir ui exec vitest run
packages/app-shell/src/views/studio-design/ObjectApiPanel.exampleBody-11803.test.tsx`:
Test Files 1 passed (1), Tests 13 passed (13).
- Ablation A, through `scripts/ablation-replace.mjs`: the never-shown
predicate replaced by `false` (anchor 1 to 0, blob f6f17e6 to
bdfdf47c). Tests 4 failed, 8 passed: the three new body tests and the
existing ordering test. Restored: blob equals HEAD, `git diff HEAD`
empty.
- Ablation B: the reference placeholder replaced by the old
`'related_record_id'` (blob f6f17e6 to a11e246e). Tests 1 failed (the
placeholder test), 11 passed. Restored the same way.
- Ablation C (head 8e49824): the empty-body condition's `||
omitted.length > 0` replaced by a constant-false marker (blob e4365cd
to b4195746). Tests 1 failed (the empty-body note test), 12 passed.
Restored the same way. A first attempt whose replacement was a substring
of the anchor was refused by the tool (replacement count did not rise)
and ran nothing.
- Ablations A and B ran on c2a2ffc; the later commit does not touch
those lines.
- `pnpm --filter @object-ui/app-shell type-check` (both `tsc --noEmit`
and `tsc -p tsconfig.test.json`): exit 0.
</details>
## Acceptance notes
- Acceptance "the copied Create/Update example carries no reference
field the author must fill by hand unless required, never owner_id": met
by construction and pinned. `owner_id` is `system: true` and never
required, so it is never in the body.
- Acceptance "the pin proves the body is accepted": the pin asserts the
body leaves the write path's reference check nothing to resolve and that
each value parses under the stored-form contract. It does not POST to a
live server. The card's own reproduction step 5 (the same bodies without
the reference keys answer 201 and 200) is the live reading; it was not
re-run here.
- Media fields (`FILE_REFERENCE_TYPES`) keep the `file_id` sample. The
write path's reference check does not resolve them (`referenceTargetOf`
answers no target), so they are outside this card.
## Verification
Local gates on head 8e49824: the `dispatch-gates --commands` list for
this diff, 34 families, each recorded as `command :: exit code` before
any pipe. All 34 exit 0; `--ran` reconciliation: 34 derived, 34 run, 0
NOT-MEASURED, 0 UNRUN. `node scripts/check-sdui-manifest.mjs` exit 0 (in
that list). `pnpm --dir ui check:new-line-citations`: 0 new citations.
`check-nul-bytes` exit 0.
On the first head (c2a2ffc) `pnpm --dir ui exec vitest run scripts/`
was red on two tests outside this diff
(`check-hand-rolled-comment-mask.test.ts` and
`js-comment-mask-returns-interpolation-9424.test.ts`), both `Test timed
out in 15000ms` while a build held the box; on 8e49824 the same command
exits 0.
Not run locally, left to CI: the full `app-shell` suite (the
`studio-design` folder alone holds 247 test files, past the container's
foreground limit) and the repo-wide lint. CI runs the full set.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
https://claude.ai/code/session_01Utp6CbUYNdYFJJSovGy2qL
---
_Generated by [Claude
Code](https://claude.ai/code/session_01Utp6CbUYNdYFJJSovGy2qL)_
---------
Co-authored-by: Claude <noreply@anthropic.com>1 parent ea684a0 commit 178b523
3 files changed
Lines changed: 141 additions & 20 deletions
File tree
- .changeset
- ui/packages/app-shell/src/views/studio-design
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
| 1 | + | |
| 2 | + | |
| 3 | + | |
| 4 | + | |
| 5 | + | |
| 6 | + | |
| 7 | + | |
| 8 | + | |
| 9 | + | |
| 10 | + | |
| 11 | + | |
| 12 | + | |
| 13 | + | |
| 14 | + | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
31 | 31 | | |
32 | 32 | | |
33 | 33 | | |
34 | | - | |
| 34 | + | |
| 35 | + | |
| 36 | + | |
| 37 | + | |
| 38 | + | |
| 39 | + | |
35 | 40 | | |
36 | 41 | | |
37 | 42 | | |
| |||
196 | 201 | | |
197 | 202 | | |
198 | 203 | | |
199 | | - | |
200 | | - | |
201 | | - | |
| 204 | + | |
| 205 | + | |
| 206 | + | |
| 207 | + | |
| 208 | + | |
| 209 | + | |
| 210 | + | |
| 211 | + | |
202 | 212 | | |
203 | 213 | | |
204 | 214 | | |
205 | 215 | | |
206 | 216 | | |
207 | | - | |
| 217 | + | |
208 | 218 | | |
209 | 219 | | |
210 | 220 | | |
| |||
289 | 299 | | |
290 | 300 | | |
291 | 301 | | |
| 302 | + | |
| 303 | + | |
| 304 | + | |
| 305 | + | |
| 306 | + | |
| 307 | + | |
| 308 | + | |
| 309 | + | |
| 310 | + | |
| 311 | + | |
| 312 | + | |
| 313 | + | |
| 314 | + | |
| 315 | + | |
| 316 | + | |
| 317 | + | |
| 318 | + | |
| 319 | + | |
| 320 | + | |
| 321 | + | |
| 322 | + | |
| 323 | + | |
| 324 | + | |
| 325 | + | |
| 326 | + | |
| 327 | + | |
| 328 | + | |
| 329 | + | |
| 330 | + | |
| 331 | + | |
| 332 | + | |
| 333 | + | |
| 334 | + | |
| 335 | + | |
| 336 | + | |
| 337 | + | |
| 338 | + | |
| 339 | + | |
| 340 | + | |
| 341 | + | |
| 342 | + | |
| 343 | + | |
| 344 | + | |
| 345 | + | |
| 346 | + | |
| 347 | + | |
| 348 | + | |
| 349 | + | |
| 350 | + | |
| 351 | + | |
| 352 | + | |
| 353 | + | |
| 354 | + | |
| 355 | + | |
| 356 | + | |
| 357 | + | |
| 358 | + | |
| 359 | + | |
| 360 | + | |
| 361 | + | |
| 362 | + | |
| 363 | + | |
| 364 | + | |
| 365 | + | |
| 366 | + | |
| 367 | + | |
| 368 | + | |
| 369 | + | |
| 370 | + | |
| 371 | + | |
| 372 | + | |
| 373 | + | |
| 374 | + | |
| 375 | + | |
| 376 | + | |
| 377 | + | |
| 378 | + | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
20 | 20 | | |
21 | 21 | | |
22 | 22 | | |
23 | | - | |
24 | | - | |
| 23 | + | |
| 24 | + | |
| 25 | + | |
25 | 26 | | |
26 | 27 | | |
27 | 28 | | |
| |||
39 | 40 | | |
40 | 41 | | |
41 | 42 | | |
| 43 | + | |
42 | 44 | | |
43 | 45 | | |
44 | 46 | | |
| |||
154 | 156 | | |
155 | 157 | | |
156 | 158 | | |
157 | | - | |
158 | | - | |
| 159 | + | |
| 160 | + | |
| 161 | + | |
| 162 | + | |
| 163 | + | |
| 164 | + | |
159 | 165 | | |
160 | 166 | | |
161 | 167 | | |
| |||
175 | 181 | | |
176 | 182 | | |
177 | 183 | | |
| 184 | + | |
| 185 | + | |
| 186 | + | |
| 187 | + | |
| 188 | + | |
| 189 | + | |
178 | 190 | | |
179 | 191 | | |
180 | 192 | | |
| |||
185 | 197 | | |
186 | 198 | | |
187 | 199 | | |
188 | | - | |
189 | | - | |
190 | | - | |
191 | | - | |
| 200 | + | |
| 201 | + | |
| 202 | + | |
| 203 | + | |
| 204 | + | |
| 205 | + | |
| 206 | + | |
| 207 | + | |
| 208 | + | |
| 209 | + | |
| 210 | + | |
192 | 211 | | |
193 | 212 | | |
194 | 213 | | |
195 | 214 | | |
196 | 215 | | |
197 | 216 | | |
198 | 217 | | |
199 | | - | |
200 | | - | |
201 | | - | |
202 | | - | |
| 218 | + | |
| 219 | + | |
| 220 | + | |
| 221 | + | |
203 | 222 | | |
204 | | - | |
| 223 | + | |
205 | 224 | | |
206 | 225 | | |
207 | 226 | | |
208 | | - | |
| 227 | + | |
| 228 | + | |
209 | 229 | | |
210 | 230 | | |
211 | 231 | | |
| |||
273 | 293 | | |
274 | 294 | | |
275 | 295 | | |
276 | | - | |
| 296 | + | |
277 | 297 | | |
278 | 298 | | |
279 | 299 | | |
| |||
0 commit comments