Skip to content

feat(native): page retained feature traces through analysis views - #8533

Open
kaoru0822-kitauji wants to merge 3 commits into
mainfrom
feat/8373-native-trace-views
Open

kaoru0822-kitauji wants to merge 3 commits into
mainfrom
feat/8373-native-trace-views

Conversation

@kaoru0822-kitauji

@kaoru0822-kitauji kaoru0822-kitauji commented Nov 1, 2026 •

Copy link
Copy Markdown
Collaborator

What broke: a large native trace_feature result, with thousands of references and unavailable owners, could only be consumed whole. inspect_analysis_view refused it (unsupported_target), detail: "summary" was rejected, and an overflow offered only export.
Fix: the trace result gets one domain owner. A native-trace retained view adds a summary plus pages of references/matches/residual_unknowns with exact filters and source indexes. trace_feature accepts detail: "summary", and an oversized complete trace offers a references continuation.
Risk: additive. detail defaults to complete, the complete result is unchanged, the CLI is unchanged, and residual-Unknown recording is unchanged (one per unresolved owner).

Summary

Fixes #8373, the retained-view part (proposal: #8373 (comment)). It is the native counterpart of #8522 (JavaScript feature traces) and uses the same retained-view projector registry.

Problem and expected behavior

From the issue (real Kuna, 3,000–16,000 references): the trace reply reached 2–8.5 MB or overflowed. A filtered bundle summary found the trace ID, but inspect_analysis_view returned unsupported_target for both summary and native-observation, and trace_feature rejected detail: summary. Export/import was the only working route.

Expected contract: a bounded summary or pages that keep each source and target identity, unavailable reason, provider/profile and reference-cap coverage, with complete Evidence still accessible. An omitted page must not imply an absent reference. Independent Unknown revisions are preserved.

Change and scope

  • src/domain/native/literalFeatureTrace.ts (new owner): the result shape used to live only in toolOutputSchemaGroups.ts as literalTraceOutput. The contract output and the view now both parse with literalFeatureTraceResultSchema. literalReferenceOwner derives found / not-found / unavailable from the recorded containing_procedure without reinterpreting it.
  • src/domain/analysisView/nativeTraceView.ts, registered for trace_feature, so MCP and CLI inspect-analysis-view share it:
    • summary: query, search_mode, truncated, match counts by type, reference counts by owner outcome, and the residual-unknown count, with source provider/profile/parameters.
    • {kind:"native-trace", collection, where?, offset, limit}:
      • references filter by exact target_addresses (no address normalization) and owners;
      • matches filter by types;
      • residual_unknowns page the texts.
    • Rows keep source_index into the complete retained array, so duplicates stay distinct. truncated and the provider limitations travel with every page. Residual-unknown texts are paged rather than repeated in each view's unknowns; that matters with one Unknown per unavailable owner.
    • Parents must carry the rea.analysis predicate, the same check as other native views.
  • trace_feature detail: it uses the existing enhanced-tool summary delivery (as get_call_graph does). It refuses before analysis when the server retains no Evidence, and recordWorkflowUnknowns still runs before summary delivery.
  • Overflow continuation: {kind:"native-trace",collection:"references",offset:0,limit:64} for a retained trace.
  • Not included:
    • grouping or deduplicating residual Unknowns, which the issue's experiment showed must keep independent identity;
    • get_evidence_bundle summary size;
    • provider-side reference discovery.

Contract and boundary impact

  • Semantic owner and earliest changed stage: the trace result schema moved to domain/native. Consumers are the MCP output contract, the view projector, the delivery continuation and the CLI view. The superseded inline contract schema was removed.

  • Contribution scope fit and linked maintainer decision: read-only projection of retained Evidence. Proposal posted on [Design] Bound delivery of large native feature traces and their unknowns #8373. No new provider capability.

  • CLI and MCP/tool-catalog contract: trace_feature gains optional detail (default complete). Its output becomes the complete result or the summary view, via analysisDetailOutputSchemaOf. inspect_analysis_view gains native-trace. One description sentence was added. The CLI rea trace is unchanged.

  • Provider, bridge, target-format, or platform compatibility: provider-neutral projection of already returned facts; no provider call.

  • Evidence, artifact, provenance, or reconstruction contract: views reference the retained parent and keep its provider/profile/parameters. Owner outcomes come from recorded containing_procedure values, and page coverage is separate from discovery.

  • Target selection, authority, upstream behavior, and cleanup details: not applicable.

  • Generated metadata, package, or installation impact: none committed; docs:check and metadata:check pass.

  • Read existing files or captured data.

