diff --git a/command/fix/command.go b/command/fix/command.go new file mode 100644 index 000000000..4a50e213d --- /dev/null +++ b/command/fix/command.go @@ -0,0 +1,55 @@ +package fix + +import ( + "encoding/json" + "flag" + "fmt" + "github.com/mitchellh/packer/packer" + "os" + "strings" +) + +type Command byte + +func (Command) Help() string { + return strings.TrimSpace(helpString) +} + +func (c Command) Run(env packer.Environment, args []string) int { + cmdFlags := flag.NewFlagSet("fix", flag.ContinueOnError) + cmdFlags.Usage = func() { env.Ui().Say(c.Help()) } + if err := cmdFlags.Parse(args); err != nil { + return 1 + } + + args = cmdFlags.Args() + if len(args) != 1 { + cmdFlags.Usage() + return 1 + } + + // Read the file for decoding + tplF, err := os.Open(args[0]) + if err != nil { + env.Ui().Error(fmt.Sprintf("Error opening template: %s", err)) + return 1 + } + defer tplF.Close() + + // Decode the JSON into a generic map structure + var templateData map[string]interface{} + decoder := json.NewDecoder(tplF) + if err := decoder.Decode(&templateData); err != nil { + env.Ui().Error(fmt.Sprintf("Error parsing template: %s", err)) + return 1 + } + + // Close the file since we're done with that + tplF.Close() + + return 0 +} + +func (c Command) Synopsis() string { + return "fixes templates from old versions of packer" +} diff --git a/command/fix/command_test.go b/command/fix/command_test.go new file mode 100644 index 000000000..e6c0c59e4 --- /dev/null +++ b/command/fix/command_test.go @@ -0,0 +1,14 @@ +package fix + +import ( + "github.com/mitchellh/packer/packer" + "testing" +) + +func TestCommand_Impl(t *testing.T) { + var raw interface{} + raw = new(Command) + if _, ok := raw.(packer.Command); !ok { + t.Fatalf("must be a Command") + } +} diff --git a/command/fix/help.go b/command/fix/help.go new file mode 100644 index 000000000..aa46218dc --- /dev/null +++ b/command/fix/help.go @@ -0,0 +1,15 @@ +package fix + +const helpString = ` +Usage: packer fix [options] TEMPLATE + + Reads the JSON template and attempts to fix known backwards + incompatibilities. The fixed template will be outputted to standard out. + + If the template cannot be fixed due to an error, the command will exit + with a non-zero exit status. Error messages will appear on standard error. + +Options: + + -verbose Output each fix to standard error +` diff --git a/config.go b/config.go index 7bfaabc76..12a78d300 100644 --- a/config.go +++ b/config.go @@ -27,6 +27,7 @@ const defaultConfig = ` "commands": { "build": "packer-command-build", + "fix": "packer-command-fix", "validate": "packer-command-validate" }, diff --git a/plugin/command-fix/main.go b/plugin/command-fix/main.go new file mode 100644 index 000000000..8ae6d42a0 --- /dev/null +++ b/plugin/command-fix/main.go @@ -0,0 +1,10 @@ +package main + +import ( + "github.com/mitchellh/packer/command/fix" + "github.com/mitchellh/packer/packer/plugin" +) + +func main() { + plugin.ServeCommand(new(fix.Command)) +}