M14: validated source editing across Wright frontends (autonomous checkpoint) - #133
Conversation
…re (#128) Reconcile the M9 safe-edit contract with the current project/session architecture: one EditTransaction carries multi-file edits with exact source ranges and per-source identity/version preconditions, and validate_transaction runs the edited project through the correct native frontend (OPY via include overlays, OSTW via the ds.toml project graph with overlays) instead of forcing SourceKind::Opy through a synthetic edit.opy path. Refusals are atomic and structured (stale/unknown sources, overlaps, unsupported kinds, compiled errors) with cross-file span provenance, and validation never writes the filesystem. wright-language rename validation and the wright-consumer rename workflow now route through the shared contract; the OSTW frontend gains overlay-capable compile entry points.
…ansactions (#129) Make semantic rename a shared refactoring over the project-aware transaction contract: wright_driver::edit::semantic_rename resolves the symbol at a position through the shared semantic index of the project compiled by its original native frontend, produces one exact-range multi-source transaction (declaration/definition/reference occurrences only), and validates it through validate_transaction (#128) before success. The wright-language rename now delegates per affected root to the shared contract and unions the transactions, preserving M10 project-wide behavior; OSTW rename is added on the declared semantic surface (globals, player variables, subroutines/functions) by propagating identifier-exact name spans through the OSTW CST/parser and #118 semantic HIR, with provenance-limited targets refusing explicitly. Cross-file M10 fixtures now use real file URIs per the path-based contract.
… the shared tool API (#130) Add ToolRequest::validateEditTransaction and ToolRequest::semanticRename over the shared #128/#129 contracts: agents can request validated source-edit previews and semantic rename through Wright-owned transport-neutral operations with all-or-nothing refusal semantics, structured diagnostics, and per-source previews carrying identity/version preconditions. Capabilities advertise the mutation operations; the stdio/JSON-RPC adapters forward the full request shape (the JSON-RPC adapter previously dropped all parameters except op) and are transport-equivalence tested for OPY and OSTW evidence cases. Docs record that Wright proposes/validates edits while filesystem application stays an explicit consumer responsibility.
…tract (#131) Rename edits are now the shared #129 transaction in editor conventions: exact-occurrence 0-based UTF-16 ranges (one edit per semantic occurrence, never a whole-document replacement), and the language-service result carries the validated per-source previews. The LSP adapter is a pure mapping — grouping the exact edits per document into documentChanges/TextDocumentEdit with per-document versions and the unversioned null form for filesystem-backed sources — with no protocol-layer symbol resolution, collision, or stale checks. Protocol regressions cover multi-document OPY rename, supported OSTW rename through the same adapter, UTF-16/non-BMP ranges, version preconditions, and unsupported-target refusals; M10 rename tests now assert exact occurrence edits and preview equality.
PM verification: CHANGES_REQUIREDThe M14 branch is substantial and the architecture is mostly aligned, but the current Acceptance blocker 1 — later edit ranges drift after earlier replacements
If an earlier edit changes text length, a later range on the same line no longer addresses the original semantic occurrence. If an earlier edit inserts/removes newlines, later line/column coordinates can drift more broadly. This can incorrectly reject a valid semantic rename or, worse, mutate the wrong range if the resulting source still compiles. A common repro shape is multiple references on one line, e.g. The transaction contract must apply all ranges against the same original source snapshot, e.g. by applying non-overlapping edits in descending source order per file or by a single-pass reconstruction. Acceptance blocker 2 — invalid columns are silently clamped
This is especially important for agent-facing edits because a malformed range must never become a different valid edit. Also explicitly classify same-position zero-width insertions (and other order-dependent zero-width combinations) as conflicts or define a documented deterministic semantic. The current overlap check allows two zero-width edits at the same position. Acceptance blocker 3 — compile-invalid transactions still return a previewAfter The existing broken-include regression does not enforce this: its assertion accepts both For the current M14 contract, any failed validation should return Required regressions before acceptance
The rest of the reviewed shape is sound: #129 uses exact semantic occurrences, #130 exposes the shared operations through ToolService/transports, and #131 maps the shared rename result into LSP rather than reimplementing semantic resolution. Keep those boundaries intact while fixing #128. Do not merge or mark #132/M14 accepted until these regressions are fixed and the full PR CI is green again. |
…tion (#133) Apply every transaction range against one original source snapshot: per source, edits apply in descending position order so an earlier replacement's length or newline changes can never shift a later range (EditTransaction::apply is the mechanical public application). Columns are strict 1-based character columns: 0 or beyond-line columns refuse with edit-invalid-range instead of clamping, and order-dependent zero-width combinations at one position refuse with edit-zero-width-conflict. Validation is atomic end to end: any failed check, including compiled/semantic-invalid edited projects, returns ok=false and no validated preview. Focused regressions cover same-line length-changing edits, multiline coordinate stability, longer/shorter same-line semantic rename, invalid columns, zero-width conflicts, and compile-invalid transactions; the broken-include preview assertion is no longer tautological. Temp fixture dirs are unique per test call to remove a parallel-test race.
PM re-verification — #128 blockers resolved at
|
M14 #132 acceptance — independent verification at PR #133 head
|
Autonomous Goal
Advance Wright M14 validated source editing as far as safely possible through the currently approved M14 issues (#128 → #129 → #130/#131 → #132), maintaining this Draft PR as the persistent checkpoint. No new roadmap scope, refactoring categories, or OPY/OSTW compatibility broadening without a concrete blocker.
Base
main@ 25f21e6 (feat(driver): integrate Workshop→OPY/OSTW reconstruction behind one shared convert contract (#126))Status
REVIEW_REQUIRED (PM re-verification of
264fa43)Completed Checkpoints
264fa43— #128 acceptance blockers fixed (PM review round 2)Evidence per blocker:
apply_transactionapplies every range against one original source snapshot — per source, edits apply in descending position order, so earlier replacements' length/newline changes never shift later ranges;EditTransaction::applyis the mechanical public application. Regressions: same-line length-changing edits (same_line_edits_apply_against_the_original_snapshot_when_length_changes), multiline deletion followed by a later edit (later_edit_after_a_multiline_replacement_keeps_original_coordinates), and longer/shorter same-line semantic rename (semantic_rename_same_line_occurrences_with_longer_and_shorter_names).apply_editvalidates every column strictly (1-based, in1..=char_count+1); column 0 or beyond-line columns refuse withedit-invalid-range, never clamp (invalid_columns_are_rejected_not_clamped).edit-zero-width-conflict(same-position insertions and insert-at-another-edit's-start), with a documented deterministic rule (same_position_zero_width_edits_are_refused_as_conflicts).validate_transactionreturnsok=falseand no validated preview whenever any check fails, including compiled/semantic-invalid edited projects; the broken-include regression now assertspreview.is_none()(was tautological) andcompile_invalid_transaction_returns_no_validated_previewcovers both transaction and rename paths.cargo test --workspace --all-targets --all-featuresgreen (55 suites; driver edit suite 20/20 across 5 consecutive runs), clippy-D warningsclean,cargo fmt --checkclean; PR CI: all 22 checks pass on264fa43.#132 acceptance verification — independent verification of #128-#131 (no code changes)
Evidence (all run at commit
da89ab6, no issue-state reliance):cargo test --workspace --all-targets --all-featuresgreen;cargo fmt --all -- --checkclean;cargo clippy --workspace --all-targets --all-features -- -D warningsclean (CI job 1 equivalents).python3 scripts/v1-gates.py6/6 pass;python3 scripts/run-scenarios.py7/7 pass;cargo run -p wright-benchno regressions (CI job 2 equivalents).python3 -m unittest discover -s compatibility/tests18 tests OK;python3 compatibility/run_oracle.py26/26 OverPy oracle fixtures PASS (CI job 3 equivalent, pinned pnpm deps installed).compatibility/ostw/run_oracle.py) not locally runnable (needs--acquireof the pinned .NET reference); the OSTW differential Rust suite ran green as part of the workspace tests.reconstructcall anywhere in the mutation path (edit.rs/service.rs/language-service/LSP) — reconstruction from [M13 reverse] Reconstruct the declared Workshop surface as valid OPY source #124/[M13 reverse] Reconstruct the declared Workshop surface as valid OSTW source #125 is not the mutation mechanism; no LSP types in driver/refactoring core; nofs::writein edit validation or the tool service (application is consumer responsibility); edit validation never hard-codesSourceKind::Opyoredit.opy.Post-M14 reassessment (draft for PM review — not ratified by the autonomous run)
M14 established one validated source-mutation architecture: frontend-neutral transactions (#128), shared identity-based rename (#129), transport-neutral tool mutation (#130), and a pure LSP adapter (#131). Recommended boundary going forward: do NOT auto-expand into extract-method/inline-function/formatter/general AST mutation or a plugin ABI without concrete agent/editor consumer evidence and a PM-led milestone; #96 remains deferred; OPY/OSTW compatibility breadth unchanged (no compatibility defects blocked any M14 acceptance criterion).
#132 acceptance verification — independent verification of #128-#131 (no code changes)
Evidence (all run at commit
da89ab6, no issue-state reliance):cargo test --workspace --all-targets --all-featuresgreen;cargo fmt --all -- --checkclean;cargo clippy --workspace --all-targets --all-features -- -D warningsclean (CI job 1 equivalents).python3 scripts/v1-gates.py6/6 pass;python3 scripts/run-scenarios.py7/7 pass;cargo run -p wright-benchno regressions (CI job 2 equivalents).python3 -m unittest discover -s compatibility/tests18 tests OK;python3 compatibility/run_oracle.py26/26 OverPy oracle fixtures PASS (CI job 3 equivalent, pinned pnpm deps installed).compatibility/ostw/run_oracle.py) not locally runnable (needs--acquireof the pinned .NET reference); the OSTW differential Rust suite ran green as part of the workspace tests.reconstructcall anywhere in the mutation path (edit.rs/service.rs/language-service/LSP) — reconstruction from [M13 reverse] Reconstruct the declared Workshop surface as valid OPY source #124/[M13 reverse] Reconstruct the declared Workshop surface as valid OSTW source #125 is not the mutation mechanism; no LSP types in driver/refactoring core; nofs::writein edit validation or the tool service (application is consumer responsibility); edit validation never hard-codesSourceKind::Opyoredit.opy.Post-M14 reassessment (draft for PM review — not ratified by the autonomous run)
M14 established one validated source-mutation architecture: frontend-neutral transactions (#128), shared identity-based rename (#129), transport-neutral tool mutation (#130), and a pure LSP adapter (#131). Recommended boundary going forward: do NOT auto-expand into extract-method/inline-function/formatter/general AST mutation or a plugin ABI without concrete agent/editor consumer evidence and a PM-led milestone; #96 remains deferred; OPY/OSTW compatibility breadth unchanged (no compatibility defects blocked any M14 acceptance criterion).
da89ab6— #131 language services: LSP rename converges on the shared contractEvidence:
previews).documentChanges/TextDocumentEditwith per-document versions (null for filesystem-backed sources); no protocol-layer symbol/collision/stale logic; unsupported targets surface the shared refusal as an explicit LSP error.cargo test --workspacegreen (65 suites); clippy/fmt clean.e3f4901— #130 agent tooling: validated mutation through the shared tool APIEvidence:
ToolRequest::validateEditTransactionandToolRequest::semanticRenameover the session project with all-or-nothing semantics, structured refusal diagnostics, and per-source previews carrying identity/version preconditions.op) and is transport-equivalence tested for the mutation ops; in-process ToolService tests cover OPY + OSTW evidence cases.cargo test --workspacegreen; clippy/fmt clean.e8810ab— #128 foundation: source-edit transactions are project- and frontend-awareEvidence:
wright-driverEditTransaction/validate_transactionreplaces the OPY-hard-codedvalidate_edit/edit.opypath; edits carry per-source identity/version preconditions; stale/unknown/overlap/unsupported-kind refusals are deterministic and atomic (no partial preview).wright_opy::compile_with_overlay_outcome+ the shared HIR→IR→lower→validate chain + session profile; OSTW validation compiles throughwright_ostw::compile_with_semantics_overlaywith theds.tomlproject graph. Cross-file diagnostics keep real source paths (driver tests assert the span names the edited include/import file).wright-languageand thewright-consumerrename workflow now route through the shared contract;overlay_with_editsdead code removed.cargo test --workspacegreen;cargo clippy --workspace --all-targetsandcargo fmt --allclean.crates/wright-driver/tests/edit.rs(9 tests),wright-ostw/tests/parse.rsoverlay test.2583ca6— #129 refactoring: semantic rename unified across OPY and OSTW on validated transactionsEvidence:
wright_driver::edit::semantic_renameis the shared refactoring: resolves the symbol at a 1-based position in a project source through the shared semantic index, refuses unresolved positions/collisions/occurrences without exact identifier spans, produces one exact-range multi-source transaction (declaration/definition/reference identifiers only), and validates throughvalidate_transaction([M14 foundation] Make source-edit transactions project- and frontend-aware #128) before reporting success. No LSP types, no mutable IR.wright-language::renamedelegates per affected root to the shared contract, unions the transactions (dedupe by source+range), keeps the stale guard and per-root kind-aware validation, and materializes the M10RenameEditshape for the LSP adapter.collision_problem/symbol_at_in_file/renamed_text/TargetSpanremoved (duplicated semantics).name_spanpropagated through the OSTW CST/parser and [M13] Resolve and lower the accepted protect-ban OSTW semantic slice into HIR #118 semantic HIR for globals, player variables, functions/subroutines, and rule names; typed constants and other provenance-limited targets refuse explicitly (rename-unresolved-target).ds.toml, not the main source — file matching walks the registry instead of assuming file 0.semantic_rename_*tests (same-spelled identity isolation, cross-file OPY, OSTW cross-file, collision/unresolved/empty-name refusals, breaking-rename refusal); language-service OSTW rename tests (cross-file edits, collision/unresolved refusals, open-overlay references). M10 cross-file fixtures moved to real file URIs per the path-based contract.cargo test --workspacegreen (multiple consecutive runs; the one observed transient edit-test failure did not reproduce in 3 subsequent runs); clippy/fmt clean.Current Work
None — all approved M14 implementation issues (#128-#131) are landed; the #128 acceptance blockers recorded in the prior PM review are fixed in
264fa43with focused regressions and full PR CI green (22/22). Remaining steps require human review (PM re-verification of the blocker fixes, reassessment ratification, merge decision).Validation
Latest full run (this commit):
cargo test --workspaceall suites ok;cargo clippy --workspace --all-targetsandcargo fmt --allclean. Compatibility/oracle Python tests and pinned pnpm/Node oracle jobs not run locally (no fixture or corpus changes; CI will execute them on the PR).Blockers
None for the autonomous run. Resolved note:
cargo testdoes not run the compatibility/ Python oracle suite; that gate runs in CI.Decisions Requiring Review
validate_transaction/semantic_renamecompose the native frontends directly (mirroring thesession.loadchains) rather than routing throughCompilerSession, because edited/main texts live in memory; the session remains the single owner of normal load workflows. M10 rename validation migrated from frontend-error-only to the full chain (strictly safer).edit-input-stdin); M9's stdin+temp-file path removed. Cross-file M10 fixtures updated to real file URIs (the shared contract is path-based).SourceEditgained a requiredsourcefield;EditRangecolumns are 1-based character columns matching compiler spans.semantic_renamerequires the caller's current-text snapshot (sources) for every file the rename may edit; disk fallback only for the main source.Next Candidates
Notes
Worktree:
/private/tmp/wright-m14-autonomous(branchfeat/m14-validated-source-editing). Git/repo evidence always overrides this checkpoint.