Skip to content

rebase without trunk#129

Merged
skarim merged 2 commits into
skarim/save-selected-remotefrom
skarim/rebase-without-trunk
Jun 15, 2026
Merged

rebase without trunk#129
skarim merged 2 commits into
skarim/save-selected-remotefrom
skarim/rebase-without-trunk

Conversation

@skarim

@skarim skarim commented Jun 15, 2026

Copy link
Copy Markdown
Collaborator

Add a --no-trunk flag to gh stack rebase that performs only the inter-branch cascade rebase without fetching from the remote or rebasing with the trunk branch.

This is useful when you want to align stack branches with each other (branch 2 onto branch 1, branch 3 onto branch 2, etc.) without pulling upstream changes or rebasing branch 1 onto trunk. Common use case: you've made changes on a lower branch and just want to cascade those changes up through the stack without touching the network or trunk.

Behavior

When --no-trunk is passed:

  1. Skips all remote/trunk operationspickRemote, git fetch, ensureLocalTrunk, fastForwardTrunk, and fastForwardBranches are all gated behind !opts.noTrunk. No network calls are made.
  2. Starts the cascade from index 1 — the first branch (index 0) is never rebased onto trunk. The cascade begins with branch 2 rebased onto branch 1, branch 3 onto branch 2, etc.
  3. Combines with existing flags--no-trunk --upstack and --no-trunk --downstack work as expected. startIdx is clamped to max(startIdx, 1) so the trunk rebase is always skipped regardless of other range flags.
  4. Single-branch edge case — if the stack has only one branch, --no-trunk results in "No branches to rebase" since the only operation would have been rebasing onto trunk.

Changes

cmd/rebase.go:

  • rebaseOptions: Add noTrunk bool field
  • rebaseState: Add NoTrunk bool with json:"noTrunk,omitempty" — persisted on conflict so --continue can produce accurate success messages
  • RebaseCmd: Add --no-trunk flag definition, update Long description and Example block
  • runRebase: Wrap the fetch/trunk/fast-forward block in if !opts.noTrunk { ... }. After computing startIdx/endIdx from --downstack/--upstack, apply if opts.noTrunk && startIdx < 1 { startIdx = 1 }. Save opts.noTrunk into rebaseState on conflict. Update success message to say "without trunk" when in no-trunk mode.
  • continueRebase: Read state.NoTrunk and adjust the success message accordingly

cmd/rebase_test.go:

  • TestRebase_NoTrunk_SkipsTrunkRebase: Stack [b1, b2, b3] with --no-trunk — verifies only 2 rebase calls (b2→b1, b3→b2), no trunk rebase. Asserts output contains "without trunk".
  • TestRebase_NoTrunk_SkipsFetch: Verifies FetchFn is never called when --no-trunk is set.
  • TestRebase_NoTrunk_SingleBranch: Single-branch stack with --no-trunk — verifies "No branches to rebase" output.
  • TestRebase_NoTrunk_WithUpstack: --no-trunk --upstack from b2 — verifies the combination works correctly (upstack already starts at index 1, so --no-trunk is a no-op for the range).
  • TestRebase_NoTrunk_ConflictSavesState: Conflict on b2 with --no-trunk — verifies NoTrunk: true is persisted in the saved rebase state JSON.

Stack created with GitHub Stacks CLIGive Feedback 💬

@skarim skarim marked this pull request as ready for review June 15, 2026 15:02
Copilot AI review requested due to automatic review settings June 15, 2026 15:02

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR adds a --no-trunk flag to gh stack rebase that performs only the inter-branch cascade rebase (branch 2 onto branch 1, branch 3 onto branch 2, etc.) without fetching from the remote or rebasing the first branch onto trunk. This is useful when changes on a lower branch need to be cascaded upward without involving the network or trunk.

Changes:

  • Gates all remote/trunk operations (pickRemote, git fetch, ensureLocalTrunk, fastForwardTrunk, fastForwardBranches) behind !opts.noTrunk, clamps startIdx to skip index 0, persists the flag in rebase state for --continue, and adjusts success messages.
  • Adds five new tests covering: skip trunk rebase, skip fetch, single-branch edge case, combination with --upstack, and conflict state persistence.
  • Updates documentation (README, SKILL.md, CLI reference, workflows guide) with the new flag description and examples.
Show a summary per file
File Description
cmd/rebase.go Core implementation: new noTrunk option/state field, conditional remote/trunk block, startIdx clamping, state persistence, adjusted messages
cmd/rebase_test.go Five new test cases covering --no-trunk behavior and edge cases
README.md Documents --no-trunk flag in the rebase flags table and examples
docs/src/content/docs/reference/cli.md Documents --no-trunk flag in CLI reference
docs/src/content/docs/guides/workflows.md Adds --no-trunk usage example to workflows guide
skills/gh-stack/SKILL.md Updates skill version, adds --no-trunk to command table, docs, and examples

Copilot's findings

Tip

Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

  • Files reviewed: 6/6 changed files
  • Comments generated: 0

@ktravers ktravers left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sounds like something we'll want in the web client too 👀

@skarim skarim merged commit e45a88c into main Jun 15, 2026
4 checks passed
@skarim skarim deleted the skarim/rebase-without-trunk branch June 15, 2026 17:54
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants