diff options
| author | Gabriel Schneider <[email protected]> | 2026-09-29 08:09:08 -0300 |
|---|---|---|
| committer | Gabriel Schneider <[email protected]> | 2026-10-01 00:12:16 -0300 |
| commit | f7e3441698a4621bec0d7c14eb45303753ffbead (patch) | |
| tree | 14ed04f81a0fc7aa7e07a44e4b4c413b940b3901 | |
| parent | 72c84bd7206bba5e2323c2e7f12f2458405e800d (diff) | |
| download | pardes-f7e3441698a4621bec0d7c14eb45303753ffbead.tar.gz pardes-f7e3441698a4621bec0d7c14eb45303753ffbead.zip | |
A rename alone does not make a pane dirty
Any rename marked the pane dirty (saved revision one back), while the
guards ask only whether its text was ever edited: /index said dirty for a
pane Exit let go without asking. The name is no edit now, so /index, the
guards and Restore agree; Save writes under the new name all the same.
Co-Authored-By: Claude Opus 5.5 <[email protected]>
| -rw-r--r-- | docs/fs.md | 5 | ||||
| -rw-r--r-- | src/ninep/ctl.zig | 7 | ||||
| -rw-r--r-- | src/ninep/pane.zig | 6 | ||||
| -rw-r--r-- | test/gui-goldens.txt | 2 | ||||
| -rw-r--r-- | test/panes.zig | 3 |
5 files changed, 15 insertions, 8 deletions
@@ -504,7 +504,10 @@ selection, and leaves `look` reading back empty. `/pane/<n>/name` reads the pane's file name (a terminal's directory) and writing it renames the buffer; a relative name resolves against the pane's -directory. The write is the name and its newline, nothing trimmed: a blank +directory. A name alone is no edit: the pane's `dirty` stays what its text made it +(a renamed clean file is still 0, and nothing asks about it at Exit, +Restore or Del, which ask only about text edited), and `Save` writes it +under the new name all the same. The write is the name and its newline, nothing trimmed: a blank inside a name is taken (`two words.zig`), but one at either end, or a control character, is refused, `bad character in file name` (EINVAL), as acme refuses a blank (xfid.c:650), rather than quietly cut off. `body` appends on write and replaces on truncating open. A diff --git a/src/ninep/ctl.zig b/src/ninep/ctl.zig index 0b1ec194..8cf4f0a8 100644 --- a/src/ninep/ctl.zig +++ b/src/ninep/ctl.zig @@ -1417,9 +1417,10 @@ test "get reloads the pane from disk and reports a missing file without losing d try testing.expectEqualStrings("from disk\n", pane.file.?.content); try testing.expect(!pane_files.dirtyOf(pane)); try testing.expect(pane.file.?.history.undo_len > 0); - // What it had (renamed, so dirty) was thrown away for it: logged. + // Renamed but never edited, it was clean: nothing thrown away, nothing + // logged as reloaded over edits. var reloaded: [32]u8 = undefined; - try testing.expect(th.logHas(p, try std.fmt.bufPrint(&reloaded, "changed {d} reloaded\n", .{serial}))); + try testing.expect(!th.logHas(p, try std.fmt.bufPrint(&reloaded, "changed {d} reloaded\n", .{serial}))); _ = wr(p, Node.of(serial, .name), try std.fmt.bufPrint(&name, "{s}/missing.txt\n", .{directory})); _ = wr(p, Node.of(serial, .body), "unsaved\n"); @@ -1440,7 +1441,7 @@ test "exec Save writes the named file through the host" { const serial = serialOf(p); const pane = p.panes[0].?; try testing.expectEqual(Status.ok, wr(p, Node.of(serial, .name), "/tmp/renamed.txt\n").reply.status); - try testing.expect(pane_files.dirtyOf(pane)); + try testing.expect(!pane_files.dirtyOf(pane)); // a name alone is no edit; Save writes all the same const saved = wr(p, Node.of(serial, .exec), "Save\n"); try testing.expectEqual(Status.ok, saved.reply.status); try testing.expect(saved.saved); diff --git a/src/ninep/pane.zig b/src/ninep/pane.zig index d8329ccc..5f8fc00a 100644 --- a/src/ninep/pane.zig +++ b/src/ninep/pane.zig @@ -636,7 +636,9 @@ pub fn nameBuffer(p: *Pardes, id: usize, full: []const u8, preserve_tag: bool) ! if (pane.tag.own) |own| p.gpa.free(own); pane.tag.own = null; } - f.saved_revision = f.revision -% 1; + // A name alone is no edit: dirty stays what the text made it, as + // the guards ask only whether it was ever edited, so /index, Exit + // and Restore agree. Save writes it under the new name all the same. f.watch_after_save = fs.localPath(full) != null; } if (f.highlights.len > 0) p.tree_sitter_gpa.free(f.highlights); @@ -1151,7 +1153,7 @@ test "relative names use the file directory and can name a new target" { var expected_buf: [4096]u8 = undefined; const expected = try std.fmt.bufPrint(&expected_buf, "{s}/created.txt", .{directory}); try testing.expectEqualStrings(expected, pane.file.?.path); - try testing.expect(dirtyOf(pane)); + try testing.expect(!dirtyOf(pane)); // a name alone is no edit } test "relative names follow a pane/new scratch's session directory and virtual directories" { diff --git a/test/gui-goldens.txt b/test/gui-goldens.txt index 01bdfc7c..93e77764 100644 --- a/test/gui-goldens.txt +++ b/test/gui-goldens.txt @@ -5,7 +5,7 @@ 05-body-selection 96a158adac982f4141526d10956e19828632edc0f6f60d1161d1353e34797118 06-tag-focus-selection 94aff8499a6e6f399761ffdd56369d526fbe65232eb21c88addd12973af611aa 07-prompt-notice 041603b841605b0a9456cbbb9b3e06e219b0a08a58e2d38229e1c81366577a87 -08-wide-glyph-edges 94b0beb7cc2f2a09259f4f7d57999001ef75ed53ea210a65a1510404bd161af9 +08-wide-glyph-edges 4f15245cb2e14f4190940a79c61751bbb6efbf21c1e3ab423fb1469e0466697e 09-collapsed-focus-tint 1d0e6e4b371bc3b2bba96d9177b91f240fa4bef38c62470dc078fa9feed119ac 10-tagbottom f7175dfb338b75c5ac3457c8422dc0e352c46d51b2c52533ce32ef143fcf6c6b 12-multiline-tag ddd7d775a246e91b88f0eff98b6f9bea8aa5d63dbfbe931bd830ccb9086bd5c4 diff --git a/test/panes.zig b/test/panes.zig index 1988fe16..1ca33053 100644 --- a/test/panes.zig +++ b/test/panes.zig @@ -1622,7 +1622,8 @@ test "pane filename drafts commit and cancel without changing body or command ta try std.testing.expectEqualStrings(tail, pardes.tagline.curTail(pane)); while (p.nextEffect()) |effect| try std.testing.expect(std.meta.activeTag(effect) != .save_file); } - try std.testing.expect(pane.file.?.revision != pane.file.?.saved_revision); + // A name alone is no edit: the pane stays clean. + try std.testing.expect(pane.file.?.revision == pane.file.?.saved_revision); } test "pane filename grapheme edits and invalid empty commits preserve the buffer" { |
