Skip to content

refactor(tests): migrate the remaining features to the snap framework - #556

Merged
16bit-ykiko merged 4 commits into
mainfrom
refactor/snap-remaining-features
Jul 28, 2026
Merged

16bit-ykiko merged 4 commits into
mainfrom
refactor/snap-remaining-features

Conversation

@16bit-ykiko

Copy link
Copy Markdown
Member

What

Completes the snap-test migration started in the framework refactor: hover, document_symbol, inlay_hint and document_links move to tests/snap/, and every legacy snapshot mechanism retires. All six features are now pinned from both paths — clice inspect (standalone, no PCH) and a real server over LSP — into shared, byte-identical snapshot files.

Marker channel

Fixture § annotations become the parameter channel for inspect, so feature parameters live in the file itself:

  • Point markers (§(name)): position features run once per point — hover produces one payload per marker, keyed by name (nameless_<i> for unnamed ones).
  • Range markers (§(name)⟦...⟧): range features run once per marked range — inlay hints scope their request to the marked region, falling back to the whole document when a fixture marks nothing.

The server never sees a marker: both paths strip them at the entrance with the existing twin parsers, and the sha256 handshake keeps the coordinate space honest. On the wire side the harness holds the offsets and issues one request per marker, exactly like a real editor would.

Per-feature notes

  • hover: shared worked out of the box across all 25 fixtures — inspect emits the feature-layer reply (markdown from the same rendering code the server uses, symbol range still in byte offsets) and the wire replay matched byte-for-byte on the first run. The corpus CDB pins --target=x86_64-unknown-linux-gnu because HoverInfo carries sizeof/alignof facts that differ between LP64 and LLP64 hosts.
  • document_symbol / inlay_hint: shared; the TS renderers carry the two kind-mapping twins (clice SymbolKind → LSP SymbolKind, HintCategory → InlayHintKind), pinned against drift by the shared files.
  • document_links: shared; raw payloads carry file paths, so a path-domain sibling of the URI validator rewrites and checks them into the same ${WS}/... form the wire side pins.
  • Per-corpus compile flags are a small table now (document_links needs -I + C++23; hover pins the triple).

Retired

  • The legacy wire driver and the wire-only corpora path in the snap suite.
  • The migrated TEST_CASE(snapshot) globs in the hover, document_symbol and inlay_hint unit tests (granular unit cases stay).
  • tests/snapshots/integration/ entirely, and the migrated tests/snapshots/unit/ subtrees (tu_index and the hover presentation cases remain on zest).

Verification

  • Cross-checks before deletion: document_symbol, inlay_hint and document_links snapshot bodies are byte-identical to the old integration pins; every hover fixture marker appears exactly once in its new snapshot, with NO-HOVER parity against the old unit dumps.
  • All four suites green on RelWithDebInfo and Debug locally (a handful of pre-existing Debug integration tests flake under full parallel load on a busy machine — they pass in isolation and are untouched by this diff; CI runners arbitrate).
  • The behavioral document_links integration tests keep running against the corpus at its new home via the session factory's snap/<feature> addressing.

The fixture's § annotations become the parameter channel: position
features (hover) run once per point, range features (inlay_hint) once
per range with a whole-document default, keyed into the new markers
field of the envelope. hover emits the feature-layer reply before the
edge — markdown from the same rendering code the server uses, with the
symbol range still in byte offsets. The feature dispatch grows into a
table covering document_links, document_symbol, folding_range, hover,
inlay_hint and semantic_tokens.
The four remaining corpora move to tests/snap with their snapshots
pinned from both paths (hover shares byte-identical markdown between
inspect and the wire replay; the hover CDB pins the target triple since
HoverInfo carries sizeof facts). The legacy wire driver, the migrated
unit TEST_CASE(snapshot) globs and their snapshot trees retire; the
tests/snapshots/integration tree is gone entirely. Cross-checked before
deletion: document_symbol, inlay_hint and document_links bodies are
byte-identical to the old integration pins, and every hover fixture
marker appears exactly once in its new snapshot.
@coderabbitai

coderabbitai Bot commented Jul 28, 2026 •

Copy link
Copy Markdown

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: c5eedbba-8c0a-4077-bc5c-c0fb28c10996

📥 Commits

Reviewing files that changed from the base of the PR and between 32894b4 and d8238bc.

📒 Files selected for processing (4)
  • tests/unit/feature/folding_range_tests.cpp
  • tests/unit/test/annotation_tests.cpp
  • tests/unit/test/fixture.h
  • tests/unit/test/snap_region.h
