Skip to content

Commit 2fa286c

Browse files
os-zhuangclaude
andauthored
docs(spec,metadata-protocol): the code is the record for platform agent definitions (#4507) (#4512)
`agent` is the only authorable type with no governed write path — ADR-0063 §2 closes `*.agent.ts` to third parties, so both `allowOrgOverride` and `allowRuntimeCreate` are false and nothing reaches `saveMetaItem`. Its rows are written by the shipping plugin at boot (`AIStudioPlugin.registerMeta` → `metadataService.register()` → `MetadataManager.register` → `DatabaseLoader.save`), which writes `sys_metadata` directly with a fresh checksum and appends no `sys_metadata_history` row. A shipped agent definition that changes between releases therefore leaves no metadata-side change log. That is a deliberate position, and it now sits beside the declaration rather than only in an issue: the two definitions live in version control (`@objectstack/service-ai-studio`, `cloud` repo), so git already holds the full reviewable history, and a second history in `sys_metadata` would be a WORSE record — it would capture only the boots where a given deployment saw the checksum move, so two deployments on one release would carry different "histories" of an identical, code-fixed definition. The note names the two consequences that read as bugs and are not: the `skipped` outcome `os migrate meta --stored` reports for `agent` is correct and permanent for this type, and Studio showing no History tab is the absence of anything to show. `migrateStoredMetadata`'s TSDoc — where the skip reason was what made this look like a gap — now points at it. It also states its own expiry: opening `agent` to tenant authoring removes the git fallback, so opening the type and giving it a real history path are the same piece of work. Comment-only; empty changeset. Claude-Session: https://claude.ai/code/session_01WoZPKPDqJ7WB7z84xk9y3f Co-authored-by: Claude <noreply@anthropic.com>
1 parent 7631964 commit 2fa286c

3 files changed

Lines changed: 75 additions & 0 deletions

File tree

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
---
2+
---
3+
4+
docs(spec,metadata-protocol): record why platform `agent` definitions have no metadata change log (#4507)
5+
6+
Comment-only — no behaviour changes, nothing to release.
7+
8+
`agent` is the only authorable metadata type with no governed write path
9+
(`allowOrgOverride` and `allowRuntimeCreate` are both `false` per ADR-0063 §2,
10+
which closes `*.agent.ts` to third parties). Its rows are written by the
11+
shipping plugin at boot — `AIStudioPlugin.registerMeta``metadataService.register()`
12+
`MetadataManager.register``DatabaseLoader.save` — which writes
13+
`sys_metadata` directly with a fresh checksum and appends no
14+
`sys_metadata_history` row. So a shipped agent definition that changes between
15+
releases leaves no metadata-side change log.
16+
17+
That is accepted rather than overlooked, and the reasoning now sits beside the
18+
declaration instead of in an issue: the two definitions live in version control
19+
(`@objectstack/service-ai-studio` in the `cloud` repo), so git already holds the
20+
full reviewable history. A second history in `sys_metadata` would be a *worse*
21+
record — it would capture only the boots where a given deployment happened to
22+
see the checksum move, so two deployments on the same release would carry
23+
different "histories" of an identical, code-fixed definition.
24+
25+
Two consequences that read as bugs and are not are named explicitly: the
26+
`skipped` outcome `os migrate meta --stored` reports for `agent` rows is correct
27+
and permanent for this type, and Studio showing no History tab for an agent is
28+
the absence of anything to show. `migrateStoredMetadata`'s TSDoc now points at
29+
the note rather than leaving its skip reason to be read as a to-do.
30+
31+
The note also states its own expiry: if `agent` is ever opened to tenant
32+
authoring, an author-owned definition has no git to fall back on, so opening the
33+
type and giving it a real history path become the same piece of work.

packages/metadata-protocol/src/protocol.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6610,6 +6610,14 @@ export class ObjectStackProtocolImplementation implements
66106610
* raw-engine branch, which records no history and forces `state:
66116611
* 'active'` — a historyless rewrite that could also promote a draft is
66126612
* not what this pass promises, so it declines instead.
6613+
*
6614+
* Today that is exactly one type, `agent`, and its skip is **permanent
6615+
* by design, not a to-do** (#4507): ADR-0063 §2 closes `*.agent.ts` to
6616+
* third parties, so the only agent definitions in existence are the two
6617+
* the platform ships from version control — where git, not
6618+
* `sys_metadata_history`, is the change log. See the note beside the
6619+
* `agent` entry in `metadata-plugin.zod.ts` before treating this branch
6620+
* as a gap to close.
66136621
* - **Rows that still fail the current schema after conversion.**
66146622
* `saveMetaItem` rejects them (422) and that rejection is correct: the
66156623
* body is a genuine contract violation, not chain-owned history. They

packages/spec/src/kernel/metadata-plugin.zod.ts

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -695,6 +695,40 @@ export const DEFAULT_METADATA_TYPE_REGISTRY: MetadataTypeRegistryEntry[] = [
695695
// allowRuntimeCreate:false (no runtime "create agent") and
696696
// allowOrgOverride:false (no per-org agent fork). The runtime catalog
697697
// additionally filters out any non-platform agent record (see service-ai).
698+
//
699+
// FOR AGENTS, THE CODE IS THE RECORD — and that is the whole answer to
700+
// "where is this type's change log?" (#4507). Because the two flags above
701+
// are false, `agent` is the one authorable type with NO governed write
702+
// path: `saveMetaItem` would route it down the legacy raw-engine branch,
703+
// and nothing calls it. The rows are written instead by the shipping
704+
// plugin at boot — `AIStudioPlugin.registerMeta` → `metadataService
705+
// .register()` → `MetadataManager.register` → `DatabaseLoader.save` —
706+
// which writes `sys_metadata` directly with a fresh checksum and appends
707+
// NO `sys_metadata_history` row. So an agent definition that changes
708+
// between releases leaves no metadata-side change log, and there is no
709+
// metadata-side rollback.
710+
//
711+
// That is accepted, not overlooked. These definitions live in version
712+
// control (`@objectstack/service-ai-studio`, `cloud` repo:
713+
// `agents/ask-agent.ts`, `agents/metadata-assistant-agent.ts`), so git
714+
// already holds the full, reviewable history of every change. A second
715+
// history in `sys_metadata` would be a WORSE record, not a better one: it
716+
// would capture only the boots where a given deployment happened to see
717+
// the checksum move, so two deployments on the same release would carry
718+
// different "histories" of an identical, code-fixed definition. Do not add
719+
// one to close a perceived gap.
720+
//
721+
// Two consequences that look like bugs and are not:
722+
// - `migrateStoredMetadata` reports `agent` rows `skipped` ("no repository
723+
// write path"). That is CORRECT AND PERMANENT for this type, not a
724+
// to-do — the pass declines rather than performing a historyless
725+
// rewrite that could also promote a draft.
726+
// - Studio surfaces no History tab for an agent. There is nothing to show;
727+
// the answer to "what changed" is the `cloud` commit log.
728+
//
729+
// If `agent` is ever OPENED to tenant authoring, this note stops applying:
730+
// an author-owned definition has no git to fall back on, so opening the
731+
// type and giving it a real history path are the same piece of work.
698732
{ type: 'agent', label: 'AI Agent', filePatterns: ['**/*.agent.ts', '**/*.agent.yml'], supportsOverlay: false, allowOrgOverride: false, allowRuntimeCreate: false, supportsVersioning: true, executionPinned: true, loadOrder: 90, domain: 'ai' },
699733
{ type: 'tool', label: 'AI Tool', filePatterns: ['**/*.tool.ts', '**/*.tool.yml'], supportsOverlay: true, allowOrgOverride: true, allowRuntimeCreate: true, supportsVersioning: false, executionPinned: false, loadOrder: 85, domain: 'ai' },
700734
{ type: 'skill', label: 'AI Skill', filePatterns: ['**/*.skill.ts', '**/*.skill.yml'], supportsOverlay: true, allowOrgOverride: true, allowRuntimeCreate: true, supportsVersioning: false, executionPinned: false, loadOrder: 88, domain: 'ai' },

0 commit comments

Comments
 (0)