Evidence and regression coverage

  • Tests added or updated:
    • tests/boundary/mcp/nativeTraceViewsMcp.test.ts (new; production MCP registration with a fixture provider reporting 3 string matches, 1 procedure match, and references with found / not-found / unavailable owners; full and compact output profiles). It covers:
      • detail: summary retains the complete parent, its counts match the parent, and list_unknowns still holds one Unknown per unavailable owner;
      • the advertised input/output schemas validate the summary and the complete result;
      • small-page concatenation reproduces references (with derived owners), matches and residual_unknowns exactly;
      • exact owner, target and type filters;
      • [], case-variant addresses and past-end offsets return empty;
      • foreign views, unknown owners and unknown collections are rejected;
      • residual-unknown texts are not repeated in unknowns;
      • an oversized complete trace offers the references continuation, and a smaller page of it fits;
      • a non-retaining fixed server refuses detail: summary with no provider call.
      • a provider-capped trace keeps truncated: true and the reference-cap unknown on six views (summary reply, retained summary, one-row, owner-filtered, exhausted and unknown pages);
      • a references page carrying match rows fails both analysisViewResultSchema and the advertised inspect_analysis_view output schema under Ajv, since each collection is bound to its own rows.
    • tests/boundary/cli/analysisViewCli.test.ts: a saved trace_feature Evidence file paged with inspect-analysis-view (summary counts and the owners: ["unavailable"] page).
  • Base reproduction: the scale run below on a tree without this change. detail: summary returns invalid_request, and inspect_analysis_view returns unsupported_target / invalid_request. The new test file does not load on base because it imports the new domain module.
  • Remaining proof gaps:
    • No real Kuna/Ghidra/IDA run: no provider is installed on this host. The provider-neutral projection is exercised through the production enhanced-tool path with a fixture provider, which does not establish real-provider behavior.
    • No autonomous-agent study; token counts are byte/4 estimates.

Before/after at scale (synthetic, 8,000 references, all owners unavailable; production MCP registration in-process; macOS arm64, Node 24.22.1)

Step without this change this PR
trace_feature complete 2,336,969 B text (~584k est. tokens), 1,070 ms unchanged: 2,336,969 B, 803 ms
trace_feature detail: summary invalid_request 2,474 B (~620 est. tokens), 735 ms
inspect_analysis_view summary on the retained trace unsupported_target 2,474 B, 38 ms (first parse of the retained parent)
native-trace references (64) invalid_request 18,823 B, 3 ms
native-trace residual_unknowns (64) invalid_request 10,111 B, 1 ms
list_unknowns (64), for reference 65,983 B 65,983 B (unchanged)

Validation performed

  • After review (fd4130d65): npm run test:focused on nativeTraceViewsMcp (5/5), analysisViewMcp, outputSchemaProfile, outputSchemaSemanticConstraints, advertisedMcpTool, analysisViewCli, largeToolResult and traceFeatureCoverage: 8 files, 103/103 passed.
  • Before review: npm run test:focused on nativeTraceViewsMcp plus 12 related files (enhanced tools, trace coverage, input validation, Ghidra routing, IDA readiness trace, prompts, CLI tool coverage, analysis selectors, output schema profiles, analysis views, large results, CLI analysis views): 13 files, 144/144 passed.
  • npm run test:changed: 217 files, 4236 passed, 3 skipped.
  • npm run check:fast, npm run format:check, npm run docs:check, npm run metadata:check: passed.
  • The scale before/after above.

Compatibility, safety, and release

  • Breaking changes or migration steps: none. detail is optional with default complete; the output union is a superset.
  • Real Hopper/Ghidra, browser, or OS coverage: none on this host (see the gaps above).
  • Package or release metadata impact: none.
  • Security, privacy, process, or containment review: read-only projection; no new paths, processes or provider calls.
  • Merge note: feat(javascript): page retained feature traces through analysis views #8522 refactors the same continuation factory in src/server/toolResult.ts. Whichever lands second needs a one-line merge of the trace_feature entry into ownerFirstPage.

Author readiness

Human owner: @kaoru0822-kitauji

  • I reviewed the final diff and relevant existing code, understand the change and its edge cases, and take responsibility for the complete PR, including AI-assisted work.
  • I checked the evidence above, confirmed it supports the current change, and recorded meaningful validation gaps.
  • I declare this PR ready for initial maintainer review.

Before merge

  • This PR addresses a concrete problem or an agreed enhancement.
  • Material scope and authority questions are resolved, and any required maintainer scope decision covers the final diff.
  • The PR has one focused outcome and the title follows type(scope): outcome.
  • Related issue is linked, or the reason for not linking one is stated above.
  • Tests cover changed observable behavior and meaningful failure paths.
  • Owning docs, contracts, and generated metadata are updated where needed.
  • User-visible CLI/MCP changes include representative output.
  • I checked the final diff for secrets, unrelated cleanup, and unsupported claims.

🤖 Generated with Claude Code

A large trace_feature result can carry thousands of references with
unavailable owners. inspect_analysis_view refused it as an unsupported
parent and trace_feature rejected detail: summary, so agents had to
transfer the complete result or export the session.

- Give the trace result one domain owner (literalFeatureTrace.ts) used by
  the tool output contract and the new view.
- Add a native-trace view: a summary with match counts by type, reference
  counts by owner outcome and the residual-unknown count, and pages of
  references, matches and residual_unknowns in retained order with exact
  filters and source indexes. Residual unknowns are paged rather than
  repeated in every view.
- Accept detail: summary on trace_feature through the existing enhanced
  summary delivery; session Unknowns are recorded as before.
- Offer a ready-to-call first references page when a retained complete
  trace exceeds the MCP response budget.

Fixes #8373

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@kaoru0822-kitauji kaoru0822-kitauji added enhancement New feature or request track:feature Feature/enhancement automation track labels Nov 1, 2026
@chatgpt-codex-connector

chatgpt-codex-connector Bot commented Nov 1, 2026 •

Copy link
Copy Markdown

Codex Review Summary

This comment shows the latest Codex review activity on this pull request.

Review Status Commit Review trigger
📝 Code Review ✅ Completed 2026-11-01T15:14:44.450248Z fd4130d New commits
ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review" or "@codex security review".

Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@greptile-apps

greptile-apps Bot commented Nov 1, 2026 •

Copy link
Copy Markdown
Contributor

RetriggerView in GreptileConfidence Score: 5/5 Tier: apex

[Medium impact] The PR appears safe to merge; both earlier findings are addressed and no new blocking issue was found.

Summary

Adds summaries and filtered pages for retained native trace_feature results while preserving complete Evidence and independent Unknown records.

  • Native feature traces can now be summarized and paged.

Diagram

%%{init: {'theme': 'neutral'}}%%
flowchart LR
  T["trace_feature"] --> P["Retain complete Evidence"]
  P --> S["Return summary"]
  P --> V["inspect_analysis_view"]
  V --> R["references"]
  V --> M["matches"]
  V --> U["residual_unknowns"]
Loading

Reviews (2) · Last reviewed commit: "fix(native): bind native-trace pages to ..." · Reviewed by Greptile

Comment on lines +970 to +971
view: nativeTraceViewRequestSchema,
items: nativeTraceViewItemsSchema,

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Wrong rows pass output checks

The output schema checks view.collection and items independently. A references page containing only match or unknown rows would still pass, so clients cannot use the advertised schema to catch a wrong-collection reply. Bind each collection to its own row schema, as machoPage already does for facets.

Prompt To Fix With AI
This is a comment left during a code review.
Path: src/domain/analysisView/analysisViewResult.ts
Line: 970-971

Comment:
**Wrong rows pass output checks**

The output schema checks `view.collection` and `items` independently. A `references` page containing only `match` or `unknown` rows would still pass, so clients cannot use the advertised schema to catch a wrong-collection reply. Bind each collection to its own row schema, as `machoPage` already does for facets.

---

For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed, fixed in fd4130d65.

Root cause: items was a union of row arrays, independent of view.collection.

Fix: nativeTraceViewCollections in nativeTraceView.ts binds each collection's request schema to its own row schema. The page result is a kind-tagged union of one strict page per collection, following the machoPage pattern. The projector builds each page in its own correlated branch.

