mirror of
https://github.com/jesseduffield/lazygit.git
synced 2026-09-10 07:36:27 -04:00
Share cherry-pick state across worktrees of the same repo
Copied commits are referenced by hash, and hashes resolve identically in every worktree of a repo (shared object database), so there's no reason pasting shouldn't work after switching worktrees. Move the clipboard out of the per-worktree GuiRepoState into a per-repo SharedRepoState, keyed by the repo's common git dir; every worktree's Modes.CherryPicking now points at the same instance. Submodules and unrelated repos have different git dirs, so they keep isolated clipboards. As a side effect, cancelling a cherry-pick in one worktree now correctly clears it in all of them.
This commit is contained in:
parent
d3f16e5d3b
commit
a869854c63
|
|
@ -76,7 +76,11 @@ type Gui struct {
|
|||
// this is a mapping of repos to gui states, so that we can restore the original
|
||||
// gui state when returning from a subrepo.
|
||||
// In repos with multiple worktrees, we store a separate repo state per worktree.
|
||||
RepoStateMap map[Repo]*GuiRepoState
|
||||
RepoStateMap map[Repo]*GuiRepoState
|
||||
// Holds state shared between all worktrees of the same repo, keyed by the
|
||||
// repo's common git dir (one entry per repo, where RepoStateMap has one
|
||||
// entry per worktree).
|
||||
sharedRepoStateMap map[Repo]*SharedRepoState
|
||||
Config config.AppConfigurer
|
||||
Updater *updates.Updater
|
||||
statusManager *status.StatusManager
|
||||
|
|
@ -259,6 +263,14 @@ type GuiRepoState struct {
|
|||
|
||||
var _ types.IRepoStateAccessor = new(GuiRepoState)
|
||||
|
||||
// SharedRepoState is state shared between all worktrees of the same repo.
|
||||
// Unlike GuiRepoState, of which we keep one instance per worktree, there is
|
||||
// only one instance of this per repo; e.g. commits copied for cherry-picking
|
||||
// in one worktree can be pasted in another.
|
||||
type SharedRepoState struct {
|
||||
CherryPicking *cherrypicking.CherryPicking
|
||||
}
|
||||
|
||||
func (self *GuiRepoState) GetViewsSetup() bool {
|
||||
return self.ViewsSetup
|
||||
}
|
||||
|
|
@ -591,6 +603,15 @@ func (gui *Gui) resetState(startArgs appTypes.StartArgs) types.Context {
|
|||
return gui.c.Context().Current()
|
||||
}
|
||||
|
||||
repoGitDirPath := gui.git.RepoPaths.RepoGitDirPath()
|
||||
sharedState := gui.sharedRepoStateMap[Repo(repoGitDirPath)]
|
||||
if sharedState == nil {
|
||||
sharedState = &SharedRepoState{
|
||||
CherryPicking: cherrypicking.New(),
|
||||
}
|
||||
gui.sharedRepoStateMap[Repo(repoGitDirPath)] = sharedState
|
||||
}
|
||||
|
||||
contextTree := gui.contextTree()
|
||||
|
||||
initialScreenMode := initialScreenMode(startArgs, gui.Config)
|
||||
|
|
@ -614,7 +635,7 @@ func (gui *Gui) resetState(startArgs appTypes.StartArgs) types.Context {
|
|||
},
|
||||
Modes: &types.Modes{
|
||||
Filtering: filtering.New(startArgs.FilterPath, ""),
|
||||
CherryPicking: cherrypicking.New(),
|
||||
CherryPicking: sharedState.CherryPicking,
|
||||
Diffing: diffing.New(),
|
||||
MarkedBaseCommit: marked_base_commit.New(),
|
||||
},
|
||||
|
|
@ -738,6 +759,7 @@ func NewGui(
|
|||
showRecentRepos: showRecentRepos,
|
||||
RepoPathStack: &utils.StringStack{},
|
||||
RepoStateMap: map[Repo]*GuiRepoState{},
|
||||
sharedRepoStateMap: map[Repo]*SharedRepoState{},
|
||||
GuiLog: []string{},
|
||||
|
||||
// initializing this to true for the time being; it will be reset to the
|
||||
|
|
|
|||
|
|
@ -8,8 +8,13 @@ import (
|
|||
)
|
||||
|
||||
type Modes struct {
|
||||
Filtering filtering.Filtering
|
||||
CherryPicking *cherrypicking.CherryPicking
|
||||
Filtering filtering.Filtering
|
||||
|
||||
// Shared between all worktrees of the same repo (see gui.SharedRepoState).
|
||||
// Mutate it through this pointer, but never replace it, otherwise it is no
|
||||
// longer shared.
|
||||
CherryPicking *cherrypicking.CherryPicking
|
||||
|
||||
Diffing diffing.Diffing
|
||||
MarkedBaseCommit marked_base_commit.MarkedBaseCommit
|
||||
}
|
||||
|
|
|
|||
|
|
@ -44,7 +44,6 @@ var CherryPickAcrossWorktrees = NewIntegrationTest(NewIntegrationTestArgs{
|
|||
).
|
||||
Press(keys.Commits.PasteCommits)
|
||||
|
||||
/* EXPECTED:
|
||||
t.ExpectPopup().Alert().
|
||||
Title(Equals("Cherry-pick")).
|
||||
Content(Contains("Are you sure you want to cherry-pick the 1 copied commit(s) onto this branch?")).
|
||||
|
|
@ -57,7 +56,5 @@ var CherryPickAcrossWorktrees = NewIntegrationTest(NewIntegrationTestArgs{
|
|||
Contains("one"),
|
||||
Contains("base").IsSelected(),
|
||||
)
|
||||
ACTUAL: */
|
||||
t.ExpectToast(Equals("Disabled: No copied commits"))
|
||||
},
|
||||
})
|
||||
|
|
|
|||
Loading…
Reference in a new issue