ref: use `plugins` part of config file

To avoid any conflict with the CLI, use the `plugins` section of the
config. This section is read and saved by the CLI without the risk to
remove the value in there. So it's a safe way to deal with this feature.

As it's a cross plugin configuration (now for scout but goal is wider
than that) then put it under a generic `-x-cli-hints` name so that other
plugins might use it if needed.

Value can be true/false, but is parsed against these exact two values
instead of using the ParseBool.

Both the environment variable and the config value are parsed the same
way.

Signed-off-by: Yves Brissaud <yves.brissaud@docker.com>
This commit is contained in:
Yves Brissaud 2023-06-12 17:10:45 +02:00
Родитель fac770ab1d
Коммит 8371dab4ae
Не найден ключ, соответствующий данной подписи
3 изменённых файлов: 75 добавлений и 15 удалений

Просмотреть файл

@ -100,6 +100,6 @@ func configFilePath(dir string) string {
// File contains the current context from the docker configuration file
type File struct {
CurrentContext string `json:"currentContext,omitempty"`
CliHints *bool `json:"cliHints,omitempty"`
CurrentContext string `json:"currentContext,omitempty"`
Plugins map[string]map[string]string `json:"plugins,omitempty"`
}

Просмотреть файл

@ -17,8 +17,8 @@
package mobycli
import (
"fmt"
"os"
"strconv"
"github.com/docker/compose-cli/api/config"
)
@ -26,11 +26,16 @@ import (
const (
cliHintsEnvVarName = "DOCKER_CLI_HINTS"
cliHintsDefaultBehaviour = true
cliHintsPluginName = "-x-cli-hints"
cliHintsEnabledName = "enabled"
cliHintsEnabled = "true"
cliHintsDisabled = "false"
)
func CliHintsEnabled() bool {
if envValue, ok := os.LookupEnv(cliHintsEnvVarName); ok {
if enabled, err := strconv.ParseBool(envValue); err == nil {
if enabled, err := parseCliHintFlag(envValue); err == nil {
return enabled
}
}
@ -40,9 +45,24 @@ func CliHintsEnabled() bool {
// can't read the config file, use the default behaviour
return cliHintsDefaultBehaviour
}
if conf.CliHints != nil {
return *conf.CliHints
if cliHintsPluginConfig, ok := conf.Plugins[cliHintsPluginName]; ok {
if cliHintsValue, ok := cliHintsPluginConfig[cliHintsEnabledName]; ok {
if cliHints, err := parseCliHintFlag(cliHintsValue); err == nil {
return cliHints
}
}
}
return cliHintsDefaultBehaviour
}
func parseCliHintFlag(value string) (bool, error) {
switch value {
case cliHintsEnabled:
return true, nil
case cliHintsDisabled:
return false, nil
default:
return cliHintsDefaultBehaviour, fmt.Errorf("could not parse CLI hints enabled flag")
}
}

Просмотреть файл

@ -38,23 +38,23 @@ func TestCliHintsEnabled(t *testing.T) {
true,
},
{
"handle true value",
"enabled from environment variable",
func() {
t.Setenv(cliHintsEnvVarName, "t")
t.Setenv(cliHintsEnvVarName, "true")
},
true,
},
{
"handle false value",
"disabled from environment variable",
func() {
t.Setenv(cliHintsEnvVarName, "FALSE")
t.Setenv(cliHintsEnvVarName, "false")
},
false,
},
{
"handle error",
"unsupported value",
func() {
t.Setenv(cliHintsEnvVarName, "123")
t.Setenv(cliHintsEnvVarName, "maybe")
},
true,
},
@ -66,6 +66,23 @@ func TestCliHintsEnabled(t *testing.T) {
},
true,
},
{
"plugin defined in config file but no enabled entry",
func() {
d := testConfigDir(t)
writeSampleConfig(t, d, configPartial)
},
true,
},
{
"unsupported value",
func() {
d := testConfigDir(t)
writeSampleConfig(t, d, configOnce)
},
true,
},
{
"disabled in config file",
func() {
@ -79,7 +96,7 @@ func TestCliHintsEnabled(t *testing.T) {
func() {
d := testConfigDir(t)
writeSampleConfig(t, d, configEnabled)
t.Setenv(cliHintsEnvVarName, "FALSE")
t.Setenv(cliHintsEnvVarName, "false")
},
false,
},
@ -120,9 +137,32 @@ func writeSampleConfig(t *testing.T, d string, conf []byte) {
}
var configEnabled = []byte(`{
"cliHints": true
"plugins": {
"-x-cli-hints": {
"enabled": "true"
}
}
}`)
var configDisabled = []byte(`{
"cliHints": false
"plugins": {
"-x-cli-hints": {
"enabled": "false"
}
}
}`)
var configPartial = []byte(`{
"plugins": {
"-x-cli-hints": {
}
}
}`)
var configOnce = []byte(`{
"plugins": {
"-x-cli-hints": {
"enabled": "maybe"
}
}
}`)