💤 Files with no reviewable changes (4)
  • tests/unit/feature/folding_range_tests.cpp
  • tests/unit/test/snap_region.h
  • tests/unit/test/fixture.h
  • tests/unit/test/annotation_tests.cpp

📝 Walkthrough

Walkthrough

The inspect CLI now supports registry-driven marker results for additional language features. Snap tooling renders marker-scoped outputs, generates feature-specific compile databases, and removes legacy wire corpus handling. New document-link, document-symbol, hover, and inlay-hint fixtures move into the current snap corpus.

Changes

Inspect and snapshot pipeline

Layer / File(s) Summary
Registry-based inspect execution
src/driver/inspect.cc
Feature execution now uses a registry with marker-aware results for hover, document links, document symbols, inlay hints, folding ranges, and semantic tokens.
Marker-aware rendering and normalization
tools/snap/annotation.ts, tools/snap/inspect.ts, tools/snap/presenters.ts, tools/snap/snapshot.ts, tools/snap/standalone.ts
Snapshot renderers consume ordered marker points/ranges, format raw feature results, render hover and inlay-hint sections, and normalize workspace-relative document-link targets.
Wire and corpus generation migration
tools/compile_commands.ts, tools/snap/wire.ts, tests/snap/snap.test.ts, tests/unit/feature/*
Compile database generation and wire presenters target current snap fixtures, while legacy corpus generation and snapshot test cases are removed.

Snap fixtures

Layer / File(s) Summary
Document feature fixtures
tests/snap/document_links/*, tests/snap/document_symbol/*, tests/integration/features/document_links.test.ts
Document-link fixtures cover spaces, reserved characters, UTF-8 names, and embeds; document-symbol fixtures cover nested C++ declarations.
Hover fixture corpus
tests/snap/hover/*
New hover inputs and snapshots cover deduction, templates, declarations, expressions, calls, values, scopes, operators, documentation, and no-hover cases.
Inlay-hint fixture
tests/snap/inlay_hint/*
The inlay-hint fixture covers parameter hints, inferred types, references, and formatting-sensitive source layout.
Snap documentation
.claude/CLAUDE.md, .claude/skills/write-tests/SKILL.md
Snap-test guidance now describes the current tests/snap/<feature>/ corpus without the legacy corpus path.

Estimated code review effort: 5 (Critical) | ~120 minutes

Possibly related PRs

  • clice-io/clice#537: Adds the marker and snap-region annotation model used by the marker-driven inspect and snapshot flow.
  • clice-io/clice#555: Introduces the inspect command and earlier feature payload handling extended by this change.
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 4.67% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately summarizes the main change: migrating the remaining tests to the snap framework.
Description check ✅ Passed The description is directly related to the changeset and explains the snap-test migration and marker-based flow.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch refactor/snap-remaining-features

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: fc2cf8204a

ℹ️ 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".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread tests/integration/features/document_links.test.ts
Comment thread tools/snap/inspect.ts

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 4

🧹 Nitpick comments (3)
tools/snap/snapshot.ts (1)

87-101: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Duplicates the tail of normalizeFileUri.

Lines 94-100 are byte-identical to lines 74-80 apart from the error message. Extracting a shared relativizeToWorkspace(fsPath, workspace, describe) keeps the two validators from drifting.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@tools/snap/snapshot.ts` around lines 87 - 101, Extract the shared
workspace-relative path logic from normalizeFilePath and normalizeFileUri into a
helper such as relativizeToWorkspace(fsPath, workspace, describe). Have both
validators reuse it while preserving their distinct validation and error-message
behavior, then apply the existing workspace placeholder formatting consistently.
src/driver/inspect.cc (2)

358-358: 🩺 Stability & Availability | 🔵 Trivial | 💤 Low value

Unchecked dereference of find_feature.

Safe today because run_inspect validates first, but process_file is a separate entry point; an assertion or early error would keep it safe under refactoring.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/driver/inspect.cc` at line 358, Handle a missing result from find_feature
before dereferencing it in process_file: add an assertion or early error path
for the absent feature, then only construct spec after validation. Preserve the
existing behavior for valid features.

148-171: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Consider enforcing the "exactly one shape" invariant.

Nothing prevents a future FeatureSpec entry from leaving all three pointers null, which process_file turns into a null function-pointer call on the run_over fallthrough. A static_assert over the table (exactly one non-null pointer per spec) would keep the invariant where the table lives.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/driver/inspect.cc` around lines 148 - 171, Enforce the one-shape
invariant for every entry in the constexpr features table by adding a
compile-time assertion that exactly one of FeatureSpec::run,
FeatureSpec::run_at, or FeatureSpec::run_over is non-null. Place the validation
alongside the features definition so invalid entries fail during compilation
before process_file can dispatch through a null pointer.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/driver/inspect.cc`:
- Around line 187-196: The range marker ordering is inconsistent between the C++
and TypeScript consumers. In src/driver/inspect.cc lines 187-196, update
marker_ranges to establish and document the canonical ordering, preferably
grouping nameless markers last to match marker_points; in tools/snap/inspect.ts
lines 421-434, update sortedMarkers to implement that same ordering so wire and
standalone snapshots remain byte-identical.
- Around line 137-146: Update run_hover to distinguish absent hover information
from serialization failure: preserve the empty RawValue for a missing hover, but
return a distinct failure state when to_raw_json(result) cannot serialize.
Propagate that state through the caller, process_file, so it sets entry.error
consistently with the whole-document serialization path instead of recording NO
HOVER.

In `@tests/snap/hover/using_decls.snap.yml`:
- Line 17: Refresh the stale snapshot marker ranges in
tests/snap/hover/using_decls.snap.yml:17-17 and
tests/snap/hover/variables.snap.yml:55-55, updating them to the corresponding
fixture lines: 19:35-19:38 and 41:17-41:20 respectively.

In `@tools/snap/inspect.ts`:
- Around line 376-393: Update renderRawInlayHints so an unmapped hint.kind does
not fall back to the raw clice category name; instead, fail loudly when
LSP_INLAY_KIND lacks the value. Preserve the existing mapped-kind output and
remaining hint formatting.

---

Nitpick comments:
In `@src/driver/inspect.cc`:
- Line 358: Handle a missing result from find_feature before dereferencing it in
process_file: add an assertion or early error path for the absent feature, then
only construct spec after validation. Preserve the existing behavior for valid
features.
- Around line 148-171: Enforce the one-shape invariant for every entry in the
constexpr features table by adding a compile-time assertion that exactly one of
FeatureSpec::run, FeatureSpec::run_at, or FeatureSpec::run_over is non-null.
Place the validation alongside the features definition so invalid entries fail
during compilation before process_file can dispatch through a null pointer.

In `@tools/snap/snapshot.ts`:
- Around line 87-101: Extract the shared workspace-relative path logic from
normalizeFilePath and normalizeFileUri into a helper such as
relativizeToWorkspace(fsPath, workspace, describe). Have both validators reuse
it while preserving their distinct validation and error-message behavior, then
apply the existing workspace placeholder formatting consistently.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: 3d395b59-cac5-4ba9-87da-b572060727fe

📥 Commits

Reviewing files that changed from the base of the PR and between b0fc458 and fc2cf82.

⛔ Files ignored due to path filters (1)
  • tests/snap/document_links/data.bin is excluded by !**/*.bin
