From 52dad0d9a32cfd14d61513f661299a24e7713cab Mon Sep 17 00:00:00 2001 From: Jacob Carlborg Date: Fri, 28 Oct 2022 20:21:04 +0200 Subject: [PATCH] Add boot steps configuration option Adds a new configuration option called `boot_steps`. This is an array of tuples of boot commands, to type when the virtual machine is booted. The first element of the tuple is the actual boot command. The second element of the tuple, which is optional, is a description of what the boot command does. This is intended to be used for interactive installers that requires many commands to complete the installation. Both the command and the description will be printed when logging is enabled. When debug mode is enabled Packer will pause after typing each boot command. This will make it easier to follow along the installation process and make sure the Packer and the installer are in sync. --- bootcommand/config.go | 44 ++++++++++++++++++++++++++++++++++++++ bootcommand/config_test.go | 9 ++++++++ 2 files changed, 53 insertions(+) diff --git a/bootcommand/config.go b/bootcommand/config.go index 2ef5d926fa..f8b7ac67af 100644 --- a/bootcommand/config.go +++ b/bootcommand/config.go @@ -165,6 +165,45 @@ type BootConfig struct { // well, and are covered in the section below on the boot command. If this // is not specified, it is assumed the installer will start itself. BootCommand []string `mapstructure:"boot_command"` + // This is an array of tuples of boot commands, to type when the virtual + // machine is booted. The first element of the tuple is the actual boot + // command. The second element of the tuple, which is optional, is a + // description of what the boot command does. This is intended to be used for + // interactive installers that requires many commands to complete the + // installation. Both the command and the description will be printed when + // logging is enabled. When debug mode is enabled Packer will pause after + // typing each boot command. This will make it easier to follow along the + // installation process and make sure the Packer and the installer are in + // sync. `boot_steps` and `boot_commands` are mutually exclusive. + // + // Example: + // + // In HCL: + // ```hcl + // boot_steps = [ + // ["1", "Install NetBSD"], + // ["a", "Installation messages in English"], + // ["a", "Keyboard type: unchanged"], + // + // ["a", "Install NetBSD to hard disk"], + // ["b", "Yes"] + // ] + // ``` + // + // In JSON: + // ```json + // { + // "boot_steps": [ + // ["1", "Install NetBSD"], + // ["a", "Installation messages in English"], + // ["a", "Keyboard type: unchanged"], + // + // ["a", "Install NetBSD to hard disk"], + // ["b", "Yes"] + // ] + // } + // ``` + BootSteps [][]string `mapstructure:"boot_steps" required:"false"` } // The boot command "typed" character for character over a VNC connection to @@ -184,6 +223,11 @@ type VNCConfig struct { } func (c *BootConfig) Prepare(ctx *interpolate.Context) (errs []error) { + if len(c.BootCommand) > 0 && len(c.BootSteps) > 0 { + errs = append(errs, + fmt.Errorf("Both boot command and boot steps cannot be used.")) + } + if c.BootWait == 0 { c.BootWait = 10 * time.Second } diff --git a/bootcommand/config_test.go b/bootcommand/config_test.go index a8297c17f5..f0bca76b52 100644 --- a/bootcommand/config_test.go +++ b/bootcommand/config_test.go @@ -28,6 +28,15 @@ func TestConfigPrepare(t *testing.T) { if len(errs) > 0 { t.Fatalf("bad: %#v", errs) } + + // Test boot command and boot steps + c = new(BootConfig) + c.BootCommand = []string{"a", "b"} + c.BootSteps = [][]string{{"a"}, {"b"}} + errs = c.Prepare(&interpolate.Context{}) + if len(errs) == 0 { + t.Fatal("should error") + } } func TestVNCConfigPrepare(t *testing.T) {