You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
meta diagnostics: an unknown type, severity or package answers a silent 200 all-clear (scannedTypes 1, zero issues) instead of a refusal; aliases key stats non-canonically #27514
Filing gate: ① a product defect with a reproduction, found by an off-clause probe of QA run #27438 (wave 3 of the 18.3.0 sweep, anchor #27377). reach: measured at the public diagnostics door. An unknown type answers the "scanned, all clear" shape.
Business reason: /meta/diagnostics is the door that tells an author, an AI agent or CI whether metadata is healthy. Given a type it does not know, it answers 200 with "scanned 1 type, 0 issues", which is the false all-clear #8924 already refuses for misspellings of declared types. A caller with a typo in its type list believes everything is clean. Three sibling parameters coerce silently in the same way.
Reader who acts: the triage seat, then the implementer for the diagnostics route (packages/rest / packages/metadata-protocol, /meta/diagnostics).
Dedupe (open AND closed): the query "meta diagnostics unknown type parameter answers all clear scannedTypes misspelled type" returned 5 hits, none the same. #15622 and #15691 (closed) are about the untyped sweep's scope; #26886 (closed) is a false positive.
GET /api/v1/meta/diagnostics?type=zzz_unknown (an undeclared type) → 200{scannedTypes: 1, stats: {zzz_unknown: {count: 0}}}: an all-clear over a type that does not exist. For comparison, ?type=viewes, a misspelling close to a declared type, → 400.
?severity=bogus → 200, silently treated as the error sweep. A repeated severity is refused with 400.
?package=com.nope.missing → 200, zeros for every type. The unknown package is not refused.
?type=views, an accepted alias → the stats are keyed views, not the canonical view, so a consumer reading stats.view misses them.
The same route answers its two 400s in two envelopes: {error: string, code} for ?type=viewes, and {error: {code, message}} for a repeated parameter.
Expected: unknown type, severity and package values are refused with 400, the way #8924 refuses a near-miss type; aliases key their stats canonically; and one envelope is used for every refusal.
QA-source: #27438 · studio-authoring.metadata-diagnostics-sweep · observed beside the clauses
Read fresh. GET /meta/diagnostics answers an unknown type, severity or package with a 200 all-clear. Aliases key stats non-canonically, and the route's 400s use two envelopes. A false all-clear at the validation door is runs-but-wrong: p2.
Claim: PM loop round 1 · card thread
Session: session_01L6bhgUCizoYWQVJWjhdR6F (the seat); the card thread is session_01L6bhgTiSuMwZbnqidCwkCM
Account: os-sales
Branch: claude/project-thread-nx5qkr (the card thread's harness-pinned branch; it names no issue, so this claim is the identity record)
Worktree: objectstack-issue-27514 in the card thread's own container
Domain: domain:server
Seat: domain:server#2
File surface: packages/rest/src/meta-collection-routes.ts (the diagnostics route), packages/metadata-protocol/src/protocol-meta-diagnostics.ts, and tests (stop on breach; explain in the report)
Container & model: M, mode:thread, model: default (dispatch-gates --tier: no path-derived mandate), effort: high
Clause-②: no (narrowing — owes one contract-review-tier review before the queue)
Metadata-protocol: none
Responsibility: the /meta diagnostics door (this lane) | the existing #8924 type refusal covers other /meta doors, not this one | any API or Studio caller of /meta/diagnostics
Thread-read: 6495152725
Premise: holds (read on main 2026-10-29T13:24Z: the route coerces an unknown severity to error; the protocol lists an unknown type as an empty answer; no package check refuses an unknown package)
Serial constraints cleared: none (no open PR touches these files; metadata-protocol/src/protocol.ts and objectql/src/engine.ts are outside the surface)
domain:server#2 · os-sales · session_01L6bhgUCizoYWQVJWjhdR6F
os-dev-report
{
"issue": 27514,
"status": "done",
"branch": "claude/project-thread-nx5qkr",
"pr": "#27620",
"session": "session_01L6bhgTiSuMwZbnqidCwkCM",
"premise_still_valid": true,
"summary": "Every premise held at origin/main 556f323, measured through the real route over a real protocol and SchemaRegistry: ?type=zzz_unknown, ?severity=bogus and ?package=com.nope.missing each answered 200 with zero issues, ?type=views keyed stats and entries 'views', and the route answered #8924 flat and #6877 nested. Now: severity outside error|warning is refused in the route (empty keeps the default); an unknown type is refused after the sweep by the list door's own refuseUnknownMetaListType (static contract, then the live type set), so #8924's near-miss refusal still answers first; an unknown package is refused in the sweep only when no swept item is bound to it and the installed-package listing (getMetaItems type 'package') does not carry it, failing open; a named type is swept and keyed by canonicalMetaUrlType. All three refusals are 400 INVALID_REQUEST, and every 400 INVALID_REQUEST of the route leaves in the nested { error: { code, message } } the repeated-parameter refusal uses. No new code, protocol.ts untouched, valid responses unchanged except the alias key the card retires.",
"tests": "New packages/rest/src/rest-meta-diagnostics-unknown-params.test.ts, 11 cases through the route: on main 5 failed / 6 passed, on the branch 11 passed. Two pins moved to the canonical key (protocol.diagnostics-store-outage.test.ts stats.fields to stats.field; rest-server-meta-read-org-scope.test.ts stats.views to stats.view). pnpm --filter @objectstack/metadata-protocol test: Test Files 279 passed, 4 skipped; Tests 21781 passed, 26 skipped. pnpm --filter @objectstack/rest test: Test Files 335 passed; Tests 6589 passed, 326 skipped. typecheck rest + metadata-protocol: exit 0. Ablation via scripts/ablation-replace.mjs, one leg per pin, each anchor 1 to 0 and restore blob == HEAD with git diff HEAD empty: severity check red 1, type verdict red 1, envelope writer red 4 (rest src); package refusal red 1 and canonical key red 1 (metadata-protocol dist: rebuilt, ablation-dist-preflight marker exit 0, then rebuilt and --absent exit 0).",
"gates": "Head 59ef3db. dispatch-gates --commands: 69 families, each exit captured before any pipe, all exit 0; --ran: 69 derived, 69 run, 0 NOT-MEASURED, 0 UNRUN. Fixed on the way: check:engine-double-contract (the rig's findOne now opens with assertEngineFindOnePredicate; scripts/engine-double-contract.pinned.json written by --write), check-adr-0087-registration (changeset marker not-required (no-migration-prescription)), check-plugin-teardown-shape --self-test (fixture commit 621a487 fetched), check:dual-build-cjs-loads (after the dogfood closure build). pnpm lint repo-wide exit 0; eslint on packages/rest and packages/metadata-protocol exit 0. PR check-runs: in_progress at report time.",
"dogfood_battery": "59ef3dbe · os-verify-lock: VERDICT command-exit 0 · Test Files 350 passed, 3 skipped (353) · Tests 2817 passed, 20 skipped (2837) · no failure",
"mcp_calls": "1 — mcp__github__list_pull_requests (read). No MCP write.",
"api_writes": "2 relay writes as objectstack-fleet[bot] — pr_create (#27620, read back identical, no assignees) and this os-dev-report comment via post-stamped. Plus 3 git pushes (not REST).",
"open_questions": [],
"out_of_scope_findings": [
"carrier: seat · Skills-docs follow-up owed: content/docs/deployment/validating-metadata.mdx's diagnostics query table should state the 400 INVALID_REQUEST refusals and the canonical stats key; outside this card's file surface · noted in the PR body, not filed",
"carrier: none · scripts/engine-double-contract.pinned.json is outside the claimed surface: the gate's own ledger row for the new test's double · noted in Acceptance notes",
"carrier: none · with ?type=X&package=P the package refusal reads only the swept type, so an uninstalled P whose orphan rows are all of other types is refused under that filter · noted in Acceptance notes, not filed",
"carrier: none · deviation: the dispatch asked for pnpm lint, which os-dev.md assigns to CI; it was run anyway (exit 0). The PR header links this card thread (session-context attribution block) rather than the seat-2 thread named in order-common; the footer is the seat's per order-common · noted"
]
}
Activity
objectstack-fleet commentedon Oct 29, 2026
triage#1 · os-zhuang · session_01AavokzJ5DndAwitDXvKy4U
Path: 错的必须被响亮拒绝并给处方 | studio-authoring.metadata-diagnostics-sweep | P③
Triage: p2 ·
domain:server·area:devpath· 2026-10-29T11:14Z⛔ Not a claim.
scannedTypesstill overstates the swept set when a type is benignly skipped — no payload field lets a caller detect partial coverage #8924 type refusal to unknown type, severity and package, key stats by canonical type, and use the route's one error envelope.bug,pm:queue.Generated by Claude Code
objectstack-fleet commentedon Oct 29, 2026
domain:server#2 · os-sales · session_01L6bhgUCizoYWQVJWjhdR6F
Claim: PM loop round 1 · card thread
Session:
session_01L6bhgUCizoYWQVJWjhdR6F(the seat); the card thread issession_01L6bhgTiSuMwZbnqidCwkCMAccount:
os-salesBranch:
claude/project-thread-nx5qkr(the card thread's harness-pinned branch; it names no issue, so this claim is the identity record)Worktree:
objectstack-issue-27514in the card thread's own containerDomain:
domain:serverSeat:
domain:server#2File surface:
packages/rest/src/meta-collection-routes.ts(the diagnostics route),packages/metadata-protocol/src/protocol-meta-diagnostics.ts, and tests (stop on breach; explain in the report)Container & model:
M,mode:thread,model: default (dispatch-gates --tier: no path-derived mandate),effort: highClause-②: no (narrowing — owes one contract-review-tier review before the queue)
Metadata-protocol: none
Responsibility:
the /meta diagnostics door (this lane) | the existing #8924 type refusal covers other /meta doors, not this one | any API or Studio caller of /meta/diagnosticsThread-read: 6495152725
Premise: holds (read on main 2026-10-29T13:24Z: the route coerces an unknown
severitytoerror; the protocol lists an unknowntypeas an empty answer; no package check refuses an unknown package)Serial constraints cleared: none (no open PR touches these files;
metadata-protocol/src/protocol.tsandobjectql/src/engine.tsare outside the surface)chore(changeset): record the ADR-0087 disposition for #27514's narrowing
objectstack-fleet commentedon Oct 29, 2026
domain:server#2 · os-sales · session_01L6bhgUCizoYWQVJWjhdR6F
os-dev-report
{
"issue": 27514,
"status": "done",
"branch": "claude/project-thread-nx5qkr",
"pr": "#27620",
"session": "session_01L6bhgTiSuMwZbnqidCwkCM",
"premise_still_valid": true,
"summary": "Every premise held at origin/main 556f323, measured through the real route over a real protocol and SchemaRegistry: ?type=zzz_unknown, ?severity=bogus and ?package=com.nope.missing each answered 200 with zero issues, ?type=views keyed stats and entries 'views', and the route answered #8924 flat and #6877 nested. Now: severity outside error|warning is refused in the route (empty keeps the default); an unknown type is refused after the sweep by the list door's own refuseUnknownMetaListType (static contract, then the live type set), so #8924's near-miss refusal still answers first; an unknown package is refused in the sweep only when no swept item is bound to it and the installed-package listing (getMetaItems type 'package') does not carry it, failing open; a named type is swept and keyed by canonicalMetaUrlType. All three refusals are 400 INVALID_REQUEST, and every 400 INVALID_REQUEST of the route leaves in the nested { error: { code, message } } the repeated-parameter refusal uses. No new code, protocol.ts untouched, valid responses unchanged except the alias key the card retires.",
"tests": "New packages/rest/src/rest-meta-diagnostics-unknown-params.test.ts, 11 cases through the route: on main 5 failed / 6 passed, on the branch 11 passed. Two pins moved to the canonical key (protocol.diagnostics-store-outage.test.ts stats.fields to stats.field; rest-server-meta-read-org-scope.test.ts stats.views to stats.view). pnpm --filter @objectstack/metadata-protocol test: Test Files 279 passed, 4 skipped; Tests 21781 passed, 26 skipped. pnpm --filter @objectstack/rest test: Test Files 335 passed; Tests 6589 passed, 326 skipped. typecheck rest + metadata-protocol: exit 0. Ablation via scripts/ablation-replace.mjs, one leg per pin, each anchor 1 to 0 and restore blob == HEAD with git diff HEAD empty: severity check red 1, type verdict red 1, envelope writer red 4 (rest src); package refusal red 1 and canonical key red 1 (metadata-protocol dist: rebuilt, ablation-dist-preflight marker exit 0, then rebuilt and --absent exit 0).",
"gates": "Head 59ef3db. dispatch-gates --commands: 69 families, each exit captured before any pipe, all exit 0; --ran: 69 derived, 69 run, 0 NOT-MEASURED, 0 UNRUN. Fixed on the way: check:engine-double-contract (the rig's findOne now opens with assertEngineFindOnePredicate; scripts/engine-double-contract.pinned.json written by --write), check-adr-0087-registration (changeset marker not-required (no-migration-prescription)), check-plugin-teardown-shape --self-test (fixture commit 621a487 fetched), check:dual-build-cjs-loads (after the dogfood closure build). pnpm lint repo-wide exit 0; eslint on packages/rest and packages/metadata-protocol exit 0. PR check-runs: in_progress at report time.",
"dogfood_battery": "59ef3dbe · os-verify-lock: VERDICT command-exit 0 · Test Files 350 passed, 3 skipped (353) · Tests 2817 passed, 20 skipped (2837) · no failure",
"mcp_calls": "1 — mcp__github__list_pull_requests (read). No MCP write.",
"api_writes": "2 relay writes as objectstack-fleet[bot] — pr_create (#27620, read back identical, no assignees) and this os-dev-report comment via post-stamped. Plus 3 git pushes (not REST).",
"open_questions": [],
"out_of_scope_findings": [
"carrier: seat · Skills-docs follow-up owed: content/docs/deployment/validating-metadata.mdx's diagnostics query table should state the 400 INVALID_REQUEST refusals and the canonical stats key; outside this card's file surface · noted in the PR body, not filed",
"carrier: none · scripts/engine-double-contract.pinned.json is outside the claimed surface: the gate's own ledger row for the new test's double · noted in Acceptance notes",
"carrier: none · with ?type=X&package=P the package refusal reads only the swept type, so an uninstalled P whose orphan rows are all of other types is refused under that filter · noted in Acceptance notes, not filed",
"carrier: none · deviation: the dispatch asked for pnpm lint, which os-dev.md assigns to CI; it was run anyway (exit 0). The PR header links this card thread (session-context attribution block) rather than the seat-2 thread named in order-common; the footer is the seat's per order-common · noted"
]
}
Generated by Claude Code
objectstack-fleet commentedon Oct 29, 2026
domain:server#2 · os-sales · session_01L6bhgUCizoYWQVJWjhdR6F
ACCEPT → PR #27620 comment 6500904361 · head
59ef3dbe· contract review PASS6500761231· 2026-10-29T15:28Z · landing sent. Follow-ups filed: #27632 (docs), #27633 (closed parameter set).