Skip to content

Commit

Permalink
Allow pasting commits more than once
Browse files Browse the repository at this point in the history
After pasting commits once, we hide the cherry-picking status (as if it had been
reset), and no longer paint the copied commits with blue hashes; however, we
still allow pasting them again. This can be useful e.g. to backport a bugfix to
multiple major version release branches.
  • Loading branch information
stefanhaller committed Oct 11, 2024
1 parent 6b5d2e7 commit db2a001
Show file tree
Hide file tree
Showing 3 changed files with 44 additions and 2 deletions.
7 changes: 5 additions & 2 deletions pkg/gui/controllers/helpers/cherry_pick_helper.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,8 @@ func (self *CherryPickHelper) CopyRange(commitsList []*models.Commit, context ty
}
}

self.getData().DidPaste = false

self.rerender()
return nil
}
Expand Down Expand Up @@ -103,7 +105,8 @@ func (self *CherryPickHelper) Paste() error {
return err
}
if !isInRebase {
return self.Reset()
self.getData().DidPaste = true
self.rerender()
}
return nil
})
Expand All @@ -114,7 +117,7 @@ func (self *CherryPickHelper) Paste() error {
}

func (self *CherryPickHelper) CanPaste() bool {
return self.getData().Active()
return self.getData().CanPaste()
}

func (self *CherryPickHelper) Reset() error {
Expand Down
12 changes: 12 additions & 0 deletions pkg/gui/modes/cherrypicking/cherry_picking.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,10 @@ type CherryPicking struct {
// we only allow cherry picking from one context at a time, so you can't copy a commit from
// the local commits context and then also copy a commit in the reflog context
ContextKey string

// keep track of whether the currently copied commits have been pasted already. If so, we hide
// the mode and the blue display of the commits, but we still allow pasting them again.
DidPaste bool
}

func New() *CherryPicking {
Expand All @@ -22,10 +26,18 @@ func New() *CherryPicking {
}

func (self *CherryPicking) Active() bool {
return self.CanPaste() && !self.DidPaste
}

func (self *CherryPicking) CanPaste() bool {
return len(self.CherryPickedCommits) > 0
}

func (self *CherryPicking) SelectedHashSet() *set.Set[string] {
if self.DidPaste {
return set.New[string]()
}

hashes := lo.Map(self.CherryPickedCommits, func(commit *models.Commit, _ int) string {
return commit.Hash
})
Expand Down
27 changes: 27 additions & 0 deletions pkg/integration/tests/cherry_pick/cherry_pick.go
Original file line number Diff line number Diff line change
Expand Up @@ -79,5 +79,32 @@ var CherryPick = NewIntegrationTest(NewIntegrationTestArgs{
Contains("one"),
Contains("base"),
)

// Even though the cherry-picking mode has been reset, it's still possible to paste the copied commits again:
t.Views().Branches().
Focus().
NavigateToLine(Contains("master")).
PressPrimaryAction()

t.Views().Commits().
Focus().
Lines(
Contains("base").IsSelected(),
).
Press(keys.Commits.PasteCommits).
Tap(func() {
t.ExpectPopup().Alert().
Title(Equals("Cherry-pick")).
Content(Contains("Are you sure you want to cherry-pick the copied commits onto this branch?")).
Confirm()
}).
Tap(func() {
t.Views().Information().Content(DoesNotContain("commits copied"))
}).
Lines(
Contains("four"),
Contains("three"),
Contains("base"),
)
},
})

0 comments on commit db2a001

Please sign in to comment.