Skip to content

refactor(spec)!: the #3896 close-out sweep — fourteen inert authoring keys leave the surface - #4054

Merged
os-zhuang merged 3 commits into
mainfrom
claude/sharing-rules-schema-bypass-h4c7xr
Jul 30, 2026
Merged

refactor(spec)!: the #3896 close-out sweep — fourteen inert authoring keys leave the surface#4054
os-zhuang merged 3 commits into
mainfrom
claude/sharing-rules-schema-bypass-h4c7xr

Conversation

@os-zhuang

Copy link
Copy Markdown
Contributor

The enforce-or-remove worklist across the remaining governed types, inside the v17 window. Every removal got the full retirement kit (retiredKey prescription + protocol-17 conversion + retirement pin tests); the sweep also produced one correction in the opposite direction, which is the most instructive part.

Removed (14 keys, 6 conversions)

TypeKeysWhy the claim was false
actionshortcut, bulkEnabledno keydown path ever dispatched a shortcut (objectui's keyboard stack never consults action metadata); the multi-select toolbar reads the view'sbulkActions, never this flag
flowactive, template, node outputSchema, errorHandling.fallbackNodeIdactive: false never stopped a flowstatus is the enforced lifecycle, and the default even read as disabled while the engine treated unset as enabled (the rls.enabled shape, over-permissive direction); template had no reader; node outputs were never validated; faults route via per-node fault edges
viewlist responsive/performance, form defaultSort/ariano renderer read any of them (re-verified; list aria/data stay live) — an ARIA claim merely accepted is false accessibility compliance
dashboardaria, performance, widget performanceno renderer applied them; widget.performance had no ledger entry and was call-graph-closed fresh across both repos (objectui's virtual scrolling reads the live top-level virtualScroll)
agentknowledgedeclaring sources/indexes never scoped retrievalsearch_knowledge takes sourceIds from the LLM's own tool-call arguments, never the agent record. A grounding claim in the dangerous direction
skilltriggerPhrasesphrases were never matched against the user's message; activation is triggerConditions ∩ the agent's skills[]. The cloud API even served the field back — a dead-end projection that made the false capability look real

Orphaned value schemas removed with their keys (PerformanceConfigSchema, AIKnowledgeSchema, #3950 precedent); the same-major topicssources rename is absorbed into the knowledge removal pre-release — composed, its effect was unobservable, and the conversion table's fixture-disjointness contract enforces exactly that judgment.

The correction: form.data survived, and the build is the referee

The ledger said form data was dead ("no form-path reader in either repo"). The removal attempt broke the build: defineForm writes data: { provider: 'schema', schemaId } onto every *.form.ts metadata form, and metadata-protocol serves it to the metadata-admin pipeline. So the entry's verdict is corrected to live (with the real evidence and a verifiedAt), the conversion narrowed, and the lint tests pin the non-warn. Method note now recorded in the entry: a ledger verdict is an input to removal, not a substitute for the build's own proof.

Deliberate keeps (recorded, not skipped)

hook.label/description and flow.description are docs-shaped annotation fields — they document intent for the next reader (per ADR-0033, often a model) even without a runtime consumer. Kept, with ledger notes marking them exempt from enforce-or-remove so future audits don't re-litigate. Stale report aria/performance ledger entries (schema already clean since the report-liveness close-out) deleted as hygiene.

Kit details

  • 6 conversions + chain step; chain-replay composability green; spec-changes.json/upgrade guide carry every entry.
  • The surface guard's tombstone-coverage matcher generalized to split ' / '-separated multi-key conversion surfaces before matching — exactly as strict per key as before; multi-key conversions have been the house style since the tool sweep, and this is the first retiredKey batch to exercise that path.
  • Retirement pins across 7 test files; forms pruned (action/flow/dashboard/agent/skill — a form input for an unenforced capability is the UI half of false compliance); i18n bundles regenerated (merge mode, pure deletions); example flows drop template: true (3 sites — two of them caught by the tombstone's tsc leg after the initial grep missed them); SKILL.md and ai/agents.mdx stop teaching the removed keys; v17 notes, upgrade checklist, and ledger README rows updated; major changeset.

Verification

  • spec 6932 / objectql 1179 / cli 830 tests green; all spec gates green (liveness, empty-state, authorable-surface, api-surface, spec-changes, upgrade-guide, docs 251, skill-refs, skill-examples 198, i18n).
  • Examples + downstream-contract typecheck clean; spec tsc clean.
  • Ledger state after the sweep: action/view/dashboard/report/agent/skill dead-count = 0; flow = 1 (kept docs field), hook = 2 (kept docs fields).

Generated by Claude Code

… keys leave the surface
The enforce-or-remove worklist across the remaining governed types, each key
tombstoned with its prescription (retiredKey) and stripped by a protocol-17
conversion:
- action shortcut/bulkEnabled — no keydown path dispatches shortcuts; the
multi-select toolbar reads the view's bulkActions.
- flow active/template, node outputSchema, errorHandling.fallbackNodeId —
active:false never stopped a flow (status is the enforced lifecycle; the
default even READ as disabled while the engine treated unset as enabled);
faults route via per-node fault edges.
- view list responsive/performance, form defaultSort/aria — no renderer read
them. List aria/data stay live. form.data SURVIVED: the removal attempt
broke the build (defineForm writes data.provider='schema' onto every
metadata form; metadata-protocol serves it) — the build refuted the
ledger's dead verdict, so the entry is CORRECTED to live instead. The
sweep's method note: a ledger verdict is an input to removal, not a
substitute for the build's own proof.
- dashboard aria/performance + widget performance (+ orphaned
PerformanceConfigSchema) — no renderer applied them; widget.performance
had no ledger entry and was call-graph-closed fresh across both repos.
- agent knowledge (+ orphaned AIKnowledgeSchema) — declaring sources never
scoped retrieval (search_knowledge takes sourceIds from the LLM's
tool-call args). The same-major topics→sources rename is ABSORBED into the
removal pre-release: composed, its effect was unobservable, and the
fixture-disjointness contract of the conversion table enforces exactly
that judgment.
- skill triggerPhrases — never matched; activation is triggerConditions ∩
the agent's skills[] allowlist.
Deliberate keeps, recorded so they are not re-litigated: hook
label/description and flow description are docs-shaped annotation fields,
exempt from enforce-or-remove. Stale report aria/performance ledger entries
(schema already clean) deleted as hygiene.
Kit: 6 conversions + chain step (chain-replay green); retirement pins across
7 test files; forms pruned (action/flow/dashboard/agent/skill); i18n bundles
regenerated (merge mode); baselines edited deliberately (authorable-surface,
json-schema.manifest — AIKnowledge/PerformanceConfig unpublished); the
surface guard's coverage matcher generalized to ' / '-separated multi-key
conversion surfaces (exactly as strict per key); example flows drop
template:true (3 sites, caught by the tombstone's tsc leg); SKILL.md +
agents.mdx stop teaching the removed keys; v17 notes + upgrade checklist +
README ledger rows updated; major changeset.
spec 6932 / objectql 1179 / cli 830 green; all spec gates green; examples +
downstream-contract typecheck clean.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01QuViRSR1j6GJjf9qGbnqFX
@vercel

vercelBot commented Jul 30, 2026

Copy link
Copy Markdown

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

1 Skipped Deployment
ProjectDeploymentActionsUpdated (UTC)
objectstackIgnoredIgnoredJul 30, 2026 7:15am

Request Review

@github-actions

Copy link
Copy Markdown
Contributor

📓 Docs Drift Check

This PR changes 3 package(s): @objectstack/cli, @objectstack/platform-objects, @objectstack/spec.

111 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 packages/cli, @objectstack/spec)
  • content/docs/ai/skills.mdx(via @objectstack/spec)
  • content/docs/api/client-sdk.mdx(via @objectstack/cli, @objectstack/spec)
  • content/docs/api/data-flow.mdx(via @objectstack/cli)
  • content/docs/api/environment-routing.mdx(via @objectstack/cli, @objectstack/spec)
  • content/docs/api/error-catalog.mdx(via @objectstack/cli, @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 packages/spec)
  • content/docs/automation/flows.mdx(via @objectstack/spec)
  • content/docs/automation/hook-bodies.mdx(via packages/cli, 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/backup-restore.mdx(via @objectstack/cli)
  • content/docs/deployment/cli.mdx(via @objectstack/cli, @objectstack/spec)
  • content/docs/deployment/self-hosting.mdx(via @objectstack/cli)
  • 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/cli, @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/data-service.mdx(via packages/cli)
  • content/docs/kernel/runtime-services/email-service.mdx(via packages/spec)
  • content/docs/kernel/runtime-services/index.mdx(via packages/cli, 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/permissions/authentication.mdx(via @objectstack/cli)
  • 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/cli, @objectstack/platform-objects, @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/cli, @objectstack/spec)
  • content/docs/protocol/kernel/realtime-protocol.mdx(via @objectstack/cli)
  • 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/cli, @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/cli, @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/platform-objects, @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.

claude added 2 commits July 30, 2026 07:14
….md defineSkill example drops triggerPhrases
CI's liveness gate caught the sweep's ledger discipline error: retiredKey
keeps a key in the walked shape, so its entry must STAY (dead + REMOVED
note — the rls.priority precedent), not be deleted (that is the strict-
removal discipline, used for the tool batch where keys left the shape).
All 14 entries restored with verifiedAt + per-key prescriptions; README
counts corrected to match. The local 'pass' before push was a masked exit
code ('| tail -1' swallows the gate's status) — gates now re-run with
explicit exit checks, which also surfaced the SKILL.md defineSkill example
still authoring triggerPhrases (a head-truncated grep miss; the os:check
harness is the authoritative sweeper and is green again).
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01QuViRSR1j6GJjf9qGbnqFX
…allbackNodeId
Found by the corrected sweep after the SKILL.md catch — flows.mdx's
defineFlow example authored template: false, and the error-handling section
documented fallbackNodeId in both the example and the property table. The
:208 'template' hit is the notify node's email template (a different, live
config key); the sharing-rule and app 'active' hits are live keys on other
types — all three verified before leaving them alone.
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01QuViRSR1j6GJjf9qGbnqFX
@os-zhuang
os-zhuang marked this pull request as ready for review July 30, 2026 07:39
@os-zhuang
os-zhuang merged commit 12a19a8 into mainJul 30, 2026
18 checks passed
@os-zhuang
os-zhuang deleted the claude/sharing-rules-schema-bypass-h4c7xr branch July 30, 2026 07:40
baozhoutao added a commit that referenced this pull request Jul 30, 2026
…he api reference
Only conflict was `content/docs/references/api/errors.mdx`, an AUTO-GEN file that
both sides touched: main through #4054's authoring-key sweep, this branch through
`FieldErrorSchema.label`. Took main's copy and re-ran `gen:schema && gen:docs`
rather than hand-merging a generated artifact.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
os-zhuang added a commit that referenced this pull request Jul 30, 2026
* feat(showcase): demonstrate bulk actions over a selection
`bulkActions` — naming declared object actions so each SELECTED record is fanned
out through the action runner — had no example in the showcase. It is also the
only way to declare a bulk action: `action.bulkEnabled` was retired in spec 17
(#3896 close-out, #4054) precisely because nothing consumed it, and its
tombstone prescribes this key.
Adds a `bulk_actions` named view on showcase_task — the selection-bar twin of
the existing `legacy_row_actions` fixture — naming both an action whose work is
a sandboxed script (showcase_mark_done, via the platform action route) and one
that is a custom endpoint (showcase_recalc_estimate, whose already-declared
`recordIdParam` carries each record's id). Neither is a field patch, which is
what distinguishes this from project.view.ts's `bulkActionDefs`: those mass-EDIT
through the data API, this dispatches a real action per record.
Verified in a browser against this app: selecting all 10 tasks and running each
button issues 10 POSTs (one per record, all 200) to
/api/v1/actions/showcase_task/showcase_mark_done and /api/v1/showcase/recalc
respectively, and the records change server-side. No console errors.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
* fix(showcase): translate the new view label, add the release-nothing changeset
The zh-CN bundle must carry every declared label — the i18n coverage ratchet
counts untranslated declared strings per example and refused the 456 → 457
growth. And objectstack requires a changeset per PR; an empty one is the
sanctioned declaration for a change that releases nothing (the showcase package
is private).
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
---------
Co-authored-by: Jack Zhuang <277994282+os-zhuang@users.noreply.github.com>
Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

documentationImprovements or additions to documentationprotocol:aiprotocol:uisize/xlteststooling

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants

@os-zhuang@claude