From 96c026eb301f4f9d2cb224d0ee1a2312b7f5b60c Mon Sep 17 00:00:00 2001 From: Tom Klingenberg Date: Sun, 1 Jul 2018 23:55:38 +0200 Subject: [PATCH] import environment variables that are present previously docker did import environment variables if they were present but created them if they were not when it was asked via a --env-file cli option to import but not create them. fix is to only import the variable into the environment if it is present. additionally do not import variable names of zero-length (which are lines w/ a potential variable definition w/o a variable name). refs: - https://github.com/docker/for-linux/issues/284 Signed-off-by: Tom Klingenberg --- opts/envfile.go | 2 +- opts/file.go | 14 ++++++++++---- opts/parse.go | 4 ++-- 3 files changed, 13 insertions(+), 7 deletions(-) diff --git a/opts/envfile.go b/opts/envfile.go index 10054c896c..69d3ca6f60 100644 --- a/opts/envfile.go +++ b/opts/envfile.go @@ -18,5 +18,5 @@ import ( // environment variables, that's why we just strip leading whitespace and // nothing more. func ParseEnvFile(filename string) ([]string, error) { - return parseKeyValueFile(filename, os.Getenv) + return parseKeyValueFile(filename, os.LookupEnv) } diff --git a/opts/file.go b/opts/file.go index 281905949b..1721a46ef9 100644 --- a/opts/file.go +++ b/opts/file.go @@ -21,7 +21,7 @@ func (e ErrBadKey) Error() string { return fmt.Sprintf("poorly formatted environment: %s", e.msg) } -func parseKeyValueFile(filename string, emptyFn func(string) string) ([]string, error) { +func parseKeyValueFile(filename string, emptyFn func(string) (string, bool)) ([]string, error) { fh, err := os.Open(filename) if err != nil { return []string{}, err @@ -53,17 +53,23 @@ func parseKeyValueFile(filename string, emptyFn func(string) string) ([]string, if strings.ContainsAny(variable, whiteSpaces) { return []string{}, ErrBadKey{fmt.Sprintf("variable '%s' has white spaces", variable)} } + if len(variable) == 0 { + return []string{}, ErrBadKey{fmt.Sprintf("no variable name on line '%s'", line)} + } if len(data) > 1 { // pass the value through, no trimming lines = append(lines, fmt.Sprintf("%s=%s", variable, data[1])) } else { var value string + var present bool if emptyFn != nil { - value = emptyFn(line) + value, present = emptyFn(line) + } + if present { + // if only a pass-through variable is given, clean it up. + lines = append(lines, fmt.Sprintf("%s=%s", strings.TrimSpace(line), value)) } - // if only a pass-through variable is given, clean it up. - lines = append(lines, fmt.Sprintf("%s=%s", strings.TrimSpace(line), value)) } } } diff --git a/opts/parse.go b/opts/parse.go index 679759deda..70b60e142f 100644 --- a/opts/parse.go +++ b/opts/parse.go @@ -19,10 +19,10 @@ func ReadKVStrings(files []string, override []string) ([]string, error) { // present in the file with additional pairs specified in the override parameter. // If a key has no value, it will get the value from the environment. func ReadKVEnvStrings(files []string, override []string) ([]string, error) { - return readKVStrings(files, override, os.Getenv) + return readKVStrings(files, override, os.LookupEnv) } -func readKVStrings(files []string, override []string, emptyFn func(string) string) ([]string, error) { +func readKVStrings(files []string, override []string, emptyFn func(string) (string, bool)) ([]string, error) { variables := []string{} for _, ef := range files { parsedVars, err := parseKeyValueFile(ef, emptyFn)