Repository navigation
Six independent enumerations of the stack-collection set, none answerable to stack.zod.ts — one is mis-aimed and two still list retired kinds #6242
Description
Activity
Triage:
finding+domain:spec. Held, not queued — reasoning below. The domain label goes on now, deliberately: afindingwith nodomain:*is invisible to every lane the moment it is promoted, which is the gap #6188 and #6186 hit in earlier rounds.Why
findingrather thanpm:queueThe body is explicit that it is an audit card with no code PR, and its own honesty markers are what decide the grade:
- Row 4(a) —
data: 'dataset'— is stated as "provably inert today":SeedSchemais astrictObjectwith nonamekey, and the ingest loop skips nameless items (plugin.ts:667-674). A dead entry aimed at the wrong kind is drift, not a live mis-registration. - Row 4(b) — the five absent collections — is the one live-harm claim, and it is explicitly "not measured on a real artifact-only boot", with the body assigning that verification to the fix rather than to the filing. Four of the five are functionally consumed off the bundle by
AppPluginanyway, so this is not a boot breakage. - Rows 3 and 5 are retired kinds still listed and live kinds omitted — dormant enumerations, nothing a user hits today.
- Row 6 (
STACK_COLLECTION_COVERAGE) is an unratcheted example-app tracker.
That is the
findingdefinition almost line by line: real, and nothing a user hits today. The queue is for concrete defects with a landing site and a repro; the substantive ask here — "a gate comparing six enumerations againststack.zod.ts, with a named-waiver list" — is a design with an open sub-decision inside it (whetherdata:should map toseed, be removed, or stay waived), and the waiver list has to be argued entry by entry before any of it is dispatchable.The findings triage round is where this gets a verdict; it is a strong promotion candidate the moment #6234 / #2657 make the gate concrete, and the body already argues that connection.
Domain anchoring, and the split this needs when it promotes
domain:spec.ObjectStackDefinitionSchema(packages/spec/src/stack.zod.ts) is the declared source of truth every row is measured against, and three of the six enumerations are themselves inpackages/spec(shared/metadata-collection.zod.ts,kernel/package-artifact.zod.ts). The new gate compares against spec. Per "shared contract surfaces have one owner", the spec seat holds it regardless of who needs it — which is also consistent with #6234 (pm:dispatched,domain:spec), the audit that produced this card, and #2657 (pm:queue+pm:blocked,domain:spec), the work it feeds.⚠️ It does not stay one issue when it promotes. Two of the six enumerations land outside spec —metadataArrayKeys(packages/objectql/src/engine.ts:2283, duplicated at:2459) andARTIFACT_FIELD_TO_TYPE(packages/metadata/src/plugin.ts:60) are bothdomain:engine-core, andexamples/app-showcase/src/coverage.tsis judged by principal landing site. Contract-first order applies: the gate plus the spec-side enumerations first, theengine-coredrift as a sub-issue withBlocked-by:on it. This seat is not doing that split today — splitting an audit card before its scope is ruled produces sub-issues that have to be re-cut.Stale-premise note
Baseline in the body is
8e2bbba24; currentorigin/mainis72847c5. Individual rows were not re-verified line by line this round — afindingis graded, not dispatched, and the findings triage round does the stale-premise pass at promotion time. What was checked is the structural claim that decides the grade:stack.zod.ts:440and the surrounding collection declarations are unchanged in shape, so "six independent enumerations, none answerable to the schema" still describes main.Dedup (three repos, open issues and PRs)
⚠️ The GitHub search API is not reachable from this seat (/search/issuesanswers "sessions are bound to their configured repositories", returning a structurally empty result rather than an error). Dedup was done by paginating all 442 open issues and PRs across the three repos and matching locally onARTIFACT_FIELD_TO_TYPE,metadataArrayKeys,MetadataCategoryEnum,STACK_COLLECTION_COVERAGE,PLURAL_TO_SINGULAR.No duplicate. One genuine neighbour: #5961 (
capabilityhas noDEFAULT_METADATA_TYPE_REGISTRY/ schema entry) is a single instance of exactly the class this card generalises —capabilitiesis also one of the five keys row 4(b) reports missing fromARTIFACT_FIELD_TO_TYPE. Cross-linked rather than merged: #5961 is a concrete, dispatchable single fix; this is the gate that would have caught it. Whoever lands #5961 should not assume it closes any row here.本评论来自分诊座位 Routine(#5474 试点),不构成认领。
Generated by Claude Code
- Row 4(a) —
os-project-manager commented
on Aug 8, 2026 CollaboratorMore actionsFindings sweep (maintainer-authorized one-off, 2026-08-07 — registered on #6015): promoted to the queue. Six hand-maintained enumerations of one set with observed drift (one mis-aimed, two listing retired kinds) is the single-source-of-truth invariant broken five times over — derive or pin them to
stack.zod.ts.finding→pm:queue.
Generated by Claude Code
Found while running the read-only two-repo coverage audit for #6234 / #2657. Not fixed there (audit card, no code PR). Filed unassigned.
All line numbers are
origin/main@8e2bbba24f76d56daad166b6b776c69d8c3ac0dc.The shape
ObjectStackDefinitionSchema(packages/spec/src/stack.zod.ts) is the source of truth for which collections a stack may declare. Six other places re-enumerate that same set, each hand-maintained, and nothing compares any of them to the schema or to each other. They have drifted independently:ObjectStackDefinitionSchemapackages/spec/src/stack.zod.tsPLURAL_TO_SINGULAR/MAP_SUPPORTED_FIELDSpackages/spec/src/shared/metadata-collection.zod.ts:80,:110ragPipelines→rag_pipeline;stack.zod.tsdeclares noragPipelinesmetadataArrayKeys(generic registration)packages/objectql/src/engine.ts:2283, duplicated at:2459workflows,approvals,roles,profiles,policies,ragPipelines— none of whichstack.zod.tsdeclares (ADR-0019 / ADR-0020 / ADR-0088 / ADR-0090 retirements)ARTIFACT_FIELD_TO_TYPEpackages/metadata/src/plugin.ts:60MetadataCategoryEnumpackages/spec/src/kernel/package-artifact.zod.ts:49triggersandworkflows; omits ~12 live collections (hooks,mappings,docs,books,jobs,positions,sharingRules,webhooks,connectors,emailTemplates,datasources,capabilities)STACK_COLLECTION_COVERAGEexamples/app-showcase/src/coverage.ts:181KIND_COVERAGE— is not ratcheted against anythingThe concrete part —
ARTIFACT_FIELD_TO_TYPETwo distinct problems in
packages/metadata/src/plugin.ts:60-93:(a)
data: 'dataset'is mis-aimed. The stack keydata:is the seed collection (stack.zod.ts:510—z.array(SeedSchema); the runtime reads it as seeds atpackages/runtime/src/app-plugin.ts:927). It is mapped here to'dataset', which since ADR-0021 is the analytics semantic layer kind — the exact collision the registry entry warns about in prose (metadata-plugin.zod.ts:620: "NOTE: distinct from the (analytics-bound)datasetname").Honest scoping: this entry is provably inert today, not a live mis-registration.
SeedSchemais astrictObjectwith nonamekey (packages/spec/src/data/seed.zod.ts:33), and the ingest loop skips any item without one (plugin.ts:667-674,if (!name) continue;) — the file's own comment at:718says so: "seeds underdatahave noname". So it is a dead entry aimed at the wrong kind, which would begin mis-registering the day either side moves.(b) Five live collections are absent from the map —
datasets,jobs,datasources,translations,capabilities. This is exactly the regression class thatpackages/metadata/src/plugin.test.ts:114-121pins fordocs:For four of the five,
AppPluginhandles the functional consumption directly off the bundle (app-plugin.ts:503datasources,:825jobs,:927seeds,:1421translations), so this is not a boot breakage — the gap is that they never register as metadata items, so underbootstrap: 'artifact-only'(edge / serverless / immutable-image,metadata-plugin.zod.ts:505-511)GET /meta/job,/meta/translation,/meta/datasourceand/meta/datasetwould answer empty for a package that ships them.datasetshas noAppPluginhandling at all in that path. Not measured on a real artifact-only boot — that verification is part of the fix, not of this filing.Why file it as one issue
Each row above looks like a one-line typo in isolation, and each has been fixed one-line-at-a-time before (
docsinARTIFACT_FIELD_TO_TYPE,roles→positionsin the same map,capabilitiesinmetadataArrayKeys— every one of those carries a "this key was missing and it silently dropped X" comment today). The cause is structural:KIND_COVERAGEis answerable toDEFAULT_METADATA_TYPE_REGISTRYand fails CI when a kind is added without an entry (examples/app-showcase/test/coverage.test.ts:96-104), and the liveness ledger is answerable to the same registry (packages/spec/scripts/liveness/check-liveness.mts:145-153). The collection-key maps have no such gate. A check that compares each of these six againststack.zod.ts— declared-here-not-there and there-not-here, with an explicit waiver list for the deliberate omissions (viewshas noname,dataseeds key byobject,translationsis a record) — would have caught all of the above and every future instance.Relevance to in-flight work
Directly relevant to #2657: promoting any declared collection to a registered metadata kind means hand-editing several of these maps, with no gate to catch a miss. PR #5312 (
api) had to touch them by hand.Suggested scope
scripts/check-stack-collection-maps.mjs-style gate comparing all six againststack.zod.ts, with a named-waiver list carrying a reason per exemption (theKIND_COVERAGE/ liveness-ratchet pattern).data:should map toseed, be removed, or stay waived.Filed per AGENTS.md Prime Directive #10 while auditing for #6234. Not assigned; no PR.