github / github/gh-stack

`gh stack checkout` reports "Local stack matches remote" without comparing local branch refs

Offen
#413 0 Kommentare 1 Reaktion 0 zugewiesene Personen Auf GitHub ansehen
bug topic: cli - general
Vorherrschende Sprache
Go
Sterne
1.5k
Forks
70
Ø Merge
1 T. 8 Std.
Gemergte PRs (30 T.)
7

Beschreibung

## Summary

`gh stack checkout` reports `✓ Local stack matches remote` when a local branch has diverged from its remote counterpart. It appears to compare its recorded state against the remote, and never against the actual local branch refs — so a local branch that has moved is invisible to the check.

```
$ git rev-parse --short=10 stack-b-two # local
df863cea57
$ git rev-parse --short=10 origin/stack-b-two # remote, one commit ahead
41fd74d3ae

$ gh stack checkout 6
✓ Local stack matches remote — switching to branch (stack #6)
ℹ Already on stack-b-two

$ gh stack view --short # no warning, no ⚠ Needs rebase
Stack #6
» stack-b-two ○ #5 (current)
├ stack-b-one ○ #4
└ main
```

The extension's own state file held the **correct** value the whole time:

```
$ jq -r '.stacks[].branches[] | select(.branch=="stack-b-two") | .head' .git/gh-stack
41fd74d3ae... # matches the remote; the local ref is what diverged
```

So this is not stale metadata. Recorded state and remote agreed, the local ref disagreed with both, and nothing compared against it.

## Why this matters

This is the reassurance a user sees immediately before #380 destroys their work. In that state `gh stack push` rewinds the remote branch and the commits become unreachable — and if the branch loses its only commit, GitHub auto-closes the PR with no files. The sequence is:

```
gh stack checkout -> "✓ Local stack matches remote"
gh stack push -> "✓ Pushed N branches" (remote commits gone, PR closed)
```

Fixing #380 addresses the destruction. Fixing this addresses the false confidence that leads someone to run the command in the first place.

## How a local branch gets behind

Anything not mediated by the extension. A plain `git fetch` after a colleague pushes; CI committing to the PR head branch (the trigger in #380); or building a change in a `git worktree` and pushing it with `git push origin :`, which moves the remote and leaves the local branch untouched.

## Reproduction

Against a stack whose branches are in sync:

```bash
git switch
git reset --hard HEAD~1 # simulate the local branch falling behind
gh stack checkout # -> "✓ Local stack matches remote"
gh stack view --short # -> no warning
```

Public repo with two stacks set up for this: https://github.com/xn/gh-stack-repro

## Expected

Compare recorded/remote heads against the actual local branch refs. On divergence, say so and name the fix (`git branch -f origin/`), rather than reporting a match.

A `gh stack status` / `gh stack doctor` surfacing per-branch local-vs-remote drift would cover the general case, since plain git will always be able to desync the extension's state.

## Environment

- `gh` 2.97.0
- `gh-stack` v0.1.0
- git 2.50.1
- macOS 26.4.1, darwin/arm64

## Related

- #380 — the data loss this false reassurance leads into.
- #193 — handling rebases performed outside `gh stack`; same general gap (external git operations invisible to the extension).

Beitragsleitfaden

Beitragsleitfaden öffnen

Rechercherichtung

Beginne beim Befehl `gh stack checkout` und verfolge die Prüfung, die `Local stack matches remote` meldet; führe die bereitgestellte Reproduktion aus, nachdem du einen lokalen Branch-Ref mit `git reset --hard` verschoben hast. Fertig ist es, wenn der Befehl aufgezeichnete oder Remote-Heads mit den tatsächlichen lokalen Refs vergleicht, bei einer Abweichung warnt und die vorgeschlagene Korrektur mit `git branch -f` nennt.

Vom Indexierungsmodell aus dem Issue-Text verfasst.

Bewertung

Tech-Stack
git, go
Bereich
cli
Issue-Typ
Bug
Schwierigkeit
3/5
Geschätzter Aufwand
1-2 Tage
Aktivitätsstatus
Ruhig
Klarheit
Größtenteils klar
Anfängerfreundlichkeit
55/100

Neue Issues direkt in Ihr Postfach

Eine kurze Übersicht über anfängerfreundliche GitHub-Issues.