diff --git a/command/build_test.go b/command/build_test.go new file mode 100644 index 000000000..73837e1a2 --- /dev/null +++ b/command/build_test.go @@ -0,0 +1,132 @@ +package command + +import ( + "bytes" + "os" + "path/filepath" + "testing" + + "github.com/mitchellh/packer/builder/file" + "github.com/mitchellh/packer/packer" +) + +func TestBuildOnlyFileCommaFlags(t *testing.T) { + c := &BuildCommand{ + Meta: testMetaFile(t), + } + + args := []string{ + "-only=chocolate,vanilla", + filepath.Join(testFixture("build-only"), "template.json"), + } + + defer cleanup() + + if code := c.Run(args); code != 0 { + fatalCommand(t, c.Meta) + } + + if !fileExists("chocolate.txt") { + t.Error("Expected to find chocolate.txt") + } + if !fileExists("vanilla.txt") { + t.Error("Expected to find vanilla.txt") + } + if fileExists("cherry.txt") { + t.Error("Expected NOT to find cherry.txt") + } +} + +func TestBuildOnlyFileMultipleFlags(t *testing.T) { + c := &BuildCommand{ + Meta: testMetaFile(t), + } + + args := []string{ + "-only=chocolate", + "-only=cherry", + filepath.Join(testFixture("build-only"), "template.json"), + } + + defer cleanup() + + if code := c.Run(args); code != 0 { + fatalCommand(t, c.Meta) + } + + if !fileExists("chocolate.txt") { + t.Error("Expected to find chocolate.txt") + } + if fileExists("vanilla.txt") { + t.Error("Expected NOT to find vanilla.txt") + } + if !fileExists("cherry.txt") { + t.Error("Expected to find cherry.txt") + } +} + +func TestBuildExceptFileCommaFlags(t *testing.T) { + c := &BuildCommand{ + Meta: testMetaFile(t), + } + + args := []string{ + "-except=chocolate", + filepath.Join(testFixture("build-only"), "template.json"), + } + + defer cleanup() + + if code := c.Run(args); code != 0 { + fatalCommand(t, c.Meta) + } + + if fileExists("chocolate.txt") { + t.Error("Expected NOT to find chocolate.txt") + } + if !fileExists("vanilla.txt") { + t.Error("Expected to find vanilla.txt") + } + if !fileExists("cherry.txt") { + t.Error("Expected to find cherry.txt") + } +} + +// fileExists returns true if the filename is found +func fileExists(filename string) bool { + if _, err := os.Stat(filename); err == nil { + return true + } + return false +} + +// testCoreConfigBuilder creates a packer CoreConfig that has a file builder +// available. This allows us to test a builder that writes files to disk. +func testCoreConfigBuilder(t *testing.T) *packer.CoreConfig { + components := packer.ComponentFinder{ + Builder: func(n string) (packer.Builder, error) { + return &file.Builder{}, nil + }, + } + return &packer.CoreConfig{ + Components: components, + } +} + +// testMetaFile creates a Meta object that includes a file builder +func testMetaFile(t *testing.T) Meta { + var out, err bytes.Buffer + return Meta{ + CoreConfig: testCoreConfigBuilder(t), + Ui: &packer.BasicUi{ + Writer: &out, + ErrorWriter: &err, + }, + } +} + +func cleanup() { + os.RemoveAll("chocolate.txt") + os.RemoveAll("vanilla.txt") + os.RemoveAll("cherry.txt") +} diff --git a/command/test-fixtures/build-only/template.json b/command/test-fixtures/build-only/template.json new file mode 100644 index 000000000..ee89d635e --- /dev/null +++ b/command/test-fixtures/build-only/template.json @@ -0,0 +1,22 @@ +{ + "builders": [ + { + "name":"chocolate", + "type":"file", + "content":"chocolate", + "target":"chocolate.txt" + }, + { + "name":"vanilla", + "type":"file", + "content":"vanilla", + "target":"vanilla.txt" + }, + { + "name":"cherry", + "type":"file", + "content":"cherry", + "target":"cherry.txt" + } + ] +} diff --git a/helper/flag-slice/flag.go b/helper/flag-slice/flag.go index da75149dc..587b674fa 100644 --- a/helper/flag-slice/flag.go +++ b/helper/flag-slice/flag.go @@ -11,6 +11,6 @@ func (s *StringFlag) String() string { } func (s *StringFlag) Set(value string) error { - *s = append(*s, value) + *s = append(*s, strings.Split(value, ",")...) return nil } diff --git a/helper/flag-slice/flag_test.go b/helper/flag-slice/flag_test.go index f72e1d960..61d8682b2 100644 --- a/helper/flag-slice/flag_test.go +++ b/helper/flag-slice/flag_test.go @@ -14,6 +14,8 @@ func TestStringFlag_implements(t *testing.T) { } } +// TestStringFlagSet tests for setting the same flag more than once on the CLI +// like: blah -flag foo -flag bar func TestStringFlagSet(t *testing.T) { sv := new(StringFlag) err := sv.Set("foo") @@ -31,3 +33,18 @@ func TestStringFlagSet(t *testing.T) { t.Fatalf("Bad: %#v", sv) } } + +// TestMultiStringFlag tests for setting the same flag using a comma-separated +// list of items like: blah -flag=foo,bar +func TestMultiStringFlag(t *testing.T) { + sv := new(StringFlag) + err := sv.Set("chocolate,vanilla") + if err != nil { + t.Fatalf("err :%s", err) + } + + expected := []string{"chocolate", "vanilla"} + if !reflect.DeepEqual([]string(*sv), expected) { + t.Fatalf("Expected: %#v, found: %#v", expected, sv) + } +}