diff --git a/pkg/commands/git_commands/stash.go b/pkg/commands/git_commands/stash.go index 26460bfa0..71b8f655b 100644 --- a/pkg/commands/git_commands/stash.go +++ b/pkg/commands/git_commands/stash.go @@ -38,7 +38,6 @@ func (self *StashCommands) Apply(index int) error { } // Save save stash -// TODO: before calling this, check if there is anything to save func (self *StashCommands) Save(message string) error { return self.cmd.New("git stash save " + self.cmd.Quote(message)).Run() } @@ -53,6 +52,19 @@ func (self *StashCommands) StashAndKeepIndex(message string) error { return self.cmd.New(fmt.Sprintf("git stash save %s --keep-index", self.cmd.Quote(message))).Run() } +func (self *StashCommands) StashUnstagedChanges(message string) error { + if err := self.cmd.New("git commit -m \"WIP\"").Run(); err != nil { + return err + } + if err := self.Save(message); err != nil { + return err + } + if err := self.cmd.New("git reset --soft HEAD^").Run(); err != nil { + return err + } + return nil +} + // SaveStagedChanges stashes only the currently staged changes. This takes a few steps // shoutouts to Joe on https://stackoverflow.com/questions/14759748/stashing-only-staged-changes-in-git-is-it-possible func (self *StashCommands) SaveStagedChanges(message string) error { diff --git a/pkg/gui/controllers/files_controller.go b/pkg/gui/controllers/files_controller.go index e37cc0951..26c6e131f 100644 --- a/pkg/gui/controllers/files_controller.go +++ b/pkg/gui/controllers/files_controller.go @@ -559,21 +559,37 @@ func (self *FilesController) createStashMenu() error { { DisplayString: self.c.Tr.LcStashAllChanges, OnPress: func() error { - return self.handleStashSave(self.git.Stash.Save, self.c.Tr.Actions.StashAllChanges) + return self.handleStashSave(self.git.Stash.Save, self.c.Tr.Actions.StashAllChanges, self.c.Tr.NoFilesToStash) }, Key: 'a', }, { DisplayString: self.c.Tr.LcStashAllChangesKeepIndex, OnPress: func() error { - return self.handleStagedStashSave() + // if there are no staged files it behaves the same as Stash.Save + return self.handleStashSave(self.git.Stash.StashAndKeepIndex, self.c.Tr.Actions.StashAllChangesKeepIndex, self.c.Tr.NoFilesToStash) }, Key: 'i', }, + { + DisplayString: self.c.Tr.LcStashStagedChanges, + OnPress: func() error { + // there must be something in staging otherwise the current implementation mucks the stash up + if !self.helpers.WorkingTree.AnyStagedFiles() { + return self.c.ErrorMsg(self.c.Tr.NoTrackedStagedFilesStash) + } + return self.handleStashSave(self.git.Stash.SaveStagedChanges, self.c.Tr.Actions.StashStagedChanges, self.c.Tr.NoTrackedStagedFilesStash) + }, + Key: 's', + }, { DisplayString: self.c.Tr.LcStashUnstagedChanges, OnPress: func() error { - return self.handleStashSave(self.git.Stash.StashAndKeepIndex, self.c.Tr.Actions.StashUnstagedChanges) + if self.helpers.WorkingTree.AnyStagedFiles() { + return self.handleStashSave(self.git.Stash.StashUnstagedChanges, self.c.Tr.Actions.StashUnstagedChanges, self.c.Tr.NoFilesToStash) + } + // ordinary stash + return self.handleStashSave(self.git.Stash.Save, self.c.Tr.Actions.StashUnstagedChanges, self.c.Tr.NoFilesToStash) }, Key: 'u', }, @@ -582,7 +598,7 @@ func (self *FilesController) createStashMenu() error { } func (self *FilesController) stash() error { - return self.handleStashSave(self.git.Stash.Save, self.c.Tr.Actions.StashAllChanges) + return self.handleStashSave(self.git.Stash.Save, self.c.Tr.Actions.StashAllChanges, self.c.Tr.NoTrackedStagedFilesStash) } func (self *FilesController) createResetToUpstreamMenu() error { @@ -610,17 +626,9 @@ func (self *FilesController) toggleTreeView() error { return self.c.PostRefreshUpdate(self.context()) } -func (self *FilesController) handleStagedStashSave() error { - if !self.helpers.WorkingTree.AnyStagedFiles() { - return self.c.ErrorMsg(self.c.Tr.NoTrackedStagedFilesStash) - } - - return self.handleStashSave(self.git.Stash.StashAndKeepIndex, self.c.Tr.Actions.StashStagedChanges) -} - -func (self *FilesController) handleStashSave(stashFunc func(message string) error, action string) error { +func (self *FilesController) handleStashSave(stashFunc func(message string) error, action string, errorMsg string) error { if !self.helpers.WorkingTree.IsWorkingTreeDirty() { - return self.c.ErrorMsg(self.c.Tr.NoTrackedStagedFilesStash) + return self.c.ErrorMsg(errorMsg) } return self.c.Prompt(types.PromptOpts{ diff --git a/pkg/i18n/english.go b/pkg/i18n/english.go index 1df120dda..b34dcf369 100644 --- a/pkg/i18n/english.go +++ b/pkg/i18n/english.go @@ -119,6 +119,7 @@ type TranslationSet struct { StashApply string SureApplyStashEntry string NoTrackedStagedFilesStash string + NoFilesToStash string StashChanges string MergeAborted string OpenConfig string @@ -276,6 +277,7 @@ type TranslationSet struct { PressEnterToReturn string LcViewStashOptions string LcStashAllChanges string + LcStashStagedChanges string LcStashAllChangesKeepIndex string LcStashUnstagedChanges string LcStashOptions string @@ -545,6 +547,7 @@ type Actions struct { Pull string OpenFile string StashAllChanges string + StashAllChangesKeepIndex string StashStagedChanges string StashUnstagedChanges string GitFlowFinish string @@ -720,6 +723,7 @@ func EnglishTranslationSet() TranslationSet { StashApply: "Stash apply", SureApplyStashEntry: "Are you sure you want to apply this stash entry?", NoTrackedStagedFilesStash: "You have no tracked/staged files to stash", + NoFilesToStash: "You have no files to stash", StashChanges: "Stash changes", MergeAborted: "Merge aborted", OpenConfig: "open config file", @@ -878,6 +882,7 @@ func EnglishTranslationSet() TranslationSet { PressEnterToReturn: "Press enter to return to lazygit", LcViewStashOptions: "view stash options", LcStashAllChanges: "stash all changes", + LcStashStagedChanges: "stash staged changes", LcStashAllChangesKeepIndex: "stash all changes and keep index", LcStashUnstagedChanges: "stash unstaged changes", LcStashOptions: "Stash options", @@ -1130,6 +1135,7 @@ func EnglishTranslationSet() TranslationSet { Pull: "Pull", OpenFile: "Open file", StashAllChanges: "Stash all changes", + StashAllChangesKeepIndex: "Stash all changes and keep index", StashStagedChanges: "Stash staged changes", StashUnstagedChanges: "Stash unstaged changes", GitFlowFinish: "Git flow finish",