From ef0c7543e1290cf821087fc6824819c7c39b36b3 Mon Sep 17 00:00:00 2001 From: Jeremy Asher Date: Thu, 1 Sep 2016 12:30:48 -0700 Subject: [PATCH] add amazon-chroot post mount commands This adds an additional PostMountCommands step to the amazon-chroot builder which executes after the volume is mounted, but before the extra chroot mounts and copy step. --- builder/amazon/chroot/builder.go | 29 +++++++----- .../amazon/chroot/step_post_mount_commands.go | 45 +++++++++++++++++++ 2 files changed, 62 insertions(+), 12 deletions(-) create mode 100644 builder/amazon/chroot/step_post_mount_commands.go diff --git a/builder/amazon/chroot/builder.go b/builder/amazon/chroot/builder.go index 681581107..5bf5e7a69 100644 --- a/builder/amazon/chroot/builder.go +++ b/builder/amazon/chroot/builder.go @@ -30,18 +30,19 @@ type Config struct { awscommon.AMIConfig `mapstructure:",squash"` awscommon.AccessConfig `mapstructure:",squash"` - ChrootMounts [][]string `mapstructure:"chroot_mounts"` - CommandWrapper string `mapstructure:"command_wrapper"` - CopyFiles []string `mapstructure:"copy_files"` - DevicePath string `mapstructure:"device_path"` - FromScratch bool `mapstructure:"from_scratch"` - MountOptions []string `mapstructure:"mount_options"` - MountPartition int `mapstructure:"mount_partition"` - MountPath string `mapstructure:"mount_path"` - PreMountCommands []string `mapstructure:"pre_mount_commands"` - RootDeviceName string `mapstructure:"root_device_name"` - RootVolumeSize int64 `mapstructure:"root_volume_size"` - SourceAmi string `mapstructure:"source_ami"` + ChrootMounts [][]string `mapstructure:"chroot_mounts"` + CommandWrapper string `mapstructure:"command_wrapper"` + CopyFiles []string `mapstructure:"copy_files"` + DevicePath string `mapstructure:"device_path"` + FromScratch bool `mapstructure:"from_scratch"` + MountOptions []string `mapstructure:"mount_options"` + MountPartition int `mapstructure:"mount_partition"` + MountPath string `mapstructure:"mount_path"` + PostMountCommands []string `mapstructure:"post_mount_commands"` + PreMountCommands []string `mapstructure:"pre_mount_commands"` + RootDeviceName string `mapstructure:"root_device_name"` + RootVolumeSize int64 `mapstructure:"root_volume_size"` + SourceAmi string `mapstructure:"source_ami"` ctx interpolate.Context } @@ -63,6 +64,7 @@ func (b *Builder) Prepare(raws ...interface{}) ([]string, error) { InterpolateFilter: &interpolate.RenderFilter{ Exclude: []string{ "command_wrapper", + "post_mount_commands", "pre_mount_commands", "mount_path", }, @@ -217,6 +219,9 @@ func (b *Builder) Run(ui packer.Ui, hook packer.Hook, cache packer.Cache) (packe MountOptions: b.config.MountOptions, MountPartition: b.config.MountPartition, }, + &StepPostMountCommands{ + Commands: b.config.PostMountCommands, + }, &StepMountExtra{}, &StepCopyFiles{}, &StepChrootProvision{}, diff --git a/builder/amazon/chroot/step_post_mount_commands.go b/builder/amazon/chroot/step_post_mount_commands.go new file mode 100644 index 000000000..2eb50926c --- /dev/null +++ b/builder/amazon/chroot/step_post_mount_commands.go @@ -0,0 +1,45 @@ +package chroot + +import ( + "github.com/mitchellh/multistep" + "github.com/mitchellh/packer/packer" +) + +type postMountCommandsData struct { + Device string + MountPath string +} + +// StepPostMountCommands allows running arbitrary commands after mounting the +// device, but prior to the bind mount and copy steps. +type StepPostMountCommands struct { + Commands []string +} + +func (s *StepPostMountCommands) Run(state multistep.StateBag) multistep.StepAction { + config := state.Get("config").(*Config) + device := state.Get("device").(string) + mountPath := state.Get("mount_path").(string) + ui := state.Get("ui").(packer.Ui) + wrappedCommand := state.Get("wrappedCommand").(CommandWrapper) + + if len(s.Commands) == 0 { + return multistep.ActionContinue + } + + ctx := config.ctx + ctx.Data = &postMountCommandsData{ + Device: device, + MountPath: mountPath, + } + + ui.Say("Running post-mount commands...") + if err := RunLocalCommands(s.Commands, wrappedCommand, ctx, ui); err != nil { + state.Put("error", err) + ui.Error(err.Error()) + return multistep.ActionHalt + } + return multistep.ActionContinue +} + +func (s *StepPostMountCommands) Cleanup(state multistep.StateBag) {}