2017-06-05 18:23:21 -04:00
|
|
|
package opts
|
|
|
|
|
|
|
|
import (
|
|
|
|
"bufio"
|
|
|
|
"os"
|
2024-10-03 08:08:22 -04:00
|
|
|
"path/filepath"
|
2017-06-05 18:23:21 -04:00
|
|
|
"strings"
|
|
|
|
"testing"
|
2024-10-03 08:08:22 -04:00
|
|
|
|
|
|
|
"gotest.tools/v3/assert"
|
|
|
|
is "gotest.tools/v3/assert/cmp"
|
2017-06-05 18:23:21 -04:00
|
|
|
)
|
|
|
|
|
2022-02-25 09:35:13 -05:00
|
|
|
func tmpFileWithContent(t *testing.T, content string) string {
|
|
|
|
t.Helper()
|
2024-10-03 08:08:22 -04:00
|
|
|
fileName := filepath.Join(t.TempDir(), "envfile")
|
|
|
|
err := os.WriteFile(fileName, []byte(content), 0o644)
|
|
|
|
assert.NilError(t, err)
|
|
|
|
return fileName
|
2017-06-05 18:23:21 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
// Test ParseEnvFile for a file with a few well formatted lines
|
|
|
|
func TestParseEnvFileGoodFile(t *testing.T) {
|
|
|
|
content := `foo=bar
|
|
|
|
baz=quux
|
|
|
|
# comment
|
|
|
|
|
|
|
|
_foobar=foobaz
|
|
|
|
with.dots=working
|
|
|
|
and_underscore=working too
|
|
|
|
`
|
|
|
|
// Adding a newline + a line with pure whitespace.
|
|
|
|
// This is being done like this instead of the block above
|
|
|
|
// because it's common for editors to trim trailing whitespace
|
|
|
|
// from lines, which becomes annoying since that's the
|
|
|
|
// exact thing we need to test.
|
|
|
|
content += "\n \t "
|
2022-02-25 09:35:13 -05:00
|
|
|
tmpFile := tmpFileWithContent(t, content)
|
2017-06-05 18:23:21 -04:00
|
|
|
|
|
|
|
lines, err := ParseEnvFile(tmpFile)
|
2024-10-03 08:08:22 -04:00
|
|
|
assert.NilError(t, err)
|
2017-06-05 18:23:21 -04:00
|
|
|
|
|
|
|
expectedLines := []string{
|
|
|
|
"foo=bar",
|
|
|
|
"baz=quux",
|
|
|
|
"_foobar=foobaz",
|
|
|
|
"with.dots=working",
|
|
|
|
"and_underscore=working too",
|
|
|
|
}
|
|
|
|
|
2024-10-03 08:08:22 -04:00
|
|
|
assert.Check(t, is.DeepEqual(lines, expectedLines))
|
2017-06-05 18:23:21 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
// Test ParseEnvFile for an empty file
|
|
|
|
func TestParseEnvFileEmptyFile(t *testing.T) {
|
2022-02-25 09:35:13 -05:00
|
|
|
tmpFile := tmpFileWithContent(t, "")
|
2017-06-05 18:23:21 -04:00
|
|
|
|
|
|
|
lines, err := ParseEnvFile(tmpFile)
|
2024-10-03 08:08:22 -04:00
|
|
|
assert.NilError(t, err)
|
|
|
|
assert.Check(t, is.Len(lines, 0))
|
2017-06-05 18:23:21 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
// Test ParseEnvFile for a non existent file
|
|
|
|
func TestParseEnvFileNonExistentFile(t *testing.T) {
|
2024-10-03 08:08:22 -04:00
|
|
|
_, err := ParseEnvFile("no_such_file")
|
|
|
|
assert.Check(t, is.ErrorType(err, os.IsNotExist))
|
2017-06-05 18:23:21 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
// Test ParseEnvFile for a badly formatted file
|
|
|
|
func TestParseEnvFileBadlyFormattedFile(t *testing.T) {
|
|
|
|
content := `foo=bar
|
|
|
|
f =quux
|
|
|
|
`
|
2022-02-25 09:35:13 -05:00
|
|
|
tmpFile := tmpFileWithContent(t, content)
|
2017-06-05 18:23:21 -04:00
|
|
|
|
|
|
|
_, err := ParseEnvFile(tmpFile)
|
2024-10-03 08:08:22 -04:00
|
|
|
const expectedMessage = "variable 'f ' contains whitespaces"
|
|
|
|
assert.Check(t, is.ErrorContains(err, expectedMessage))
|
2017-06-05 18:23:21 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
// Test ParseEnvFile for a file with a line exceeding bufio.MaxScanTokenSize
|
|
|
|
func TestParseEnvFileLineTooLongFile(t *testing.T) {
|
2022-02-25 09:35:13 -05:00
|
|
|
content := "foo=" + strings.Repeat("a", bufio.MaxScanTokenSize+42)
|
|
|
|
tmpFile := tmpFileWithContent(t, content)
|
2017-06-05 18:23:21 -04:00
|
|
|
|
|
|
|
_, err := ParseEnvFile(tmpFile)
|
2024-10-03 08:08:22 -04:00
|
|
|
const expectedMessage = "bufio.Scanner: token too long"
|
|
|
|
assert.Check(t, is.ErrorContains(err, expectedMessage))
|
2017-06-05 18:23:21 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
// ParseEnvFile with a random file, pass through
|
|
|
|
func TestParseEnvFileRandomFile(t *testing.T) {
|
|
|
|
content := `first line
|
|
|
|
another invalid line`
|
2022-02-25 09:35:13 -05:00
|
|
|
tmpFile := tmpFileWithContent(t, content)
|
2017-06-05 18:23:21 -04:00
|
|
|
|
|
|
|
_, err := ParseEnvFile(tmpFile)
|
2024-10-03 08:08:22 -04:00
|
|
|
const expectedMessage = "variable 'first line' contains whitespaces"
|
|
|
|
assert.Check(t, is.ErrorContains(err, expectedMessage))
|
2017-06-05 18:23:21 -04:00
|
|
|
}
|
2018-07-02 01:33:44 -04:00
|
|
|
|
|
|
|
// ParseEnvFile with environment variable import definitions
|
|
|
|
func TestParseEnvVariableDefinitionsFile(t *testing.T) {
|
|
|
|
content := `# comment=
|
|
|
|
UNDEFINED_VAR
|
2024-10-03 08:08:22 -04:00
|
|
|
DEFINED_VAR
|
2018-07-02 01:33:44 -04:00
|
|
|
`
|
2022-02-25 09:35:13 -05:00
|
|
|
tmpFile := tmpFileWithContent(t, content)
|
2018-07-02 01:33:44 -04:00
|
|
|
|
2024-10-03 08:08:22 -04:00
|
|
|
t.Setenv("DEFINED_VAR", "defined-value")
|
2018-07-02 01:33:44 -04:00
|
|
|
variables, err := ParseEnvFile(tmpFile)
|
2024-10-03 08:08:22 -04:00
|
|
|
assert.NilError(t, err)
|
2018-07-02 01:33:44 -04:00
|
|
|
|
2024-10-03 08:08:22 -04:00
|
|
|
expectedLines := []string{"DEFINED_VAR=defined-value"}
|
|
|
|
assert.Check(t, is.DeepEqual(variables, expectedLines))
|
2018-07-02 01:33:44 -04:00
|
|
|
}
|
2018-07-02 01:52:02 -04:00
|
|
|
|
|
|
|
// ParseEnvFile with empty variable name
|
|
|
|
func TestParseEnvVariableWithNoNameFile(t *testing.T) {
|
|
|
|
content := `# comment=
|
|
|
|
=blank variable names are an error case
|
|
|
|
`
|
2022-02-25 09:35:13 -05:00
|
|
|
tmpFile := tmpFileWithContent(t, content)
|
2018-07-02 01:52:02 -04:00
|
|
|
|
|
|
|
_, err := ParseEnvFile(tmpFile)
|
2024-10-03 08:08:22 -04:00
|
|
|
const expectedMessage = "no variable name on line '=blank variable names are an error case'"
|
|
|
|
assert.Check(t, is.ErrorContains(err, expectedMessage))
|
2018-07-02 01:52:02 -04:00
|
|
|
}
|