diff --git a/docs/Config.md b/docs/Config.md index 25f9fcbd3..6be09a383 100644 --- a/docs/Config.md +++ b/docs/Config.md @@ -399,6 +399,16 @@ git: # displays the whole git graph by default in the commits view (equivalent to passing the `--all` argument to `git log`) showWholeGraph: false + # How branches are sorted in the local branches view. + # One of: 'date' (default) | 'recency' | 'alphabetical' + # Can be changed from within Lazygit with the Sort Order menu (`s`) in the branches panel. + localBranchSortOrder: date + + # How branches are sorted in the remote branches view. + # One of: 'date' (default) | 'alphabetical' + # Can be changed from within Lazygit with the Sort Order menu (`s`) in the remote branches panel. + remoteBranchSortOrder: date + # When copying commit hashes to the clipboard, truncate them to this # length. Set to 40 to disable truncation. truncateCopiedCommitHashesTo: 12 diff --git a/pkg/commands/git_commands/branch_loader.go b/pkg/commands/git_commands/branch_loader.go index 73127ae63..a4e41b756 100644 --- a/pkg/commands/git_commands/branch_loader.go +++ b/pkg/commands/git_commands/branch_loader.go @@ -74,7 +74,7 @@ func (self *BranchLoader) Load(reflogCommits []*models.Commit, ) ([]*models.Branch, error) { branches := self.obtainBranches() - if self.AppState.LocalBranchSortOrder == "recency" { + if self.UserConfig().Git.LocalBranchSortOrder == "recency" { reflogBranches := self.obtainReflogBranches(reflogCommits) // loop through reflog branches. If there is a match, merge them, then remove it from the branches and keep it in the reflog branches branchesWithRecency := make([]*models.Branch, 0) @@ -254,7 +254,7 @@ func (self *BranchLoader) obtainBranches() []*models.Branch { return nil, false } - storeCommitDateAsRecency := self.AppState.LocalBranchSortOrder != "recency" + storeCommitDateAsRecency := self.UserConfig().Git.LocalBranchSortOrder != "recency" return obtainBranch(split, storeCommitDateAsRecency), true }) } @@ -268,7 +268,7 @@ func (self *BranchLoader) getRawBranches() (string, error) { ) var sortOrder string - switch strings.ToLower(self.AppState.LocalBranchSortOrder) { + switch strings.ToLower(self.UserConfig().Git.LocalBranchSortOrder) { case "recency", "date": sortOrder = "-committerdate" case "alphabetical": diff --git a/pkg/commands/git_commands/remote_loader.go b/pkg/commands/git_commands/remote_loader.go index 1b2e33682..2e632def4 100644 --- a/pkg/commands/git_commands/remote_loader.go +++ b/pkg/commands/git_commands/remote_loader.go @@ -85,7 +85,7 @@ func (self *RemoteLoader) getRemoteBranchesByRemoteName() (map[string][]*models. remoteBranchesByRemoteName := make(map[string][]*models.RemoteBranch) var sortOrder string - switch strings.ToLower(self.AppState.RemoteBranchSortOrder) { + switch strings.ToLower(self.UserConfig().Git.RemoteBranchSortOrder) { case "alphabetical": sortOrder = "refname" case "date": diff --git a/pkg/config/app_config.go b/pkg/config/app_config.go index aaaf7adb3..184d8e07a 100644 --- a/pkg/config/app_config.go +++ b/pkg/config/app_config.go @@ -676,9 +676,7 @@ type AppState struct { // For backwards compatibility we keep the old name in yaml files. ShellCommandsHistory []string `yaml:"customcommandshistory"` - HideCommandLog bool - LocalBranchSortOrder string - RemoteBranchSortOrder string + HideCommandLog bool // One of: 'date-order' | 'author-date-order' | 'topo-order' | 'default' // 'topo-order' makes it easier to read the git log graph, but commits may not @@ -692,14 +690,12 @@ type AppState struct { func getDefaultAppState() *AppState { return &AppState{ - LastUpdateCheck: 0, - RecentRepos: []string{}, - StartupPopupVersion: 0, - LastVersion: "", - LocalBranchSortOrder: "recency", - RemoteBranchSortOrder: "alphabetical", - GitLogOrder: "", // should be "topo-order" eventually - GitLogShowGraph: "", // should be "always" eventually + LastUpdateCheck: 0, + RecentRepos: []string{}, + StartupPopupVersion: 0, + LastVersion: "", + GitLogOrder: "", // should be "topo-order" eventually + GitLogShowGraph: "", // should be "always" eventually } } diff --git a/pkg/config/user_config.go b/pkg/config/user_config.go index 39c67bc4b..5d619231e 100644 --- a/pkg/config/user_config.go +++ b/pkg/config/user_config.go @@ -285,6 +285,14 @@ type GitConfig struct { ParseEmoji bool `yaml:"parseEmoji"` // Config for showing the log in the commits view Log LogConfig `yaml:"log"` + // How branches are sorted in the local branches view. + // One of: 'date' (default) | 'recency' | 'alphabetical' + // Can be changed from within Lazygit with the Sort Order menu (`s`) in the branches panel. + LocalBranchSortOrder string `yaml:"localBranchSortOrder" jsonschema:"enum=date,enum=recency,enum=alphabetical"` + // How branches are sorted in the remote branches view. + // One of: 'date' (default) | 'alphabetical' + // Can be changed from within Lazygit with the Sort Order menu (`s`) in the remote branches panel. + RemoteBranchSortOrder string `yaml:"remoteBranchSortOrder" jsonschema:"enum=date,enum=alphabetical"` // When copying commit hashes to the clipboard, truncate them to this // length. Set to 40 to disable truncation. TruncateCopiedCommitHashesTo int `yaml:"truncateCopiedCommitHashesTo"` @@ -805,6 +813,8 @@ func GetDefaultConfig() *UserConfig { ShowGraph: "always", ShowWholeGraph: false, }, + LocalBranchSortOrder: "date", + RemoteBranchSortOrder: "date", SkipHookPrefix: "WIP", MainBranches: []string{"master", "main"}, AutoFetch: true, diff --git a/pkg/config/user_config_validation.go b/pkg/config/user_config_validation.go index f46dfca9a..5d43c4a28 100644 --- a/pkg/config/user_config_validation.go +++ b/pkg/config/user_config_validation.go @@ -23,6 +23,14 @@ func (config *UserConfig) Validate() error { []string{"none", "onlyMainBranches", "allBranches"}); err != nil { return err } + if err := validateEnum("git.localBranchSortOrder", config.Git.LocalBranchSortOrder, + []string{"date", "recency", "alphabetical"}); err != nil { + return err + } + if err := validateEnum("git.remoteBranchSortOrder", config.Git.RemoteBranchSortOrder, + []string{"date", "alphabetical"}); err != nil { + return err + } if err := validateKeybindings(config.Keybinding); err != nil { return err } diff --git a/pkg/config/user_config_validation_test.go b/pkg/config/user_config_validation_test.go index f98431713..67ff16991 100644 --- a/pkg/config/user_config_validation_test.go +++ b/pkg/config/user_config_validation_test.go @@ -56,6 +56,32 @@ func TestUserConfigValidate_enums(t *testing.T) { {value: "invalid_value", valid: false}, }, }, + { + name: "Git.LocalBranchSortOrder", + setup: func(config *UserConfig, value string) { + config.Git.LocalBranchSortOrder = value + }, + testCases: []testCase{ + {value: "date", valid: true}, + {value: "recency", valid: true}, + {value: "alphabetical", valid: true}, + {value: "", valid: false}, + {value: "invalid_value", valid: false}, + }, + }, + { + name: "Git.RemoteBranchSortOrder", + setup: func(config *UserConfig, value string) { + config.Git.RemoteBranchSortOrder = value + }, + testCases: []testCase{ + {value: "date", valid: true}, + {value: "recency", valid: false}, + {value: "alphabetical", valid: true}, + {value: "", valid: false}, + {value: "invalid_value", valid: false}, + }, + }, { name: "Keybindings", setup: func(config *UserConfig, value string) { diff --git a/pkg/gui/controllers/branches_controller.go b/pkg/gui/controllers/branches_controller.go index 454216df7..b49a5f6f3 100644 --- a/pkg/gui/controllers/branches_controller.go +++ b/pkg/gui/controllers/branches_controller.go @@ -674,16 +674,15 @@ func (self *BranchesController) createTag(branch *models.Branch) error { func (self *BranchesController) createSortMenu() error { return self.c.Helpers().Refs.CreateSortOrderMenu([]string{"recency", "alphabetical", "date"}, func(sortOrder string) error { - if self.c.GetAppState().LocalBranchSortOrder != sortOrder { - self.c.GetAppState().LocalBranchSortOrder = sortOrder - self.c.SaveAppStateAndLogError() + if self.c.UserConfig().Git.LocalBranchSortOrder != sortOrder { + self.c.UserConfig().Git.LocalBranchSortOrder = sortOrder self.c.Contexts().Branches.SetSelection(0) self.c.Refresh(types.RefreshOptions{Mode: types.ASYNC, Scope: []types.RefreshableView{types.BRANCHES}}) return nil } return nil }, - self.c.GetAppState().LocalBranchSortOrder) + self.c.UserConfig().Git.LocalBranchSortOrder) } func (self *BranchesController) createResetMenu(selectedBranch *models.Branch) error { diff --git a/pkg/gui/controllers/helpers/refresh_helper.go b/pkg/gui/controllers/helpers/refresh_helper.go index e377cfdf9..2682d8296 100644 --- a/pkg/gui/controllers/helpers/refresh_helper.go +++ b/pkg/gui/controllers/helpers/refresh_helper.go @@ -125,7 +125,7 @@ func (self *RefreshHelper) Refresh(options types.RefreshOptions) { refresh("commits and commit files", self.refreshCommitsAndCommitFiles) includeWorktreesWithBranches = scopeSet.Includes(types.WORKTREES) - if self.c.AppState.LocalBranchSortOrder == "recency" { + if self.c.UserConfig().Git.LocalBranchSortOrder == "recency" { refresh("reflog and branches", func() { self.refreshReflogAndBranches(includeWorktreesWithBranches, options.KeepBranchSelectionIndex) }) } else { refresh("branches", func() { self.refreshBranches(includeWorktreesWithBranches, options.KeepBranchSelectionIndex, true) }) @@ -446,7 +446,7 @@ func (self *RefreshHelper) refreshBranches(refreshWorktrees bool, keepBranchSele defer self.c.Mutexes().RefreshingBranchesMutex.Unlock() reflogCommits := self.c.Model().FilteredReflogCommits - if self.c.Modes().Filtering.Active() && self.c.AppState.LocalBranchSortOrder == "recency" { + if self.c.Modes().Filtering.Active() && self.c.UserConfig().Git.LocalBranchSortOrder == "recency" { // in filter mode we filter our reflog commits to just those containing the path // however we need all the reflog entries to populate the recencies of our branches // which allows us to order them correctly. So if we're filtering we'll just diff --git a/pkg/gui/controllers/remote_branches_controller.go b/pkg/gui/controllers/remote_branches_controller.go index 629bbbaa3..3bb99380a 100644 --- a/pkg/gui/controllers/remote_branches_controller.go +++ b/pkg/gui/controllers/remote_branches_controller.go @@ -146,15 +146,14 @@ func (self *RemoteBranchesController) rebase(selectedBranch *models.RemoteBranch func (self *RemoteBranchesController) createSortMenu() error { return self.c.Helpers().Refs.CreateSortOrderMenu([]string{"alphabetical", "date"}, func(sortOrder string) error { - if self.c.GetAppState().RemoteBranchSortOrder != sortOrder { - self.c.GetAppState().RemoteBranchSortOrder = sortOrder - self.c.SaveAppStateAndLogError() + if self.c.UserConfig().Git.RemoteBranchSortOrder != sortOrder { + self.c.UserConfig().Git.RemoteBranchSortOrder = sortOrder self.c.Contexts().RemoteBranches.SetSelection(0) self.c.Refresh(types.RefreshOptions{Mode: types.ASYNC, Scope: []types.RefreshableView{types.REMOTES}}) } return nil }, - self.c.GetAppState().RemoteBranchSortOrder) + self.c.UserConfig().Git.RemoteBranchSortOrder) } func (self *RemoteBranchesController) createResetMenu(selectedBranch *models.RemoteBranch) error { diff --git a/pkg/integration/tests/branch/checkout_by_name.go b/pkg/integration/tests/branch/checkout_by_name.go index 127ea10dd..af06162a7 100644 --- a/pkg/integration/tests/branch/checkout_by_name.go +++ b/pkg/integration/tests/branch/checkout_by_name.go @@ -33,8 +33,8 @@ var CheckoutByName = NewIntegrationTest(NewIntegrationTestArgs{ }). Lines( MatchesRegexp(`\*.*new-branch`).IsSelected(), - Contains("master"), Contains("@"), + Contains("master"), ) }, }) diff --git a/pkg/integration/tests/branch/delete.go b/pkg/integration/tests/branch/delete.go index ae29a679c..5da844622 100644 --- a/pkg/integration/tests/branch/delete.go +++ b/pkg/integration/tests/branch/delete.go @@ -9,7 +9,9 @@ var Delete = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Try all combination of local and remote branch deletions", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shell. CloneIntoRemote("origin"). diff --git a/pkg/integration/tests/branch/delete_multiple.go b/pkg/integration/tests/branch/delete_multiple.go index a03a822f6..0bba33b9d 100644 --- a/pkg/integration/tests/branch/delete_multiple.go +++ b/pkg/integration/tests/branch/delete_multiple.go @@ -10,7 +10,8 @@ var DeleteMultiple = NewIntegrationTest(NewIntegrationTestArgs{ ExtraCmdArgs: []string{}, Skip: false, SetupConfig: func(config *config.AppConfig) { - config.GetAppState().LocalBranchSortOrder = "alphabetic" + config.GetUserConfig().Git.LocalBranchSortOrder = "alphabetical" + config.GetUserConfig().Git.RemoteBranchSortOrder = "alphabetical" }, SetupRepo: func(shell *Shell) { shell. diff --git a/pkg/integration/tests/branch/delete_while_filtering.go b/pkg/integration/tests/branch/delete_while_filtering.go index d967ff40f..2b2039d67 100644 --- a/pkg/integration/tests/branch/delete_while_filtering.go +++ b/pkg/integration/tests/branch/delete_while_filtering.go @@ -12,7 +12,7 @@ var DeleteWhileFiltering = NewIntegrationTest(NewIntegrationTestArgs{ ExtraCmdArgs: []string{}, Skip: false, SetupConfig: func(config *config.AppConfig) { - config.GetAppState().LocalBranchSortOrder = "alphabetic" + config.GetUserConfig().Git.LocalBranchSortOrder = "alphabetical" }, SetupRepo: func(shell *Shell) { shell.EmptyCommit("one") diff --git a/pkg/integration/tests/branch/rebase.go b/pkg/integration/tests/branch/rebase.go index 6bc2083c4..3c86ddffc 100644 --- a/pkg/integration/tests/branch/rebase.go +++ b/pkg/integration/tests/branch/rebase.go @@ -10,7 +10,9 @@ var Rebase = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Rebase onto another branch, deal with the conflicts.", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shared.MergeConflictsSetup(shell) }, diff --git a/pkg/integration/tests/branch/rebase_abort_on_conflict.go b/pkg/integration/tests/branch/rebase_abort_on_conflict.go index 47f59d3d1..79ceba510 100644 --- a/pkg/integration/tests/branch/rebase_abort_on_conflict.go +++ b/pkg/integration/tests/branch/rebase_abort_on_conflict.go @@ -10,7 +10,9 @@ var RebaseAbortOnConflict = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Rebase onto another branch, abort when there are conflicts.", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shared.MergeConflictsSetup(shell) }, diff --git a/pkg/integration/tests/branch/rebase_and_drop.go b/pkg/integration/tests/branch/rebase_and_drop.go index 896d27068..ff17d6417 100644 --- a/pkg/integration/tests/branch/rebase_and_drop.go +++ b/pkg/integration/tests/branch/rebase_and_drop.go @@ -10,7 +10,9 @@ var RebaseAndDrop = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Rebase onto another branch, deal with the conflicts. Also mark a commit to be dropped before continuing.", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shared.MergeConflictsSetup(shell) // adding a couple additional commits so that we can drop one diff --git a/pkg/integration/tests/branch/rebase_cancel_on_conflict.go b/pkg/integration/tests/branch/rebase_cancel_on_conflict.go index 03923c81d..be69f9753 100644 --- a/pkg/integration/tests/branch/rebase_cancel_on_conflict.go +++ b/pkg/integration/tests/branch/rebase_cancel_on_conflict.go @@ -10,7 +10,9 @@ var RebaseCancelOnConflict = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Rebase onto another branch, cancel when there are conflicts.", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shared.MergeConflictsSetup(shell) }, diff --git a/pkg/integration/tests/branch/rebase_conflicts_fix_build_errors.go b/pkg/integration/tests/branch/rebase_conflicts_fix_build_errors.go index 2ae75dafb..3690f8f2e 100644 --- a/pkg/integration/tests/branch/rebase_conflicts_fix_build_errors.go +++ b/pkg/integration/tests/branch/rebase_conflicts_fix_build_errors.go @@ -10,7 +10,9 @@ var RebaseConflictsFixBuildErrors = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Rebase onto another branch, deal with the conflicts. While continue prompt is showing, fix build errors; get another prompt when continuing.", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shared.MergeConflictsSetup(shell) }, diff --git a/pkg/integration/tests/branch/rebase_from_marked_base.go b/pkg/integration/tests/branch/rebase_from_marked_base.go index c26dce9a3..3dd60184b 100644 --- a/pkg/integration/tests/branch/rebase_from_marked_base.go +++ b/pkg/integration/tests/branch/rebase_from_marked_base.go @@ -9,7 +9,9 @@ var RebaseFromMarkedBase = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Rebase onto another branch from a marked base commit", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shell. NewBranch("base-branch"). diff --git a/pkg/integration/tests/branch/reset_to_upstream.go b/pkg/integration/tests/branch/reset_to_upstream.go index e5503f127..9a5ea498e 100644 --- a/pkg/integration/tests/branch/reset_to_upstream.go +++ b/pkg/integration/tests/branch/reset_to_upstream.go @@ -9,7 +9,9 @@ var ResetToUpstream = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Hard reset the current branch to the selected branch upstream", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shell. CloneIntoRemote("origin"). diff --git a/pkg/integration/tests/branch/sort_local_branches.go b/pkg/integration/tests/branch/sort_local_branches.go index ceff654be..9c29e17bf 100644 --- a/pkg/integration/tests/branch/sort_local_branches.go +++ b/pkg/integration/tests/branch/sort_local_branches.go @@ -22,13 +22,13 @@ var SortLocalBranches = NewIntegrationTest(NewIntegrationTestArgs{ Checkout("master") }, Run: func(t *TestDriver, keys config.KeybindingConfig) { - // sorted by recency by default + // sorted by date by default t.Views().Branches(). Focus(). Lines( Contains("master").IsSelected(), - Contains("third"), Contains("second"), + Contains("third"), Contains("first"), ). SelectNextItem() // to test that the selection jumps back to the top when sorting @@ -38,20 +38,20 @@ var SortLocalBranches = NewIntegrationTest(NewIntegrationTestArgs{ t.ExpectPopup().Menu().Title(Equals("Sort order")). Lines( - Contains("r (•) Recency").IsSelected(), + Contains("r ( ) Recency").IsSelected(), Contains("a ( ) Alphabetical"), - Contains("d ( ) Date"), + Contains("d (•) Date"), Contains(" Cancel"), ). - Select(Contains("-committerdate")). + Select(Contains("Recency")). Confirm() t.Views().Branches(). IsFocused(). Lines( Contains("master").IsSelected(), - Contains("second"), Contains("third"), + Contains("second"), Contains("first"), ) @@ -60,9 +60,9 @@ var SortLocalBranches = NewIntegrationTest(NewIntegrationTestArgs{ t.ExpectPopup().Menu().Title(Equals("Sort order")). Lines( - Contains("r ( ) Recency").IsSelected(), + Contains("r (•) Recency").IsSelected(), Contains("a ( ) Alphabetical"), - Contains("d (•) Date"), + Contains("d ( ) Date"), Contains(" Cancel"), ). Select(Contains("refname")). diff --git a/pkg/integration/tests/branch/sort_remote_branches.go b/pkg/integration/tests/branch/sort_remote_branches.go index 2cbbdb31d..90c787f41 100644 --- a/pkg/integration/tests/branch/sort_remote_branches.go +++ b/pkg/integration/tests/branch/sort_remote_branches.go @@ -27,13 +27,13 @@ var SortRemoteBranches = NewIntegrationTest(NewIntegrationTestArgs{ ). PressEnter() - // sorted alphabetically by default + // sorted by date by default t.Views().RemoteBranches(). IsFocused(). Lines( - Contains("first").IsSelected(), - Contains("second"), + Contains("second").IsSelected(), Contains("third"), + Contains("first"), ). SelectNextItem() // to test that the selection jumps back to the first when sorting @@ -42,19 +42,19 @@ var SortRemoteBranches = NewIntegrationTest(NewIntegrationTestArgs{ t.ExpectPopup().Menu().Title(Equals("Sort order")). Lines( - Contains("a (•) Alphabetical").IsSelected(), - Contains("d ( ) Date"), + Contains("a ( ) Alphabetical").IsSelected(), + Contains("d (•) Date"), Contains(" Cancel"), ). - Select(Contains("-committerdate")). + Select(Contains("Alphabetical")). Confirm() t.Views().RemoteBranches(). IsFocused(). Lines( - Contains("second").IsSelected(), + Contains("first").IsSelected(), + Contains("second"), Contains("third"), - Contains("first"), ) }, }) diff --git a/pkg/integration/tests/cherry_pick/cherry_pick.go b/pkg/integration/tests/cherry_pick/cherry_pick.go index ccdb606f8..a278a5639 100644 --- a/pkg/integration/tests/cherry_pick/cherry_pick.go +++ b/pkg/integration/tests/cherry_pick/cherry_pick.go @@ -9,7 +9,9 @@ var CherryPick = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Cherry pick commits from the subcommits view, without conflicts", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shell. EmptyCommit("base"). diff --git a/pkg/integration/tests/cherry_pick/cherry_pick_conflicts.go b/pkg/integration/tests/cherry_pick/cherry_pick_conflicts.go index f3d5eca82..b135bfd7f 100644 --- a/pkg/integration/tests/cherry_pick/cherry_pick_conflicts.go +++ b/pkg/integration/tests/cherry_pick/cherry_pick_conflicts.go @@ -10,7 +10,9 @@ var CherryPickConflicts = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Cherry pick commits from the subcommits view, with conflicts", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shared.MergeConflictsSetup(shell) }, diff --git a/pkg/integration/tests/cherry_pick/cherry_pick_during_rebase.go b/pkg/integration/tests/cherry_pick/cherry_pick_during_rebase.go index af4e8b9d2..45811fad7 100644 --- a/pkg/integration/tests/cherry_pick/cherry_pick_during_rebase.go +++ b/pkg/integration/tests/cherry_pick/cherry_pick_during_rebase.go @@ -11,6 +11,7 @@ var CherryPickDuringRebase = NewIntegrationTest(NewIntegrationTestArgs{ Skip: false, SetupConfig: func(config *config.AppConfig) { config.GetAppState().GitLogShowGraph = "never" + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" }, SetupRepo: func(shell *Shell) { shell. diff --git a/pkg/integration/tests/cherry_pick/cherry_pick_merge.go b/pkg/integration/tests/cherry_pick/cherry_pick_merge.go index 7c68ce8eb..6c883cfa4 100644 --- a/pkg/integration/tests/cherry_pick/cherry_pick_merge.go +++ b/pkg/integration/tests/cherry_pick/cherry_pick_merge.go @@ -9,7 +9,9 @@ var CherryPickMerge = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Cherry pick a merge commit", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shell. EmptyCommit("base"). diff --git a/pkg/integration/tests/cherry_pick/cherry_pick_range.go b/pkg/integration/tests/cherry_pick/cherry_pick_range.go index 329ef1e9c..dfebeae2e 100644 --- a/pkg/integration/tests/cherry_pick/cherry_pick_range.go +++ b/pkg/integration/tests/cherry_pick/cherry_pick_range.go @@ -9,7 +9,9 @@ var CherryPickRange = NewIntegrationTest(NewIntegrationTestArgs{ Description: "Cherry pick range of commits from the subcommits view, without conflicts", ExtraCmdArgs: []string{}, Skip: false, - SetupConfig: func(config *config.AppConfig) {}, + SetupConfig: func(config *config.AppConfig) { + config.GetUserConfig().Git.LocalBranchSortOrder = "recency" + }, SetupRepo: func(shell *Shell) { shell. EmptyCommit("base"). diff --git a/pkg/integration/tests/commit/checkout.go b/pkg/integration/tests/commit/checkout.go index 7815e89de..7f2f4e0d9 100644 --- a/pkg/integration/tests/commit/checkout.go +++ b/pkg/integration/tests/commit/checkout.go @@ -42,8 +42,8 @@ var Checkout = NewIntegrationTest(NewIntegrationTestArgs{ Confirm() t.Views().Branches().Lines( Contains("* (HEAD detached at"), - Contains("branch2"), Contains("branch1"), + Contains("branch2"), Contains("master"), ) @@ -63,8 +63,8 @@ var Checkout = NewIntegrationTest(NewIntegrationTestArgs{ Confirm() t.Views().Branches().Lines( Contains("master"), - Contains("branch2"), Contains("branch1"), + Contains("branch2"), ) }, }) diff --git a/pkg/integration/tests/custom_commands/check_for_conflicts.go b/pkg/integration/tests/custom_commands/check_for_conflicts.go index 25f1d2097..d3376b456 100644 --- a/pkg/integration/tests/custom_commands/check_for_conflicts.go +++ b/pkg/integration/tests/custom_commands/check_for_conflicts.go @@ -24,6 +24,8 @@ var CheckForConflicts = NewIntegrationTest(NewIntegrationTestArgs{ }, }, } + + cfg.GetUserConfig().Git.LocalBranchSortOrder = "recency" }, Run: func(t *TestDriver, keys config.KeybindingConfig) { t.Views().Branches(). diff --git a/pkg/integration/tests/custom_commands/suggestions_command.go b/pkg/integration/tests/custom_commands/suggestions_command.go index 4b6aa0f4e..0710a7698 100644 --- a/pkg/integration/tests/custom_commands/suggestions_command.go +++ b/pkg/integration/tests/custom_commands/suggestions_command.go @@ -43,9 +43,9 @@ var SuggestionsCommand = NewIntegrationTest(NewIntegrationTestArgs{ Focus(). Lines( Contains("branch-four").IsSelected(), + Contains("branch-one"), Contains("branch-three"), Contains("branch-two"), - Contains("branch-one"), ). Press("a") @@ -59,8 +59,8 @@ var SuggestionsCommand = NewIntegrationTest(NewIntegrationTestArgs{ Lines( Contains("branch-three"), Contains("branch-four").IsSelected(), - Contains("branch-two"), Contains("branch-one"), + Contains("branch-two"), ) }, }) diff --git a/pkg/integration/tests/custom_commands/suggestions_preset.go b/pkg/integration/tests/custom_commands/suggestions_preset.go index aa599946f..41a16e271 100644 --- a/pkg/integration/tests/custom_commands/suggestions_preset.go +++ b/pkg/integration/tests/custom_commands/suggestions_preset.go @@ -43,9 +43,9 @@ var SuggestionsPreset = NewIntegrationTest(NewIntegrationTestArgs{ Focus(). Lines( Contains("branch-four").IsSelected(), + Contains("branch-one"), Contains("branch-three"), Contains("branch-two"), - Contains("branch-one"), ). Press("a") @@ -59,8 +59,8 @@ var SuggestionsPreset = NewIntegrationTest(NewIntegrationTestArgs{ Lines( Contains("branch-three"), Contains("branch-four").IsSelected(), - Contains("branch-two"), Contains("branch-one"), + Contains("branch-two"), ) }, }) diff --git a/pkg/integration/tests/filter_and_search/filter_updates_when_model_changes.go b/pkg/integration/tests/filter_and_search/filter_updates_when_model_changes.go index 1907a7159..5def8bfe5 100644 --- a/pkg/integration/tests/filter_and_search/filter_updates_when_model_changes.go +++ b/pkg/integration/tests/filter_and_search/filter_updates_when_model_changes.go @@ -21,9 +21,9 @@ var FilterUpdatesWhenModelChanges = NewIntegrationTest(NewIntegrationTestArgs{ Focus(). Lines( Contains("checked-out-branch").IsSelected(), - Contains("other"), Contains("branch-to-delete"), Contains("master"), + Contains("other"), ). FilterOrSearch("branch"). Lines( @@ -65,9 +65,9 @@ var FilterUpdatesWhenModelChanges = NewIntegrationTest(NewIntegrationTestArgs{ PressEscape(). Lines( Contains("checked-out-branch").IsSelected(), - Contains("other"), Contains("master"), Contains("new-branch"), + Contains("other"), ) }, }) diff --git a/pkg/integration/tests/filter_and_search/nested_filter.go b/pkg/integration/tests/filter_and_search/nested_filter.go index db20dd5b5..b94f8990f 100644 --- a/pkg/integration/tests/filter_and_search/nested_filter.go +++ b/pkg/integration/tests/filter_and_search/nested_filter.go @@ -35,8 +35,8 @@ var NestedFilter = NewIntegrationTest(NewIntegrationTestArgs{ Focus(). Lines( Contains(`branch-bronze`).IsSelected(), - Contains(`branch-silver`), Contains(`branch-gold`), + Contains(`branch-silver`), ). FilterOrSearch("sil"). Lines( @@ -148,8 +148,8 @@ var NestedFilter = NewIntegrationTest(NewIntegrationTestArgs{ }). Lines( Contains(`branch-bronze`), - Contains(`branch-silver`).IsSelected(), Contains(`branch-gold`), + Contains(`branch-silver`).IsSelected(), ) }, }) diff --git a/schema/config.json b/schema/config.json index 9da832b4e..a98076ecb 100644 --- a/schema/config.json +++ b/schema/config.json @@ -416,6 +416,25 @@ "$ref": "#/$defs/LogConfig", "description": "Config for showing the log in the commits view" }, + "localBranchSortOrder": { + "type": "string", + "enum": [ + "date", + "recency", + "alphabetical" + ], + "description": "How branches are sorted in the local branches view.\nOne of: 'date' (default) | 'recency' | 'alphabetical'\nCan be changed from within Lazygit with the Sort Order menu (`s`) in the branches panel.", + "default": "date" + }, + "remoteBranchSortOrder": { + "type": "string", + "enum": [ + "date", + "alphabetical" + ], + "description": "How branches are sorted in the remote branches view.\nOne of: 'date' (default) | 'alphabetical'\nCan be changed from within Lazygit with the Sort Order menu (`s`) in the remote branches panel.", + "default": "date" + }, "truncateCopiedCommitHashesTo": { "type": "integer", "description": "When copying commit hashes to the clipboard, truncate them to this\nlength. Set to 40 to disable truncation.",