From 409dc015496c5eea353e2e24c20551bb00785dd4 Mon Sep 17 00:00:00 2001 From: Jake Bailey <5341706+jakebailey@users.noreply.github.com> Date: Sat, 7 Oct 2023 14:09:23 -0700 Subject: [PATCH] Fix git bisect when repo isn't clean --- .changeset/loud-impalas-whisper.md | 5 ++++ src/git.ts | 42 +++++++++++++++++++++++------- 2 files changed, 37 insertions(+), 10 deletions(-) create mode 100644 .changeset/loud-impalas-whisper.md diff --git a/.changeset/loud-impalas-whisper.md b/.changeset/loud-impalas-whisper.md new file mode 100644 index 0000000..ab303d0 --- /dev/null +++ b/.changeset/loud-impalas-whisper.md @@ -0,0 +1,5 @@ +--- +"every-ts": patch +--- + +Fix git bisect when repo isn't clean diff --git a/src/git.ts b/src/git.ts index bbc777d..9d4d753 100644 --- a/src/git.ts +++ b/src/git.ts @@ -56,7 +56,25 @@ export class Bisect extends BaseCommand { await ensureRepo(); - if (await isBisecting() && actionsWithSideEffects.has(this.subcommand)) { + let shouldReset = false; + const bisectInfo = await getBisectInfo(); + + if (this.subcommand === `start` && revs.length >= 2) { + shouldReset = true; + } else if (bisectInfo?.terms.size === 2) { + shouldReset = true; + } else { + if ( + bisectInfo + && actionsWithSideEffects.has(this.subcommand) + && !bisectInfo.terms.has(this.subcommand) + && bisectInfo.terms.size === 1 + ) { + shouldReset = true; + } + } + + if (shouldReset) { await resetTypeScript(`node_modules`, `built`); } @@ -72,17 +90,21 @@ export class Bisect extends BaseCommand { } } -async function isBisecting() { +async function getBisectInfo() { try { const { stdout } = await execa(`git`, [`bisect`, `log`], { cwd: tsDir }); const lines = stdout.split(/\r?\n/); - if (lines.some((v) => v.startsWith(`# first `))) { - return false; - } - const actions = lines.filter((v) => !v.startsWith(`#`)); - return actions.length >= 3; + const done = lines.some((v) => v.startsWith(`# first `)); + // Info lines look like "# bad: ...", "# good: ...", "# skip: ...", "# new: ...", "# old: ...", "# status: ..." + const terms = new Set( + lines + .filter((v) => v.startsWith(`# `)) + .map((v) => v.split(` `)[1].slice(0, -1)) + .filter((v) => v !== `status` && v !== `skip`), + ); + return { done, terms }; } catch { - return false; + return undefined; } } @@ -98,14 +120,14 @@ export class BisectRun extends BaseCommand { override async execute(): Promise { await ensureRepo(); - if (!await isBisecting()) { + if (!await getBisectInfo()) { throw new ExitError(`Not bisecting`); } const { stdout: termGood } = await execa(`git`, [`bisect`, `terms`, `--term-good`], { cwd: tsDir }); const { stdout: termBad } = await execa(`git`, [`bisect`, `terms`, `--term-bad`], { cwd: tsDir }); - while (await isBisecting()) { + while (!(await getBisectInfo())?.done) { await resetTypeScript(`node_modules`, `built`); await ensureBuilt();