Skip to content

Commit

Permalink
pass context as first parameter
Browse files Browse the repository at this point in the history
Signed-off-by: Nicolas De Loof <nicolas.deloof@gmail.com>
  • Loading branch information
ndeloof committed Feb 14, 2024
1 parent 2b6b594 commit 0c779a8
Show file tree
Hide file tree
Showing 5 changed files with 48 additions and 53 deletions.
46 changes: 19 additions & 27 deletions cli/options.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,8 +37,6 @@ import (

// ProjectOptions provides common configuration for loading a project.
type ProjectOptions struct {
ctx context.Context

// Name is a valid Compose project name to be used or empty.
//
// If empty, the project loader will automatically infer a reasonable
Expand Down Expand Up @@ -334,14 +332,6 @@ func WithResolvedPaths(resolve bool) ProjectOptionsFn {
}
}

// WithContext sets the context used to load model and resources
func WithContext(ctx context.Context) ProjectOptionsFn {
return func(o *ProjectOptions) error {
o.ctx = ctx
return nil
}
}

// WithResourceLoader register support for ResourceLoader to manage remote resources
func WithResourceLoader(r loader.ResourceLoader) ProjectOptionsFn {
return func(o *ProjectOptions) error {
Expand Down Expand Up @@ -381,7 +371,7 @@ var DefaultOverrideFileNames = []string{"compose.override.yml", "compose.overrid

func (o ProjectOptions) GetWorkingDir() (string, error) {
if o.WorkingDir != "" {
return o.WorkingDir, nil
return filepath.Abs(o.WorkingDir)
}
for _, path := range o.ConfigPaths {
if path != "-" {
Expand All @@ -395,9 +385,8 @@ func (o ProjectOptions) GetWorkingDir() (string, error) {
return os.Getwd()
}

// ProjectFromOptions load a compose project based on command line options
func ProjectFromOptions(options *ProjectOptions) (*types.Project, error) {
configPaths, err := getConfigPathsFromOptions(options)
func (o ProjectOptions) GeConfigFiles() ([]types.ConfigFile, error) {
configPaths, err := o.getConfigPaths()
if err != nil {
return nil, err
}
Expand Down Expand Up @@ -425,25 +414,25 @@ func ProjectFromOptions(options *ProjectOptions) (*types.Project, error) {
Content: b,
})
}
return configs, err
}

workingDir, err := options.GetWorkingDir()
// ProjectFromOptions load a compose project based on command line options
func ProjectFromOptions(ctx context.Context, options *ProjectOptions) (*types.Project, error) {
configs, err := options.GeConfigFiles()
if err != nil {
return nil, err
}
absWorkingDir, err := filepath.Abs(workingDir)

workingDir, err := options.GetWorkingDir()
if err != nil {
return nil, err
}

options.loadOptions = append(options.loadOptions,
withNamePrecedenceLoad(absWorkingDir, options),
withNamePrecedenceLoad(workingDir, options),
withConvertWindowsPaths(options))

ctx := options.ctx
if ctx == nil {
ctx = context.Background()
}

project, err := loader.LoadWithContext(ctx, types.ConfigDetails{
ConfigFiles: configs,
WorkingDir: workingDir,
Expand All @@ -453,7 +442,10 @@ func ProjectFromOptions(options *ProjectOptions) (*types.Project, error) {
return nil, err
}

project.ComposeFiles = configPaths
for _, config := range configs {
project.ComposeFiles = append(project.ComposeFiles, config.Filename)
}

return project, nil
}

Expand All @@ -480,10 +472,10 @@ func withConvertWindowsPaths(options *ProjectOptions) func(*loader.Options) {
}
}

// getConfigPathsFromOptions retrieves the config files for project based on project options
func getConfigPathsFromOptions(options *ProjectOptions) ([]string, error) {
if len(options.ConfigPaths) != 0 {
return absolutePaths(options.ConfigPaths)
// getConfigPaths retrieves the config files for project based on project options
func (o *ProjectOptions) getConfigPaths() ([]string, error) {
if len(o.ConfigPaths) != 0 {
return absolutePaths(o.ConfigPaths)
}
return nil, fmt.Errorf("no configuration file provided: %w", errdefs.ErrNotFound)
}
Expand Down
47 changes: 24 additions & 23 deletions cli/options_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
package cli

import (
"context"
"fmt"
"os"
"path/filepath"
Expand All @@ -33,23 +34,23 @@ func TestProjectName(t *testing.T) {
t.Run("by name", func(t *testing.T) {
opts, err := NewProjectOptions([]string{"testdata/simple/compose.yaml"}, WithName("my_project"))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "my_project")
})

t.Run("by name start with number", func(t *testing.T) {
opts, err := NewProjectOptions([]string{"testdata/simple/compose.yaml"}, WithName("42my_project_num"))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "42my_project_num")

opts, err = NewProjectOptions([]string{"testdata/simple/compose.yaml"}, WithEnv([]string{
fmt.Sprintf("%s=%s", consts.ComposeProjectName, "42my_project_env"),
}))
assert.NilError(t, err)
p, err = ProjectFromOptions(opts)
p, err = ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "42my_project_env")
})
Expand All @@ -60,7 +61,7 @@ func TestProjectName(t *testing.T) {
WithName(""),
)
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "simple")
})
Expand All @@ -72,7 +73,7 @@ func TestProjectName(t *testing.T) {
WithWorkingDirectory("/path/to/proj"),
)
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "proj")
})
Expand All @@ -81,7 +82,7 @@ func TestProjectName(t *testing.T) {
opts, err := NewProjectOptions([]string{"testdata/simple/compose.yaml"},
WithWorkingDirectory("/"))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)

// root directory will resolve to an empty project name since there
// IS no directory name!
Expand All @@ -97,7 +98,7 @@ func TestProjectName(t *testing.T) {
fmt.Sprintf("%s=%s", consts.ComposeProjectName, "-my_project"),
}))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.ErrorContains(t, err, `invalid project name "-my_project"`)
assert.Assert(t, p == nil)
})
Expand All @@ -110,7 +111,7 @@ func TestProjectName(t *testing.T) {
fmt.Sprintf("%s=%s", consts.ComposeProjectName, "_my_project"),
}))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.ErrorContains(t, err, `invalid project name "_my_project"`)
assert.Assert(t, p == nil)
})
Expand All @@ -123,7 +124,7 @@ func TestProjectName(t *testing.T) {
fmt.Sprintf("%s=%s", consts.ComposeProjectName, "www.my.project"),
}))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.ErrorContains(t, err, `invalid project name "www.my.project"`)
assert.Assert(t, p == nil)
})
Expand All @@ -136,31 +137,31 @@ func TestProjectName(t *testing.T) {
fmt.Sprintf("%s=%s", consts.ComposeProjectName, "MY_PROJECT"),
}))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.ErrorContains(t, err, `invalid project name "MY_PROJECT"`)
assert.Assert(t, p == nil)
})

