Skip to content

Commit

Permalink
Merge pull request #269 from compose-spec/public-dot-env
Browse files Browse the repository at this point in the history
Make dotEnv resolution plublic
  • Loading branch information
glours committed May 30, 2022
2 parents e80b082 + a741998 commit e497f1b
Show file tree
Hide file tree
Showing 3 changed files with 59 additions and 43 deletions.
77 changes: 36 additions & 41 deletions cli/options.go
Expand Up @@ -145,7 +145,7 @@ func WithDefaultConfigPath(o *ProjectOptions) error {
// WithEnv defines a key=value set of variables used for compose file interpolation
func WithEnv(env []string) ProjectOptionsFn {
return func(o *ProjectOptions) error {
for k, v := range getAsEqualsMap(env) {
for k, v := range utils.GetAsEqualsMap(env) {
o.Environment[k] = v
}
return nil
Expand All @@ -169,7 +169,7 @@ func WithLoadOptions(loadOptions ...func(*loader.Options)) ProjectOptionsFn {

// WithOsEnv imports environment variables from OS
func WithOsEnv(o *ProjectOptions) error {
for k, v := range getAsEqualsMap(os.Environ()) {
for k, v := range utils.GetAsEqualsMap(os.Environ()) {
if _, set := o.Environment[k]; set {
continue
}
Expand All @@ -188,62 +188,76 @@ func WithEnvFile(file string) ProjectOptionsFn {

// WithDotEnv imports environment variables from .env file
func WithDotEnv(o *ProjectOptions) error {
dotEnvFile := o.EnvFile
wd, err := o.GetWorkingDir()
if err != nil {
return err
}
envMap, err := GetEnvFromFile(o.Environment, wd, o.EnvFile)
if err != nil {
return err
}
for k, v := range envMap {
o.Environment[k] = v
}
return nil
}

func GetEnvFromFile(currentEnv map[string]string, workingDir string, filename string) (map[string]string, error) {
envMap := make(map[string]string)

dotEnvFile := filename
if dotEnvFile == "" {
wd, err := o.GetWorkingDir()
if err != nil {
return err
}
dotEnvFile = filepath.Join(wd, ".env")
dotEnvFile = filepath.Join(workingDir, ".env")
}
abs, err := filepath.Abs(dotEnvFile)
if err != nil {
return err
return envMap, err
}
dotEnvFile = abs

s, err := os.Stat(dotEnvFile)
if os.IsNotExist(err) {
if o.EnvFile != "" {
return errors.Errorf("Couldn't find env file: %s", o.EnvFile)
if filename != "" {
return nil, errors.Errorf("Couldn't find env file: %s", filename)
}
return nil
return envMap, nil
}
if err != nil {
return err
return envMap, err
}

if s.IsDir() {
if o.EnvFile == "" {
return nil
if filename == "" {
return envMap, nil
}
return errors.Errorf("%s is a directory", dotEnvFile)
return envMap, errors.Errorf("%s is a directory", dotEnvFile)
}

file, err := os.Open(dotEnvFile)
if err != nil {
return err
return envMap, err
}
defer file.Close()

env, err := dotenv.ParseWithLookup(file, func(k string) (string, bool) {
v, ok := o.Environment[k]
v, ok := currentEnv[k]
if !ok {

return "", false
}
return v, true
})
if err != nil {
return err
return envMap, err
}
for k, v := range env {
if _, set := o.Environment[k]; set {
if _, set := currentEnv[k]; set {
continue
}
o.Environment[k] = v
envMap[k] = v
}
return nil

return envMap, nil
}

// WithInterpolation set ProjectOptions to enable/skip interpolation
Expand Down Expand Up @@ -412,22 +426,3 @@ func absolutePaths(p []string) ([]string, error) {
}
return paths, nil
}

// getAsEqualsMap split key=value formatted strings into a key : value map
func getAsEqualsMap(em []string) map[string]string {
m := make(map[string]string)
for _, v := range em {
kv := strings.SplitN(v, "=", 2)
m[kv[0]] = kv[1]
}
return m
}

// getAsEqualsMap format a key : value map into key=value strings
func getAsStringList(em map[string]string) []string {
m := make([]string, 0, len(em))
for k, v := range em {
m = append(m, fmt.Sprintf("%s=%s", k, v))
}
return m
}
5 changes: 3 additions & 2 deletions cli/options_test.go
Expand Up @@ -23,6 +23,7 @@ import (
"testing"

"github.com/compose-spec/compose-go/consts"
"github.com/compose-spec/compose-go/utils"
"gotest.tools/v3/assert"
)

Expand Down Expand Up @@ -231,8 +232,8 @@ func TestProjectNameFromWorkingDir(t *testing.T) {
func TestEnvMap(t *testing.T) {
m := map[string]string{}
m["foo"] = "bar"
l := getAsStringList(m)
l := utils.GetAsStringList(m)
assert.Equal(t, l[0], "foo=bar")
m = getAsEqualsMap(l)
m = utils.GetAsEqualsMap(l)
assert.Equal(t, m["foo"], "bar")
}
20 changes: 20 additions & 0 deletions utils/stringutils.go
Expand Up @@ -17,6 +17,7 @@
package utils

import (
"fmt"
"strconv"
"strings"
)
Expand All @@ -36,3 +37,22 @@ func StringToBool(s string) bool {
b, _ := strconv.ParseBool(strings.ToLower(strings.TrimSpace(s)))
return b
}

// GetAsEqualsMap split key=value formatted strings into a key : value map
func GetAsEqualsMap(em []string) map[string]string {
m := make(map[string]string)
for _, v := range em {
kv := strings.SplitN(v, "=", 2)
m[kv[0]] = kv[1]
}
return m
}

// GetAsEqualsMap format a key : value map into key=value strings
func GetAsStringList(em map[string]string) []string {
m := make([]string, 0, len(em))
for k, v := range em {
m = append(m, fmt.Sprintf("%s=%s", k, v))
}
return m
}

0 comments on commit e497f1b

Please sign in to comment.