fix(changes): Discard takes only the ticked files and blocks (#87)
The Changes panel's "Discard all" threw away every changed file, ticked or not. It is now "Discard (n)": the same selection Commit sends — whole ticked files as `paths`, a partly ticked file's ticked blocks as `hunks` — and is disabled with nothing ticked. The server's `discard` accepts `hunks` (`selectionPatch` in reverse, `git apply -R`), building every patch before applying any so a stale selection undoes nothing. Closes #87
This commit is contained in:
@@ -1241,16 +1241,18 @@ async function diffHunks(dir, file, context) {
|
||||
* in file order, to be applied FORWARD onto an index holding HEAD. Every
|
||||
* header is matched against a fresh diff like `hunkPatch`'s; null when one is
|
||||
* gone or names a block the hunk lacks. Each hunk's new-side start is left as
|
||||
* git wrote it — `git apply` locates a hunk by its old side.
|
||||
* git wrote it — `git apply` locates a hunk by its old side. `reverse` cuts
|
||||
* it for `apply -R` off the working tree instead (the partial discard, #87),
|
||||
* where the NEW side is the one checked and every start stays git's own.
|
||||
*/
|
||||
async function selectionPatch(dir, file, context, picks) {
|
||||
async function selectionPatch(dir, file, context, picks, reverse = false) {
|
||||
const diff = await diffHunks(dir, file, context);
|
||||
if (!diff || !picks.length) return null;
|
||||
const at = (header) => diff.hunks.findIndex((h) => h.slice(0, h.indexOf("\n")) === header);
|
||||
if (picks.some((p) => at(p.hunk) < 0)) return null;
|
||||
const bodies = [];
|
||||
for (const p of [...picks].sort((x, y) => at(x.hunk) - at(y.hunk))) {
|
||||
const body = onlyBlock(diff.hunks[at(p.hunk)], p.blocks, false);
|
||||
const body = onlyBlock(diff.hunks[at(p.hunk)], p.blocks, reverse);
|
||||
if (!body) return null;
|
||||
bodies.push(body);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user