t.Run("by working dir", func(t *testing.T) {
opts, err := NewProjectOptions([]string{"testdata/simple/compose.yaml"}, WithWorkingDirectory("."))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "cli")
})

t.Run("by compose file parent dir", func(t *testing.T) {
opts, err := NewProjectOptions([]string{"testdata/simple/compose.yaml"})
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "simple")
})

t.Run("by compose file parent dir special", func(t *testing.T) {
opts, err := NewProjectOptions([]string{"testdata/UNNORMALIZED PATH/compose.yaml"})
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "unnormalizedpath")
})
Expand All @@ -170,7 +171,7 @@ func TestProjectName(t *testing.T) {
defer os.Unsetenv("COMPOSE_PROJECT_NAME") //nolint:errcheck
opts, err := NewProjectOptions([]string{"testdata/simple/compose.yaml"}, WithOsEnv)
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "my_project_from_env")
})
Expand All @@ -184,7 +185,7 @@ func TestProjectName(t *testing.T) {

opts, err := NewProjectOptions(nil, WithEnvFiles(), WithDotEnv, WithConfigFileEnv)
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "my_project_from_dot_env")
})
Expand All @@ -194,7 +195,7 @@ func TestProjectName(t *testing.T) {
"TEST=expected",
}))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "test-expected-test")
})
Expand All @@ -206,7 +207,7 @@ func TestProjectFromSetOfFiles(t *testing.T) {
"testdata/simple/compose-with-overrides.yaml",
}, WithName("my_project"))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
service, err := p.GetService("simple")
assert.NilError(t, err)
Expand All @@ -220,7 +221,7 @@ func TestProjectComposefilesFromSetOfFiles(t *testing.T) {
WithDefaultConfigPath,
)
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
absPath, _ := filepath.Abs(filepath.Join("testdata", "simple", "compose.yaml"))
assert.DeepEqual(t, p.ComposeFiles, []string{absPath})
Expand All @@ -232,7 +233,7 @@ func TestProjectComposefilesFromWorkingDir(t *testing.T) {
"testdata/simple/compose-with-overrides.yaml",
}, WithName("my_project"))
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
currentDir, _ := os.Getwd()
assert.DeepEqual(t, p.ComposeFiles, []string{
Expand All @@ -252,7 +253,7 @@ func TestProjectWithDotEnv(t *testing.T) {
"compose-with-variables.yaml",
}, WithName("my_project"), WithEnvFiles(), WithDotEnv)
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
service, err := p.GetService("simple")
assert.NilError(t, err)
Expand All @@ -265,7 +266,7 @@ func TestProjectWithDiscardEnvFile(t *testing.T) {
}, WithDiscardEnvFile)

assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
service, err := p.GetService("simple")
assert.NilError(t, err)
Expand All @@ -282,7 +283,7 @@ func TestProjectWithMultipleEnvFile(t *testing.T) {
WithDotEnv)

assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
service, err := p.GetService("simple")
assert.NilError(t, err)
Expand All @@ -296,7 +297,7 @@ func TestProjectNameFromWorkingDir(t *testing.T) {
"testdata/env-file/compose-with-env-file.yaml",
})
assert.NilError(t, err)
p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)
assert.NilError(t, err)
assert.Equal(t, p.Name, "env-file")
}
Expand Down
3 changes: 2 additions & 1 deletion cli/options_windows_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
package cli

import (
"context"
"os"
"testing"

Expand All @@ -31,7 +32,7 @@ func TestConvertWithEnvVar(t *testing.T) {
WithWorkingDirectory("C:\\project-dir\\"),
WithResolvedPaths(true))

p, err := ProjectFromOptions(opts)
p, err := ProjectFromOptions(context.TODO(), opts)

assert.NilError(t, err)
volumes := p.Services["test"].Volumes
Expand Down
3 changes: 2 additions & 1 deletion cmd/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
package main

import (
"context"
"fmt"
"os"

Expand Down Expand Up @@ -47,7 +48,7 @@ Usage: compose-spec [OPTIONS] COMPOSE_FILE [COMPOSE_OVERRIDE_FILE]`)
exitError("failed to configure project options", err)
}

project, err := cli.ProjectFromOptions(options)
project, err := cli.ProjectFromOptions(context.Background(), options)
if err != nil {
exitError("failed to load project", err)
}
Expand Down
2 changes: 1 addition & 1 deletion loader/loader_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ func loadYAML(yaml string) (*types.Project, error) {
}

func loadYAMLWithEnv(yaml string, env map[string]string) (*types.Project, error) {
return Load(buildConfigDetails(yaml, env), func(options *Options) {
return LoadWithContext(context.TODO(), buildConfigDetails(yaml, env), func(options *Options) {
options.SkipConsistencyCheck = true
options.SkipNormalization = true
options.ResolvePaths = true
Expand Down

0 comments on commit 0c779a8

Please sign in to comment.