oxy show lists modified files in its summary 0912a0337a95
The summary above a change's diff listed tree operations only, so a file
whose lines were edited appeared only further down, as its --- header,
and looked as if it had not been committed. Every edited file without a
tree operation now has an M line, and a rename shows its full new path.
closes #14
Author Andy McCall @andymccall <[email protected] >
When 1 month ago · 2026-09-28 23:06 UTC
Signature ✔ signed by Andy McCall
Hash 0912a0337a955864e1038da409ef794f111dd80f7fc7b050c989c74d588a4600
Depends on 75167672ebcd 982864068a59
Depended on by nothing yet
In bookmarks agents-in-readme bare-hashes carried-not-removed carry-identical doctor-trust identical-sides keyless-tags main merge-remote-bookmark only-help-103 paths-for-resolutions-and-amend push-notes show-stat subrepo-pin-state switch-says
In tags v0.1.0 v0.10.0 v0.11.0 v0.2.0 v0.3.0 v0.3.1 v0.4.0 v0.4.1 v0.4.2 v0.4.3 v0.4.4 v0.4.5 v0.4.6 v0.5.0 v0.5.1 v0.6.0 v0.7.0 v0.8.0 v0.9.0
Edits 6 atoms, 0 tree operations, 2 files
Browse the tree at this change
crates/oxy-core/src/repo/snapshot.rs crates/oxy-core/src/repo/tests.rs
modified
crates/oxy-core/src/repo/snapshot.rs
+19 −2
…
1821 unchanged lines
1822
1822
));
1823
1823
}
1824
1824
TreeOp::RemoveNode { node, .. } => out.push_str(&format!("D {}\n", path_of(node))),
1825
-
TreeOp::Move { node, name, .. } => {
1826
-
out.push_str(&format!("R {} -> {}\n", path_of(node), name))
1825
+
TreeOp::Move {
1826
+
node, parent, name, ..
1827
+
} => {
1828
+
let to = if parent.is_root() {
1829
+
name.clone()
1830
+
} else {
1831
+
format!("{}/{name}", path_of(parent))
1832
+
};
1833
+
out.push_str(&format!("R {} -> {to}\n", path_of(node)))
1827
1834
}
1828
1835
TreeOp::SetMode { node, mode, .. } => {
1829
1836
out.push_str(&format!(
…
3 unchanged lines
1833
1840
mode.opaque
1834
1841
));
1835
1842
}
1843
+
}
1844
+
}
1845
+
// Every other file the change edits is modified: the summary names
1846
+
// every path it touches, not only those with a tree operation.
1847
+
let with_op: HashSet<NodeId> = change.tree_ops.iter().map(|o| o.node()).collect();
1848
+
let mut listed: HashSet<NodeId> = HashSet::new();
1849
+
for e in &change.edits {
1850
+
let n = e.node();
1851
+
if !with_op.contains(&n) && listed.insert(n) {
1852
+
out.push_str(&format!("M {}\n", path_of(&n)));
1836
1853
}
1837
1854
}
1838
1855
let mut last_node: Option<NodeId> = None;
…
152 unchanged lines
modified
crates/oxy-core/src/repo/tests.rs
+6 −1
…
133 unchanged lines
134
134
assert_eq!(log[2].hash, h1);
135
135
let d = repo.describe_change(&h2).unwrap();
136
136
assert!(d.contains("D README.md"), "{d}");
137
+
assert!(
138
+
d.lines()
139
+
.any(|l| l.starts_with("M ") && l.ends_with("main.rs")),
140
+
"a modified file is in the summary too: {d}"
141
+
);
137
142
assert!(d.contains("+ println!(\"hi\");"), "{d}");
138
143
assert!(d.contains("-fn main() {}"), "{d}");
139
144
…
2522 unchanged lines
2662
2667
&repo.load_state(&[h1]).unwrap(),
2663
2668
&repo.load_state(&[h1]).unwrap().materialize()
2664
2669
)
2665
-
.contains("R "));
2670
+
.contains("R src/old.rs -> lib/new.rs "));
2666
2671
// A fresh checkout reproduces the tree.
2667
2672
let other = tempfile::tempdir().unwrap();
2668
2673
let clone = Repo::clone(&root.to_string_lossy(), other.path()).unwrap();
…
1202 unchanged lines