Second cross-file layer on the L1 foundations: a multi-file
WorkspaceEdit applier and an LSP rename UX driving it.
- src/rename.rs: parse a WorkspaceEdit (both `changes` map and
`documentChanges`, the latter preferred per spec; AnnotatedTextEdit
handled; create/rename/delete resource ops counted into
`unsupported_ops` for L4) into per-file TextEdit lists. RenameStore
keyed by the request's origin URI. 6 unit tests.
- src/lsp.rs: rename_store + accessor, ResponseRoute::Rename,
request_rename, and the textDocument.rename client capability
(prepareSupport=false — L2 renames from the cursor position).
- src/lua_bindings.rs: _request_rename_raw + pmacs.rename.{file_edits,
unsupported,clear}.
- pmacs_fake_lsp.rs: textDocument/rename arm; `rename` mode returns a
2-file documentChanges plus a create resource op.
- builtin/runtime/lsp.lua: apply_workspace_edit (preflight rejects
unresolvable URIs before mutating anything; per-file reverse-sorted
application; origin buffer restored), pmacs.lsp.rename with a
minibuffer prompt, lsp.rename command, C-c r keybind.
- tests/m4_acceptance.rs: m4_13 drives rename end-to-end through the
minibuffer and asserts both files mutated + origin restored.
Gates: lib 1268/0, m4 68/0, m8_1 10/0, m8_9 26/0, m8_10 19/0,
m9_1 18/0, m11_5 (--features crdt) 2/0; fmt + clippy clean.
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>