github.com/amanya/packer@v0.12.1-0.20161117214323-902ac5ab2eb6/builder/vmware/common/step_run.go (about) 1 package common 2 3 import ( 4 "fmt" 5 "github.com/mitchellh/multistep" 6 "github.com/mitchellh/packer/packer" 7 "time" 8 ) 9 10 // This step runs the created virtual machine. 11 // 12 // Uses: 13 // driver Driver 14 // ui packer.Ui 15 // vmx_path string 16 // 17 // Produces: 18 // <nothing> 19 type StepRun struct { 20 BootWait time.Duration 21 DurationBeforeStop time.Duration 22 Headless bool 23 24 bootTime time.Time 25 vmxPath string 26 } 27 28 func (s *StepRun) Run(state multistep.StateBag) multistep.StepAction { 29 driver := state.Get("driver").(Driver) 30 ui := state.Get("ui").(packer.Ui) 31 vmxPath := state.Get("vmx_path").(string) 32 33 // Set the VMX path so that we know we started the machine 34 s.bootTime = time.Now() 35 s.vmxPath = vmxPath 36 37 ui.Say("Starting virtual machine...") 38 if s.Headless { 39 vncIpRaw, vncIpOk := state.GetOk("vnc_ip") 40 vncPortRaw, vncPortOk := state.GetOk("vnc_port") 41 vncPasswordRaw, vncPasswordOk := state.GetOk("vnc_password") 42 43 if vncIpOk && vncPortOk && vncPasswordOk { 44 vncIp := vncIpRaw.(string) 45 vncPort := vncPortRaw.(uint) 46 vncPassword := vncPasswordRaw.(string) 47 48 ui.Message(fmt.Sprintf( 49 "The VM will be run headless, without a GUI. If you want to\n"+ 50 "view the screen of the VM, connect via VNC with the password \"%s\" to\n"+ 51 "%s:%d", vncPassword, vncIp, vncPort)) 52 } else { 53 ui.Message("The VM will be run headless, without a GUI, as configured.\n" + 54 "If the run isn't succeeding as you expect, please enable the GUI\n" + 55 "to inspect the progress of the build.") 56 } 57 } 58 59 if err := driver.Start(vmxPath, s.Headless); err != nil { 60 err := fmt.Errorf("Error starting VM: %s", err) 61 state.Put("error", err) 62 ui.Error(err.Error()) 63 return multistep.ActionHalt 64 } 65 66 // Wait the wait amount 67 if int64(s.BootWait) > 0 { 68 ui.Say(fmt.Sprintf("Waiting %s for boot...", s.BootWait.String())) 69 wait := time.After(s.BootWait) 70 WAITLOOP: 71 for { 72 select { 73 case <-wait: 74 break WAITLOOP 75 case <-time.After(1 * time.Second): 76 if _, ok := state.GetOk(multistep.StateCancelled); ok { 77 return multistep.ActionHalt 78 } 79 } 80 } 81 82 } 83 84 return multistep.ActionContinue 85 } 86 87 func (s *StepRun) Cleanup(state multistep.StateBag) { 88 driver := state.Get("driver").(Driver) 89 ui := state.Get("ui").(packer.Ui) 90 91 // If we started the machine... stop it. 92 if s.vmxPath != "" { 93 // If we started it less than 5 seconds ago... wait. 94 sinceBootTime := time.Since(s.bootTime) 95 waitBootTime := s.DurationBeforeStop 96 if sinceBootTime < waitBootTime { 97 sleepTime := waitBootTime - sinceBootTime 98 ui.Say(fmt.Sprintf( 99 "Waiting %s to give VMware time to clean up...", sleepTime.String())) 100 time.Sleep(sleepTime) 101 } 102 103 // See if it is running 104 running, _ := driver.IsRunning(s.vmxPath) 105 if running { 106 ui.Say("Stopping virtual machine...") 107 if err := driver.Stop(s.vmxPath); err != nil { 108 ui.Error(fmt.Sprintf("Error stopping VM: %s", err)) 109 } 110 } 111 } 112 }