feat(tui): generate word-navigation napi bindings via fluessig#308
Conversation
Conformance smoke: agent + ai + tui
Headline is rust-backed: passing cases in files whose module-under-test is a native (Rust addon) module. Raw all-pass is shown secondary — it is inflated by unflipped TypeScript that passes without touching any Rust.
agent: 73/180 (40.6%) · ai: 81/1296 (6.3%) · tui: 375/678 (55.3%) rust-backed = passing / total tests run, per the manifest's per-native-row AttributionA pi test file is rust-backed iff the module it primarily exercises — its module-under-test — is Per-file decisions (from each native manifest row's
CLI conformance (black-box, against the pidgin binary)
The four repointed coding-agent CLI test files spawn the compiled pidgin binary via |
24d23e8 to
825cd50
Compare
Swap the tui word-navigation exports (`findWordBackward`, `findWordForward`) from hand-written `#[napi]` free functions to fluessig-generated bindings, routing through the `PidginCore` trait + `core_impl` seam like modules 1-4. Both ops are `(text: string, cursor: int32) -> int32`; cursors are UTF-16 string indices authored as `int32` (JS `number`) and widened to the engine's `usize` at the seam, delegating into `pidgin_tui::word_navigation`'s default-segmenter path. The native shim still delegates to pi's original when `options.segment`/`options.isAtomicSegment` are supplied. The generated `.d.ts` blocks (JSDoc included) and `.js` glue are byte-identical to the pre-swap baseline. Verified: cargo build/fmt/clippy clean, codespell clean, and pi's own `word-navigation.test.ts` oracle passes 19/19 against the locally-built addon.
18158ba to
e549210
Compare
Stacked on #307 (module 4, tui utils/width). Base branch is
napi-fluessig/tui-utils, so this diff is just the twoword-navigation.tsexports.Before / After
The
packages/tui/src/word-navigation.tslayer —findWordBackwardandfindWordForward— used to be hand-written#[napi]free functions inlib.rs. After this change they are generated from the fluessig api schema throughcrate::generated+ thecore_implseam, routing intopidgin_tui::word_navigation's default-segmenter path.The JS surface is unchanged: every symbol's
.d.tsblock (JSDoc included) and.jsglue is byte-identical to the pre-swaporigin/mainbaseline, and the dedicated conformance oracle (packages/tui/test/word-navigation.test.ts) passes 19/19.Both ops are
(text: string, cursor: int32) -> int32. Cursors are UTF-16 string indices, authored in the schema asint32(fluessig → Rusti32→ JSnumber) and widened to the engine'susizeat the seam. The pre-swap exports usedu32(alsonumberin.d.ts), soint32reproduces the JS-visible surface byte-for-byte. The three shim-delegated "atomic segments" tests (which fall back to pi's original when a JSoptions.segment/options.isAtomicSegmentcallback is supplied) continue to pass unchanged.How
crates/pidgin-napi/schema/api.json(shape: unary,infallible: true,readonly: true,bindings.node.name= exact JS export name). Paramstext: string,cursor: int32; returnint32.catalog.jsonunchanged (no new DTOs).impl PidginCore for PidginImplinsrc/core_impl.rs, each routing to the samepidgin_tui::word_navigationfn the hand-written export called. Thei32cursor param/return is widened to the engine'susize, matching the pre-swapas usize/as u32casts.crates/pidgin-napi/regen.sh(fluessig pinned at1fed77a) to regeneratesrc/generated.rs. Deleted the 2 hand-written exports fromsrc/lib.rs.Verification
.d.ts+.jsbyte-diff vsorigin/mainbaseline: both symbols IDENTICAL (JSDoc blocks andmodule.exportsglue); the two symbols moved into the generated block right afterextractSegments, the same mechanical reorder as modules 2-4.cargo build -p pidgin-napi,cargo fmt --all --check,cargo clippy -p pidgin-napi --all-targets -- -D warnings: clean.codespellon touched files: 0 findings.git archive HEAD: 877 files, 0 errors (1 pre-existingconformance/STEWARD.mdslop-prose warning).packages/tui/test/word-navigation.test.ts(19/19) against the locally-built addon: all pass.🤖 Generated with Claude Code
https://claude.ai/code/session_017xL2W7dkhPsTSRuXQNCDeY
Generated by Claude Code