Repository navigation
refactor(engine): split exec.rs into modules with no behaviour change - #6648
Conversation
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
🔎 Codex reviewer —
|
exec.rs was ~22.8k lines. Its 46 inline modules (state registries and test modules) move to exec/<name>.rs unchanged, and the top-level code moves into 17 topical modules (entry points, algebra dispatch, BGP, WCOJ, joins, anti-join, aggregation, modifiers, expressions, compiled expressions, ...), following the file's existing section banners. exec.rs keeps the shared types (Row, Bindings, LocalVocab) and the module wiring; each new module does 'use super::*' and exec.rs glob-imports them back, so every existing path (crate::exec::foo) still resolves. Moved private items become pub(super), the narrowest visibility that keeps sibling access. The yannakakis prepass items were each behind cfg(feature = "yannakakis"); that gate now sits once on `mod yannakakis;` and its `use`, which compiles the same items in the same configurations. Model tags are stripped from the moved comments and from the comments left in exec.rs. The sparql-query skill points at the new columnar_filter_seam path. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
Leg 3 of check-vectorized-feature-off.py read only exec.rs, so after the split it no longer saw the vectorized call sites that moved to exec/expr.rs. It now scans exec.rs, every .rs file under exec/, and the #[path] child eqjoin.rs. A module whose `mod` declaration is gated on `vectorized` counts as gated as a whole. Tripwire: leg 3 resolves every `mod x;` that exec.rs (or a scanned child) declares, following rustc's #[path] and nested-module rules, and fails if the file is not in the scanned set. An indented out-of-line declaration it cannot resolve also fails. --self-test and the script's test suite gain three leg-3 cases (ungated child, unscanned child, gated tree accepted). The bench declaration covers the feature-OFF wasm byte move from the split (file!/line! metadata and codegen order). Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
ae0d999 to
5def071
Compare
🔎 Codex reviewer —
|
Same-line attributes: a declaration like `#[path = "elsewhere.rs"] mod x;` was skipped because the matcher required the line to start with `mod`, so an out-of-tree child escaped the unscanned-module tripwire. Leg 3 now strips any number of leading attributes (string-aware, any spacing) on the declaring line and preceding lines, accepts pub / pub(crate) / pub(super), and fails closed on any `mod x;` it cannot parse or whose file does not exist. cfg gates: the module-gate regex accepted `cfg(all(not (feature = "vectorized")))` because it only looked for `not(` without a space. Leg 3 now parses the cfg predicate (all / any / not, whitespace-insensitive) and treats a module as gated only when every configuration satisfying the predicate enables `vectorized`. Anything under not(...) counts as not gating. --self-test gains tripwires 9-12 and the test suite gains five cases, covering same-line attribute spellings, non-gating cfgs with whitespace variants, an unresolvable module, gating cfg spellings, and the parser itself. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
🔎 Codex reviewer —
|
…tion cfg_attr paths: `#[cfg_attr(<pred>, path = "x.rs")] mod child;` makes rustc compile x.rs under <pred>, but leg 3 audited the default child.rs. Leg 3 does not model that: any cfg_attr whose arguments mention `path` (outside a string literal) on a mod declaration, on the same line or a preceding attribute line, now fails as unsupported. A multi-line attribute before a declaration also fails, because its content cannot be read line by line. Plain #[path] is still resolved as before. Gating: when two declarations reached one file, a single gated declaration exempted it even if the other was ungated. Leg 3 now collects every declaration first. A file counts as gated only if every declaration reaching it is gated, by its own cfg or because its declaring file is gated. Descendants inherit the result. --self-test gains tripwires 13 and 14 and the test suite gains four cases, covering cfg_attr(path) spellings, path-free cfg_attr, gated plus ungated declarations in both orders with a descendant, and all-gated declarations. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
🔎 Codex reviewer —
|
`#[path = r"elsewhere.rs"] mod child;` was not recognised, so leg 3 audited the default exec/child.rs while rustc compiles elsewhere.rs. Leg 3 no longer tries to model rustc's string syntax. An attribute on a `mod` declaration whose text contains the token `path` (outside a `doc = "..."` string) is accepted only in the simple form `#[path = "<plain chars>"]`: a normal string with no backslash or quote, optional whitespace. Every other spelling fails the audit as unsupported, including raw, raw-hash, escaped and byte strings, cfg_attr(..., path = ...) and macros. A declaration with more than one path attribute also fails. --self-test gains tripwire 15 and the test suite gains one case. The fixture has a clean fallback exec/child.rs and an ungated elsewhere.rs, and covers r"...", r#"..."#, an escaped string, a byte string, concat!() and a duplicate path. A doc string mentioning `path` is still accepted. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
🔎 Codex reviewer —
|
…clarations
Any line whose code holds the mod keyword must now be an inline
mod name { or a declaration the parser understands; raw identifiers
(mod r#x;) are resolved, and mod split from its name fails as
unparseable. Tripwire 16 covers both.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
🔎 Codex reviewer —
|
…ne line A line like 'mod child; #[path = "x.rs"] mod hidden;' was audited only for its first declaration. More than one mod keyword on a line, or code after a declaration, now fails as unsupported; tripwire 16 covers it. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
🔎 Codex reviewer —
|
…osed on odd attributes A trailing // comment after #[path = ...] dropped the attribute, so the audit scanned the default file instead. Comments are now stripped outside string literals, and an attribute line it cannot parse, or a block comment between the attributes and the mod, fails as unsupported. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
🔎 Codex reviewer —
|
…any block An inline module's #[path] changes where its children live, and indentation did not reliably detect nesting. Brace depth (outside strings, chars and // comments) now does: a mod x; at depth > 0 fails as unsupported. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
🔎 Codex reviewer —
|
The split is scripted, so it is regenerated on main rather than merged by hand: inline mod blocks move to exec/<name>.rs, the top-level sections move to 17 modules re-exported at their visibility, yannakakis is gated at the mod declaration, and model tags are stripped from moved comments. Leg 3 of the vectorized feature-off audit also scans the three #[path] children main added since (exists_domain, numeric_capacity, nullable_path_tests). Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
🔎 Codex reviewer —
|
Requested by Jesse · project thread
Summary
Before:
crates/sparq-engine/src/exec.rswas one 23,844-line file. Any engine change conflicted with every other open engine PR, and agents had to page through the whole file.After:
exec.rsis 851 lines of shared types (Row,Bindings,LocalVocab, budget glue) and module wiring. The rest lives inexec/, 65 files, the largest 3,453 lines. Query behaviour is unchanged.How:
mod x { … }blocks (state registries and test modules) move verbatim toexec/x.rs, de-indented one level. Lines inside multi-line string literals are left byte-identical.entry,dispatch,sargable,spatial_pushdown,bgp,triple_terms,yannakakis,planning,wcoj,compose,antijoin,aggregation,modifiers,expr,compiled,terms,sip_rewrite.use super::*, andexec.rsglob-imports it back at the matching visibility, so every existing path such ascrate::exec::eval_selectstill resolves. Moved private items becomepub(super), the narrowest visibility that keeps sibling access.yannakakisis now gated at themoddeclaration instead of per item.pub(super)) shows only themod/usewiring and the yannakakis gates differ. Both sides have 241#[test].[OPUS-x],[FABLE-5]) are stripped from moved and remaining comments.scripts/check-vectorized-feature-off.pyleg 3 now scansexec.rs, every file underexec/, and the#[path]children outsideexec/(eqjoin.rs, which the old audit also missed, andexists_domain.rs,numeric_capacity.rsandnullable_path_tests.rs). It fails if anymoddeclared under exec resolves to a file it doesn't scan. After the split the vectorized references live underexec/, so the old leg 3 would have passed while scanning none of them.--self-testgains three tripwires.The split is scripted, so it was regenerated on main
f4e7b56crather than rebased by hand. The regenerated tree is one merge commit on top of the earlier branch, so no history was rewritten.Base gate (always required)
cargo clippy -p sparq-engine --all-targets(default and--all-features) with-D warningsis cleancargo check -p sparq-engine --all-targets --features Xpasses for each of the 32 engine features, plus--no-default-features;sparq-wasmchecks for wasm32cargo test -p sparq-enginepasses (57 suites, 957 passed, 0 failed)Targeted re-evaluation
Ratchets and conventions
skills/sparql-query/SKILL.mdnow points at the movedcolumnar_filter_seammodule.Benchmark
/mnt/project-files/engine/bench/ab.shoperators suite, mainf4e7b56cagainst this head, 15 interleaved rounds of best-of-10, run in both orders. Row counts match on all 28 queries.q12_filter_exists0.997 and 1.003.q12_filter_existsabout 9% andq06_optionalabout 7% slower in both orders.The code is identical and the shipping profile is at noise, so the release-fast gap is codegen-unit partitioning following the new module boundaries.
🤖 Generated with Claude Code
https://claude.ai/code/session_01C1gMf8RJim1LzuKapZNpZR
Generated by Claude Code
Generated by Claude Code