📒 Files selected for processing (107)
  • .claude/CLAUDE.md
  • .claude/skills/write-tests/SKILL.md
  • src/driver/inspect.cc
  • tests/integration/features/document_links.test.ts
  • tests/snap/document_links/café.h
  • tests/snap/document_links/escapes.cpp
  • tests/snap/document_links/escapes.snap.yml
  • tests/snap/document_links/hash#header.h
  • tests/snap/document_links/header_a.h
  • tests/snap/document_links/header_b.h
  • tests/snap/document_links/header_c.h
  • tests/snap/document_links/main.cpp
  • tests/snap/document_links/main.snap.yml
  • tests/snap/document_links/plus+header.h
  • tests/snap/document_links/reserved.cpp
  • tests/snap/document_links/reserved.snap.yml
  • tests/snap/document_links/sub dir/escaped header.h
  • tests/snap/document_symbol/.clang-format
  • tests/snap/document_symbol/basic.cpp
  • tests/snap/document_symbol/basic.snap.yml
  • tests/snap/hover/.clang-format
  • tests/snap/hover/attributes.cpp
  • tests/snap/hover/attributes.snap.yml
  • tests/snap/hover/auto.cpp
  • tests/snap/hover/auto.snap.yml
  • tests/snap/hover/basics.cpp
  • tests/snap/hover/basics.snap.yml
  • tests/snap/hover/callee_args.cpp
  • tests/snap/hover/callee_args.snap.yml
  • tests/snap/hover/concepts.cpp
  • tests/snap/hover/concepts.snap.yml
  • tests/snap/hover/decltype.cpp
  • tests/snap/hover/decltype.snap.yml
  • tests/snap/hover/docs.cpp
  • tests/snap/hover/docs.snap.yml
  • tests/snap/hover/expressions.cpp
  • tests/snap/hover/expressions.snap.yml
  • tests/snap/hover/fields.cpp
  • tests/snap/hover/fields.snap.yml
  • tests/snap/hover/functions.cpp
  • tests/snap/hover/functions.snap.yml
  • tests/snap/hover/getter_setter.cpp
  • tests/snap/hover/getter_setter.snap.yml
  • tests/snap/hover/lambdas.cpp
  • tests/snap/hover/lambdas.snap.yml
  • tests/snap/hover/misc.cpp
  • tests/snap/hover/misc.snap.yml
  • tests/snap/hover/no_hover.cpp
  • tests/snap/hover/no_hover.snap.yml
  • tests/snap/hover/no_hover_errors.cpp
  • tests/snap/hover/no_hover_errors.snap.yml
  • tests/snap/hover/pass_types.cpp
  • tests/snap/hover/pass_types.snap.yml
  • tests/snap/hover/spaceship.cpp
  • tests/snap/hover/spaceship.snap.yml
  • tests/snap/hover/tag_decls.cpp
  • tests/snap/hover/tag_decls.snap.yml
  • tests/snap/hover/template_params.cpp
  • tests/snap/hover/template_params.snap.yml
  • tests/snap/hover/templates.cpp
  • tests/snap/hover/templates.snap.yml
  • tests/snap/hover/this_expr.cpp
  • tests/snap/hover/this_expr.snap.yml
  • tests/snap/hover/using_decls.cpp
  • tests/snap/hover/using_decls.snap.yml
  • tests/snap/hover/values.cpp
  • tests/snap/hover/values.snap.yml
  • tests/snap/hover/variables.cpp
  • tests/snap/hover/variables.snap.yml
  • tests/snap/inlay_hint/.clang-format
  • tests/snap/inlay_hint/basic.cpp
  • tests/snap/inlay_hint/basic.snap.yml
  • tests/snap/snap.test.ts
  • tests/snapshots/unit/document_symbol/snapshot/basic.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/attributes.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/auto.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/basics.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/callee_args.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/concepts.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/decltype.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/docs.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/expressions.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/fields.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/functions.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/getter_setter.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/lambdas.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/misc.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/pass_types.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/spaceship.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/tag_decls.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/template_params.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/templates.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/this_expr.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/using_decls.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/values.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/variables.cpp.snap.yml
  • tests/snapshots/unit/inlay_hint/snapshot/basic.cpp.snap.yml
  • tests/unit/feature/document_symbol_tests.cpp
  • tests/unit/feature/hover_tests.cpp
  • tests/unit/feature/inlay_hint_tests.cpp
  • tools/compile_commands.ts
  • tools/snap/annotation.ts
  • tools/snap/inspect.ts
  • tools/snap/presenters.ts
  • tools/snap/snapshot.ts
  • tools/snap/standalone.ts
  • tools/snap/wire.ts
