summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJesse Duffield <jessedduffield@gmail.com>2023-05-29 14:24:49 +1000
committerJesse Duffield <jessedduffield@gmail.com>2023-05-29 14:24:49 +1000
commit16fa22a36ef24e433e49426052e4156cb49064e0 (patch)
tree86935a929fc63ab02eea4e587e8b2eef185c6729
parent8e6967c70273f838e4e200a61bdb631015d46bdc (diff)
Add suggestionsPreset to custom commands system
-rw-r--r--docs/Custom_Command_Keybindings.md1
-rw-r--r--pkg/config/user_config.go3
-rw-r--r--pkg/gui/services/custom_commands/client.go2
-rw-r--r--pkg/gui/services/custom_commands/handler_creator.go35
-rw-r--r--pkg/gui/services/custom_commands/resolver.go5
-rw-r--r--pkg/integration/tests/custom_commands/suggestions_preset.go64
-rw-r--r--pkg/integration/tests/test_list.go1
7 files changed, 107 insertions, 4 deletions
diff --git a/docs/Custom_Command_Keybindings.md b/docs/Custom_Command_Keybindings.md
index 62a034ecf..af9431d07 100644
--- a/docs/Custom_Command_Keybindings.md
+++ b/docs/Custom_Command_Keybindings.md
@@ -107,6 +107,7 @@ The permitted prompt fields are:
| type | one of 'input', 'menu', or 'confirm' | yes |
| title | the title to display in the popup panel | no |
| initialValue | (only applicable to 'input' prompts) the initial value to appear in the text box | no |
+| suggestionsPreset | (only applicable to 'input prompts'. Shows suggestions as the value is typed. One of 'files', 'branches', 'remotes', 'remoteBranches', refs'. | no |
| body | (only applicable to 'confirm' prompts) the immutable body text to appear in the text box | no |
| options | (only applicable to 'menu' prompts) the options to display in the menu | no |
| command | (only applicable to 'menuFromCommand' prompts) the command to run to generate | yes |
diff --git a/pkg/config/user_config.go b/pkg/config/user_config.go
index 3b311c0de..27ae17953 100644
--- a/pkg/config/user_config.go
+++ b/pkg/config/user_config.go
@@ -366,7 +366,8 @@ type CustomCommandPrompt struct {
Title string `yaml:"title"`
// this only apply to input prompts
- InitialValue string `yaml:"initialValue"`
+ InitialValue string `yaml:"initialValue"`
+ SuggestionsPreset string `yaml:"suggestionsPreset"`
// this only applies to confirm prompts
Body string `yaml:"body"`
diff --git a/pkg/gui/services/custom_commands/client.go b/pkg/gui/services/custom_commands/client.go
index 4cacba385..5e456ff6e 100644
--- a/pkg/gui/services/custom_commands/client.go
+++ b/pkg/gui/services/custom_commands/client.go
@@ -19,7 +19,7 @@ func NewClient(
helpers *helpers.Helpers,
) *Client {
sessionStateLoader := NewSessionStateLoader(c, helpers.Refs)
- handlerCreator := NewHandlerCreator(c, sessionStateLoader)
+ handlerCreator := NewHandlerCreator(c, sessionStateLoader, helpers.Suggestions)
keybindingCreator := NewKeybindingCreator(c)
customCommands := c.UserConfig.CustomCommands
diff --git a/pkg/gui/services/custom_commands/handler_creator.go b/pkg/gui/services/custom_commands/handler_creator.go
index da1c449fd..2d13a6f55 100644
--- a/pkg/gui/services/custom_commands/handler_creator.go
+++ b/pkg/gui/services/custom_commands/handler_creator.go
@@ -1,6 +1,7 @@
package custom_commands
import (
+ "fmt"
"strings"
"text/template"
@@ -18,11 +19,13 @@ type HandlerCreator struct {
sessionStateLoader *SessionStateLoader
resolver *Resolver
menuGenerator *MenuGenerator
+ suggestionsHelper *helpers.SuggestionsHelper
}
func NewHandlerCreator(
c *helpers.HelperCommon,
sessionStateLoader *SessionStateLoader,
+ suggestionsHelper *helpers.SuggestionsHelper,
) *HandlerCreator {
resolver := NewResolver(c.Common)
menuGenerator := NewMenuGenerator(c.Common)
@@ -32,6 +35,7 @@ func NewHandlerCreator(
sessionStateLoader: sessionStateLoader,
resolver: resolver,
menuGenerator: menuGenerator,
+ suggestionsHelper: suggestionsHelper,
}
}
@@ -104,15 +108,42 @@ func (self *HandlerCreator) call(customCommand config.CustomCommand) func() erro
}
func (self *HandlerCreator) inputPrompt(prompt *config.CustomCommandPrompt, wrappedF func(string) error) error {
+ var findSuggestionsFn func(string) []*types.Suggestion
+ if prompt.SuggestionsPreset != "" {
+ var err error
+ findSuggestionsFn, err = self.getPresetSuggestionsFn(prompt.SuggestionsPreset)
+ if err != nil {
+ return err
+ }
+ }
+
return self.c.Prompt(types.PromptOpts{
- Title: prompt.Title,
- InitialContent: prompt.InitialValue,
+ Title: prompt.Title,
+ InitialContent: prompt.InitialValue,
+ FindSuggestionsFunc: findSuggestionsFn,
HandleConfirm: func(str string) error {
return wrappedF(str)
},
})
}
+func (self *HandlerCreator) getPresetSuggestionsFn(preset string) (func(string) []*types.Suggestion, error) {
+ switch preset {
+ case "files":
+ return self.suggestionsHelper.GetFilePathSuggestionsFunc(), nil
+ case "branches":
+ return self.suggestionsHelper.GetBranchNameSuggestionsFunc(), nil
+ case "remotes":
+ return self.suggestionsHelper.GetRemoteSuggestionsFunc(), nil
+ case "remoteBranches":
+ return self.suggestionsHelper.GetRemoteBranchesSuggestionsFunc("/"), nil
+ case "refs":
+ return self.suggestionsHelper.GetRefsSuggestionsFunc(), nil
+ default:
+ return nil, fmt.Errorf("Unknown value for suggestionsPreset in custom command: %s. Valid values: files, branches, remotes, remoteBranches, refs", preset)
+ }
+}
+
func (self *HandlerCreator) menuPrompt(prompt *config.CustomCommandPrompt, wrappedF func(string) error) error {
menuItems := slices.Map(prompt.Options, func(option config.CustomCommandMenuOption) *types.MenuItem {
return &types.MenuItem{
diff --git a/pkg/gui/services/custom_commands/resolver.go b/pkg/gui/services/custom_commands/resolver.go
index 4c32a51ca..119581bfc 100644
--- a/pkg/gui/services/custom_commands/resolver.go
+++ b/pkg/gui/services/custom_commands/resolver.go
@@ -34,6 +34,11 @@ func (self *Resolver) resolvePrompt(
return nil, err
}
+ result.SuggestionsPreset, err = resolveTemplate(prompt.SuggestionsPreset)
+ if err != nil {
+ return nil, err
+ }
+
result.Body, err = resolveTemplate(prompt.Body)
if err != nil {
return nil, err
diff --git a/pkg/integration/tests/custom_commands/suggestions_preset.go b/pkg/integration/tests/custom_commands/suggestions_preset.go
new file mode 100644
index 000000000..894e3b1fe
--- /dev/null
+++ b/pkg/integration/tests/custom_commands/suggestions_preset.go
@@ -0,0 +1,64 @@
+package custom_commands
+
+import (
+ "github.com/jesseduffield/lazygit/pkg/config"
+ . "github.com/jesseduffield/lazygit/pkg/integration/components"
+)
+
+var SuggestionsPreset = NewIntegrationTest(NewIntegrationTestArgs{
+ Description: "Using a custom command that uses a suggestions preset in a prompt step",
+ ExtraCmdArgs: []string{},
+ Skip: false,
+ SetupRepo: func(shell *Shell) {
+ shell.NewBranch("branch-one")
+ shell.EmptyCommit("blah")
+ shell.NewBranch("branch-two")
+ shell.EmptyCommit("blah")
+ shell.NewBranch("branch-three")
+ shell.EmptyCommit("blah")
+ shell.NewBranch("branch-four")
+ shell.EmptyCommit("blah")
+ },
+ SetupConfig: func(cfg *config.AppConfig) {
+ cfg.UserConfig.CustomCommands = []config.CustomCommand{
+ {
+ Key: "a",
+ Context: "localBranches",
+ Command: `git checkout {{.Form.Branch}}`,
+ Prompts: []config.CustomCommandPrompt{
+ {
+ Key: "Branch",
+ Type: "input",
+ Title: "Enter a branch name",
+ SuggestionsPreset: "branches",
+ },
+ },
+ },
+ }
+ },
+ Run: func(t *TestDriver, keys config.KeybindingConfig) {
+ t.Views().Branches().
+ Focus().
+ Lines(
+ Contains("branch-four").IsSelected(),
+ Contains("branch-three"),
+ Contains("branch-two"),
+ Contains("branch-one"),
+ ).
+ Press("a")
+
+ t.ExpectPopup().Prompt().
+ Title(Equals("Enter a branch name")).
+ Type("three").
+ SuggestionLines(Contains("branch-three")).
+ ConfirmFirstSuggestion()
+
+ t.Views().Branches().
+ Lines(
+ Contains("branch-three").IsSelected(),
+ Contains("branch-four"),
+ Contains("branch-two"),
+ Contains("branch-one"),
+ )
+ },
+})
diff --git a/pkg/integration/tests/test_list.go b/pkg/integration/tests/test_list.go
index 1dd1a48e7..e0800f7bd 100644
--- a/pkg/integration/tests/test_list.go
+++ b/pkg/integration/tests/test_list.go
@@ -77,6 +77,7 @@ var tests = []*components.IntegrationTest{
custom_commands.MenuFromCommandsOutput,
custom_commands.MultiplePrompts,
custom_commands.OmitFromHistory,
+ custom_commands.SuggestionsPreset,
diff.Diff,
diff.DiffAndApplyPatch,
diff.DiffCommits,