github / github/gh-stack

gh stack rebase --continue doesn't report new conflicts hit while resuming a multi-commit branch rebase

Offen
#430 1 Kommentar 2 Reaktionen 0 zugewiesene Personen Auf GitHub ansehen
bug topic: cli - rebase
Vorherrschende Sprache
Go
Sterne
1.5k
Forks
70
Ø Merge
1 T. 8 Std.
Gemergte PRs (30 T.)
7

Beschreibung

## Summary

`gh stack rebase --continue` only prints `Conflicted files:` listing for first conflict encountered when cascading one stacked branch onto another. If resolving that conflict and continuing causes git to hit a second conflict on a later commit within the same branch's replay, the tool does not report what files are now conflicted and just returns a generic wrapped error.

This can make it look like there's only one conflicted file when there are actually more. You can only see the other conflicts by manually running `git status`.

## Steps to reproduce

1. Create a stack with a branch containing at least two commits and at least two files, where:
- Commit A modifies `file1.txt` so that there's a conflict with the (rebased) parent branch.
- Commit B later modifies `file2.txt` so that it also conflicts with the parent branch, independently of commit A.
2. Rebase the stack
3. The tool stops on commit A's conflict and correctly prints:
```
Conflicted files:
C file1.tsx (lines N–M)
```
4. Resolve `file1.txt`, stage it, run `gh stack rebase --continue` again.
5. Git internally applies commit B next, which conflicts on `file2.txt`.

## Expected behavior

Step 5 should print the same kind of `Conflicted files:` block, listing `file2.txt` with its conflict line numbers, like step 3 did for `file1.txt`.

## Actual behavior

Step 5 prints a generic error:
```
rebase continue failed — resolve remaining conflicts and try again: exit status 1
```

No indication of which file(s) are now conflicted. The only way to discover where the new conflict is is running `git status` manually.

## Proposed solution / notes

I'll be honest, not familiar with Go so this "solution" is mostly Claude. I did double check that it looks at least mostly right to me. Figured it might be helpful.

> Traced this to `cmd/rebase.go` and `internal/git/git.go`:
>
> - `printConflictDetails()` / `printConflictDetailsWithContinue()` (`cmd/rebase.go:545`) is the function that formats the `Conflicted files:` block with per-file conflict-marker line numbers (via `git.FindConflictMarkers`). It's only called from the branch-to-branch **cascade** logic, at `cmd/rebase.go:259` and `:435`.
> - `continueRebase()` (`cmd/rebase.go:312`) has a separate path for resuming an *already in-progress* `git rebase` within a single branch's multi-commit replay:
> ```go
> if git.IsRebaseInProgress() {
> rebaseOpts := git.RebaseOpts{CommitterDateIsAuthorDate: state.CommitterDateIsAuthorDate}
> if err := git.RebaseContinue(rebaseOpts); err != nil {
> return fmt.Errorf("rebase continue failed — resolve remaining conflicts and try again: %w", err)
> }
> }
> ```
> This path never calls `printConflictDetails`.
> - Following `RebaseContinue` (`internal/git/gitops.go:334`) into `tryAutoResolveRebase` (`internal/git/git.go:118`), the conflicted-files list is actually fetched — just to check whether `rerere` already auto-resolved everything — and then discarded on the way out:
> ```go
> conflicts, err := ConflictedFiles()
> if err != nil {
> return originalErr
> }
> if len(conflicts) > 0 {
> return originalErr // <-- conflicts is right here and gets thrown away
> }
> ```
>
> **Fix**: in `continueRebase`, when `git.RebaseContinue` returns an error, call `printConflictDetailsWithContinue` (using the still-in-progress rebase's current conflicted files, e.g. by calling `git.ConflictedFiles()` again, or by threading `tryAutoResolveRebase`'s local `conflicts` slice out through the error) before returning, instead of just wrapping the raw error string. That gives resume-mid-branch conflicts the same reporting as cascade-boundary conflicts.

## Environment

- `gh` version: 2.97.0 (2026-07-31)
- `gh-stack` extension: `github/gh-stack` v0.1.0
- OS: macOS Tahoe 26.5.1

Beitragsleitfaden

Beitragsleitfaden öffnen

Rechercherichtung

Start in cmd/rebase.go at continueRebase and compare its in-progress path with printConflictDetailsWithContinue. Then trace git.RebaseContinue in internal/git/gitops.go and tryAutoResolveRebase in internal/git/git.go; reproduce the multi-commit conflict flow with gh stack rebase --continue. Done means a later conflict reports the current Conflicted files block instead of only the generic error.

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
72/100

Neue Issues direkt in Ihr Postfach

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