💤 Files with no reviewable changes (28)
  • tests/snapshots/unit/hover/snapshot/getter_setter.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/template_params.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/using_decls.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/this_expr.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/pass_types.cpp.snap.yml
  • tests/snapshots/unit/document_symbol/snapshot/basic.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/functions.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/docs.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/expressions.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/tag_decls.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/attributes.cpp.snap.yml
  • tests/snapshots/unit/inlay_hint/snapshot/basic.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/misc.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/values.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/fields.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/templates.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/spaceship.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/callee_args.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/concepts.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/lambdas.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/variables.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/basics.cpp.snap.yml
  • tests/unit/feature/inlay_hint_tests.cpp
  • tests/snapshots/unit/hover/snapshot/auto.cpp.snap.yml
  • tests/snapshots/unit/hover/snapshot/decltype.cpp.snap.yml
  • tests/unit/feature/hover_tests.cpp
  • tests/unit/feature/document_symbol_tests.cpp
  • tools/compile_commands.ts

Comment thread src/driver/inspect.cc Outdated
Comment thread src/driver/inspect.cc
Comment thread tests/snap/hover/using_decls.snap.yml
Comment thread tools/snap/inspect.ts
- Integration setup generates the snap-corpus CDBs too: behavioral tests
  borrow snap workspaces (document links) and must not run on synthesized
  default commands by luck.
- nameless_<i> is a reserved marker namespace in both annotation twins; a
  named annotation using it fails loudly instead of colliding.
- Wire markerRanges orders named-then-nameless like every other consumer.
- Hover serialization failure is now distinct from NO HOVER (and range
  features report serialize_error instead of snapshotting null).
- An unmapped inlay-hint kind throws instead of leaking the raw name into
  a shared snapshot.
extract_snap_regions and fixture_frontmatter lost their last real
consumers when the feature snapshot globs migrated to tests/snap; only
their own tests kept them alive. tu_index (zest glob) and the hover
presentation cases are the only unit snapshot users left.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant