Skip to content

Commit

Permalink
fix: pipeline stringArray flag usage
Browse files Browse the repository at this point in the history
ENG-2735

Signed-off-by: Russell Centanni <[email protected]>
  • Loading branch information
lizardruss committed Feb 8, 2024
1 parent 863b7b6 commit 7116535
Show file tree
Hide file tree
Showing 6 changed files with 126 additions and 13 deletions.
4 changes: 2 additions & 2 deletions docs/pages/configuration/pipelines/README.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -326,8 +326,8 @@ pipelines:
short: e
type: stringArray
run: |-
extraEnv=$(get_flag "env") # Retrieve the value of the `env` flag and store it in a variable
echo ${extraEnv[1]}
extraEnv=($(get_flag "env")) # Retrieve the value of the `env` flag and store it in an array variable
echo ${extraEnv[0]} # Arrays are zero indexed

TERMINAL_ENABLED=true
if [ $(get_flag "logs") == "true" ]; then # Test if --logs/-l flag is used or not
Expand Down
2 changes: 1 addition & 1 deletion e2e/tests/pipelines/framework.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,5 +4,5 @@ import "github.com/onsi/ginkgo/v2"

// DevSpaceDescribe annotates the test with the label.
func DevSpaceDescribe(text string, body func()) bool {
return ginkgo.Describe("[pipelines] "+text, body)
return ginkgo.FDescribe("[pipelines] "+text, body)
}
53 changes: 52 additions & 1 deletion e2e/tests/pipelines/pipelines.go
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ var _ = DevSpaceDescribe("pipelines", func() {
framework.ExpectNoError(err)
})

ginkgo.It("should resolve pipeline flags", func() {
ginkgo.FIt("should resolve pipeline flags", func() {
tempDir, err := framework.CopyToTempDir("tests/pipelines/testdata/flags")
framework.ExpectNoError(err)
defer framework.CleanupTempDir(initialDir, tempDir)
Expand Down Expand Up @@ -75,6 +75,57 @@ var _ = DevSpaceDescribe("pipelines", func() {
framework.ExpectLocalFileContentsImmediately("other.txt", "test\n")
framework.ExpectLocalFileContentsImmediately("other2.txt", "false\n")
framework.ExpectLocalFileContentsImmediately("other3.txt", "true\n")
framework.ExpectLocalFileContentsImmediately("other4-0.txt", "one\n")
framework.ExpectLocalFileContentsImmediately("other4-1.txt", "two\n")
framework.ExpectLocalFileContentsImmediately("other-profile.txt", "profile1\n")
framework.ExpectLocalFileContentsImmediately("dep1-test.txt", "test\n")
framework.ExpectLocalFileContentsImmediately("dep1-test2.txt", "true\n")
framework.ExpectLocalFileContentsImmediately("dep1-dev-profile.txt", "profile1\n")
framework.ExpectLocalFileContentsImmediately("dep1-other.txt", "test\n")
framework.ExpectLocalFileContentsImmediately("dep1-other2.txt", "false\n")
framework.ExpectLocalFileContentsImmediately("dep1-other3.txt", "false\n")
framework.ExpectLocalFileContentsImmediately("dep1-other-profile.txt", "profile1\n")
})

ginkgo.FIt("should resolve pipeline override array flags", func() {
tempDir, err := framework.CopyToTempDir("tests/pipelines/testdata/flags")
framework.ExpectNoError(err)
defer framework.CleanupTempDir(initialDir, tempDir)

ns, err := kubeClient.CreateNamespace("pipelines")
framework.ExpectNoError(err)
defer framework.ExpectDeleteNamespace(kubeClient, ns)

rootCmd := cmd.NewRootCmd(f)
persistentFlags := rootCmd.PersistentFlags()
globalFlags := flags.SetGlobalFlags(persistentFlags)
globalFlags.NoWarn = true
globalFlags.Namespace = ns
globalFlags.Profiles = []string{"profile1"}

cmdCtx := values.WithCommandFlags(context.Background(), globalFlags.Flags)
cmdCtx = values.WithFlagsMap(cmdCtx, map[string]string{
"test": "test",
"test2": "",
"other4": "three,four",
})

devCmd := &cmd.RunPipelineCmd{
GlobalFlags: globalFlags,
Pipeline: "other",
Ctx: cmdCtx,
}
err = devCmd.RunDefault(f)
framework.ExpectNoError(err)

framework.ExpectLocalFileContentsImmediately("test.txt", "test\n")
framework.ExpectLocalFileContentsImmediately("test2.txt", "\n")
framework.ExpectLocalFileContentsImmediately("dev-profile.txt", "profile1\n")
framework.ExpectLocalFileContentsImmediately("other.txt", "test\n")
framework.ExpectLocalFileContentsImmediately("other2.txt", "false\n")
framework.ExpectLocalFileContentsImmediately("other3.txt", "true\n")
framework.ExpectLocalFileContentsImmediately("other4-0.txt", "three\n")
framework.ExpectLocalFileContentsImmediately("other4-1.txt", "four\n")
framework.ExpectLocalFileContentsImmediately("other-profile.txt", "profile1\n")
framework.ExpectLocalFileContentsImmediately("dep1-test.txt", "test\n")
framework.ExpectLocalFileContentsImmediately("dep1-test2.txt", "true\n")
Expand Down
9 changes: 9 additions & 0 deletions e2e/tests/pipelines/testdata/flags/devspace.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,11 @@ pipelines:
default: true
- name: other3
default: true
- name: other4
type: stringArray
default:
- one
- two
run: |-
if get_flag test; then
exit 1
Expand All @@ -24,6 +29,10 @@ pipelines:
echo $(get_flag other2) > other2.txt
echo $(get_flag other3) > other3.txt
echo $(get_flag profile) > other-profile.txt
other4=($(get_flag other4))
echo ${other4[0]} > other4-0.txt
echo ${other4[1]} > other4-1.txt
dev:
flags:
Expand Down
37 changes: 31 additions & 6 deletions pkg/devspace/pipeline/flags.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package pipeline

import (
"fmt"
"strconv"

"github.com/loft-sh/devspace/pkg/devspace/config/versions/latest"
)
Expand Down Expand Up @@ -31,18 +32,42 @@ func GetDefaultValue(pipelineFlag latest.PipelineFlag) (interface{}, error) {
case latest.PipelineFlagTypeInteger:
val := 0
if pipelineFlag.Default != nil {
val, ok = pipelineFlag.Default.(int)
if !ok {
return nil, fmt.Errorf("default is not an integer")
switch pipelineFlag.Default.(type) {
case float64:
floatVal, ok := pipelineFlag.Default.(float64)
if !ok {
return nil, fmt.Errorf("default is not an integer")
}
return int(floatVal), nil
case int:
intVal, ok := pipelineFlag.Default.(int)
if !ok {
return nil, fmt.Errorf("default is not an integer")
}
return intVal, nil
case string:
strVal, ok := pipelineFlag.Default.(string)
if !ok {
return nil, fmt.Errorf("default is not an integer")
}
intVal, err := strconv.ParseInt(strVal, 10, 0)
if err != nil {
return nil, err
}
return int(intVal), nil
}
return nil, fmt.Errorf("default is not an integer")
}
return val, nil
case latest.PipelineFlagTypeStringArray:
val := []string{}
if pipelineFlag.Default != nil {
val, ok = pipelineFlag.Default.([]string)
if !ok {
return nil, fmt.Errorf("default is not a string array")
for _, anyVal := range pipelineFlag.Default.([]interface{}) {
strVal, ok := anyVal.(string)
if !ok {
return nil, fmt.Errorf("default is not a string array")
}
val = append(val, strVal)
}
}
return val, nil
Expand Down
34 changes: 31 additions & 3 deletions pkg/devspace/pipeline/pipeline.go
Original file line number Diff line number Diff line change
Expand Up @@ -423,24 +423,52 @@ func (p *pipeline) startNewDependency(ctx devspacecontext.Context, dependency ty
}

func applyFlags(ctx devspacecontext.Context, pipeline *latest.Pipeline, setFlags []string) (devspacecontext.Context, error) {
newFlags := map[string]string{}
defaultFlags := map[string]string{}
for _, flag := range pipeline.Flags {
val, err := GetDefaultValue(flag)
if err != nil {
return nil, err
}

newFlags[flag.Name] = fmt.Sprintf("%v", val)
switch flag.Type {
case latest.PipelineFlagTypeStringArray:
defaultFlags[flag.Name] = fmt.Sprintf("%v", strings.Join(val.([]string), " "))
default:
defaultFlags[flag.Name] = fmt.Sprintf("%v", val)
}
}

fmt.Println("DEFAULT FLAGS")
fmt.Println(defaultFlags)

newFlags := map[string]string{}
for _, v := range setFlags {
splitted := strings.Split(v, "=")
if len(splitted) <= 1 {
return nil, fmt.Errorf("error parsing flag %s: expected format flag=value", v)
}

newFlags[splitted[0]] = strings.Join(splitted[1:], "=")
flagName := splitted[0]
flagVal := strings.Join(splitted[1:], "=")
flagVals := strings.Join(strings.Split(flagVal, ","), " ")

if newFlags[flagName] != "" {
newFlags[flagName] = strings.Join([]string{newFlags[flagName], flagVals}, " ")
} else {
newFlags[flagName] = flagVals
}

}

for name, value := range defaultFlags {
if _, ok := newFlags[name]; !ok {
newFlags[name] = value
}
}

fmt.Println("NEW FLAGS")
fmt.Println(newFlags)

return ctx.WithContext(values.WithFlagsMap(ctx.Context(), newFlags)), nil
}

Expand Down

0 comments on commit 7116535

Please sign in to comment.