mirror of
https://github.com/jesseduffield/lazygit.git
synced 2025-04-19 17:02:18 +03:00
119 lines
3.5 KiB
Go
119 lines
3.5 KiB
Go
package config
|
|
|
|
import (
|
|
"fmt"
|
|
"log"
|
|
"reflect"
|
|
"slices"
|
|
"strings"
|
|
|
|
"github.com/jesseduffield/lazygit/pkg/constants"
|
|
)
|
|
|
|
func (config *UserConfig) Validate() error {
|
|
if err := validateEnum("gui.statusPanelView", config.Gui.StatusPanelView,
|
|
[]string{"dashboard", "allBranchesLog"}); err != nil {
|
|
return err
|
|
}
|
|
if err := validateEnum("gui.showDivergenceFromBaseBranch", config.Gui.ShowDivergenceFromBaseBranch,
|
|
[]string{"none", "onlyArrow", "arrowAndNumber"}); err != nil {
|
|
return err
|
|
}
|
|
if err := validateKeybindings(config.Keybinding); err != nil {
|
|
return err
|
|
}
|
|
if err := validateCustomCommands(config.CustomCommands); err != nil {
|
|
return err
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func validateEnum(name string, value string, allowedValues []string) error {
|
|
if slices.Contains(allowedValues, value) {
|
|
return nil
|
|
}
|
|
allowedValuesStr := strings.Join(allowedValues, ", ")
|
|
return fmt.Errorf("Unexpected value '%s' for '%s'. Allowed values: %s", value, name, allowedValuesStr)
|
|
}
|
|
|
|
func validateKeybindingsRecurse(path string, node any) error {
|
|
value := reflect.ValueOf(node)
|
|
if value.Kind() == reflect.Struct {
|
|
for _, field := range reflect.VisibleFields(reflect.TypeOf(node)) {
|
|
var newPath string
|
|
if len(path) == 0 {
|
|
newPath = field.Name
|
|
} else {
|
|
newPath = fmt.Sprintf("%s.%s", path, field.Name)
|
|
}
|
|
if err := validateKeybindingsRecurse(newPath,
|
|
value.FieldByName(field.Name).Interface()); err != nil {
|
|
return err
|
|
}
|
|
}
|
|
} else if value.Kind() == reflect.Slice {
|
|
for i := 0; i < value.Len(); i++ {
|
|
if err := validateKeybindingsRecurse(
|
|
fmt.Sprintf("%s[%d]", path, i), value.Index(i).Interface()); err != nil {
|
|
return err
|
|
}
|
|
}
|
|
} else if value.Kind() == reflect.String {
|
|
key := node.(string)
|
|
if !isValidKeybindingKey(key) {
|
|
return fmt.Errorf("Unrecognized key '%s' for keybinding '%s'. For permitted values see %s",
|
|
key, path, constants.Links.Docs.CustomKeybindings)
|
|
}
|
|
} else {
|
|
log.Fatalf("Unexpected type for property '%s': %s", path, value.Kind())
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func validateKeybindings(keybindingConfig KeybindingConfig) error {
|
|
if err := validateKeybindingsRecurse("", keybindingConfig); err != nil {
|
|
return err
|
|
}
|
|
|
|
if len(keybindingConfig.Universal.JumpToBlock) != 5 {
|
|
return fmt.Errorf("keybinding.universal.jumpToBlock must have 5 elements; found %d.",
|
|
len(keybindingConfig.Universal.JumpToBlock))
|
|
}
|
|
|
|
return nil
|
|
}
|
|
|
|
func validateCustomCommandKey(key string) error {
|
|
if !isValidKeybindingKey(key) {
|
|
return fmt.Errorf("Unrecognized key '%s' for custom command. For permitted values see %s",
|
|
key, constants.Links.Docs.CustomKeybindings)
|
|
}
|
|
return nil
|
|
}
|
|
|
|
func validateCustomCommands(customCommands []CustomCommand) error {
|
|
for _, customCommand := range customCommands {
|
|
if err := validateCustomCommandKey(customCommand.Key); err != nil {
|
|
return err
|
|
}
|
|
|
|
if len(customCommand.CommandMenu) > 0 &&
|
|
(len(customCommand.Context) > 0 ||
|
|
len(customCommand.Command) > 0 ||
|
|
customCommand.Subprocess != nil ||
|
|
len(customCommand.Prompts) > 0 ||
|
|
len(customCommand.LoadingText) > 0 ||
|
|
customCommand.Stream != nil ||
|
|
customCommand.ShowOutput != nil ||
|
|
len(customCommand.OutputTitle) > 0 ||
|
|
customCommand.After != nil) {
|
|
commandRef := ""
|
|
if len(customCommand.Key) > 0 {
|
|
commandRef = fmt.Sprintf(" with key '%s'", customCommand.Key)
|
|
}
|
|
return fmt.Errorf("Error with custom command%s: it is not allowed to use both commandMenu and any of the other fields except key and description.", commandRef)
|
|
}
|
|
}
|
|
return nil
|
|
}
|