Validation: a references page whose items are replaced with match rows now fails both analysisViewResultSchema and the advertised inspect_analysis_view output schema under Ajv; the unmodified page passes both. 8 related files, 103 tests passed.

Comment on lines +66 to +69
case "xrefs":
return ok(
createAnalysisExecution([...(SOURCES[address] ?? [])], PROVIDER),
);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Capped traces lack view tests

The new view tests never set referencesTruncated and only assert truncated: false. They would not catch a later change that drops the reference-cap warning from summaries or pages. Add a provider-capped trace and check that its summary, filtered pages and exhausted pages retain truncated: true and the cap warning. The existing producer tests do not exercise this projection.

Prompt To Fix With AI
This is a comment left during a code review.
Path: tests/boundary/mcp/nativeTraceViewsMcp.test.ts
Line: 66-69

Comment:
**Capped traces lack view tests**

The new view tests never set `referencesTruncated` and only assert `truncated: false`. They would not catch a later change that drops the reference-cap warning from summaries or pages. Add a provider-capped trace and check that its summary, filtered pages and exhausted pages retain `truncated: true` and the cap warning. The existing producer tests do not exercise this projection.

---

For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.

@kaoru0822-kitauji kaoru0822-kitauji Nov 1, 2026 •

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed, fixed in fd4130d65. The fixture provider can now report referencesTruncated for the first match. A new test checks six views of that capped trace: the detail: summary reply, the retained summary, a one-row references page, an owner-filtered page, an exhausted matches page and the residual-unknown page. Each keeps truncated: true and both the coverage and reference-cap unknowns. Those messages are now exported constants from their owner, so the test compares owning values rather than prose.

Review follow-up.

- Advertise each native-trace page with exactly its own row schema, so a
  references page cannot validate with match or unknown rows.
- Export the coverage and reference-cap unknowns from their owner and
  verify a provider-capped trace keeps truncated and the cap warning on
  its summary, filtered, exhausted and unknown pages.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
kaoru0822-kitauji added a commit that referenced this pull request Nov 1, 2026
Advertise each feature-trace page with exactly its own row schema, so a
paths page cannot validate with node, edge, seed-match or handoff rows.
The native-trace view in #8533 received the same review finding; the two
sibling views now share one strict page contract.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
kaoru0822-kitauji added a commit that referenced this pull request Nov 1, 2026
…#8522)

* feat(javascript): page retained feature traces through analysis views

A bidirectional trace_application_feature result can exceed one MCP
response, and inspect_analysis_view refused trace parents as unsupported,
so the only recovery was exporting the whole session.

- Add a shared feature-trace view owner: a summary with the trace's
  identity, producer counts and coverage, and pages of paths, nodes,
  edges, seed_matches and native_handoffs in retained order with exact
  filters. Node rows are compact unless observations are requested.
  Page coverage never upgrades trace coverage.
- Accept an optional MCP view on trace_application_feature that retains
  the complete trace before returning the selected facts; the CLI keeps
  complete JSON and reads saved traces with inspect-analysis-view.
- Offer a ready-to-call first paths page when a retained complete trace
  exceeds the MCP response budget.
- Share the distinct authority/state/confidence basis helper with
  module references.

Fixes #8296

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

* fix(javascript): name the retained parent when a selected view overflows

Review follow-up for the feature-trace views.

- Share one delivery owner between trace_application_feature and
  compare_source_to_bundle: stage the selected view against the
  completed parent, keep the established contract that a cancelled
  request commits no session facts, then commit sources and the parent.
- A selected view that exceeds the response budget now references the
  retained parent and offers the same selection at half its limit,
  instead of naming the view record, which cannot be a view parent.
- Cover two native handoffs paged one at a time, the oversized selected
  page, and cancellation after the trace completes.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

* fix(javascript): bind feature-trace pages to their collection rows

Advertise each feature-trace page with exactly its own row schema, so a
paths page cannot validate with node, edge, seed-match or handoff rows.
The native-trace view in #8533 received the same review finding; the two
sibling views now share one strict page contract.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

* test(javascript): mix valid rows from another collection into a trace page

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement New feature or request track:feature Feature/enhancement automation track

1 participant