-
Notifications
You must be signed in to change notification settings - Fork 22
/
vm_state.go
96 lines (76 loc) · 1.86 KB
/
vm_state.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
package vm
import (
"regexp"
bosherr "github.com/cloudfoundry/bosh-utils/errors"
"github.com/cppforlife/bosh-virtualbox-cpi/driver"
)
var (
vmStarted = regexp.MustCompile(`VM ".+?" has been successfully started`)
vmStateMatch = regexp.MustCompile(`VMState="(.+?)"`)
vmStateInaccessible = regexp.MustCompile(`name="<inaccessible>"`)
)
func (vm VMImpl) Exists() (bool, error) {
output, err := vm.driver.Execute("showvminfo", vm.id, "--machinereadable")
if err != nil {
if vm.driver.IsMissingVMErr(output) {
return false, nil
}
return false, err
}
return true, nil
}
func (vm VMImpl) Start(gui bool) error {
mode := "headless"
if gui {
mode = "gui"
}
output, err := vm.driver.ExecuteComplex(
[]string{"startvm", vm.id, "--type", mode},
driver.ExecuteOpts{IgnoreNonZeroExitStatus: true},
)
if err != nil && !vmStarted.MatchString(output) {
return err
}
return nil
}
func (vm VMImpl) Reboot() error {
err := vm.HaltIfRunning()
if err != nil {
return err
}
return vm.Start(false) // todo find out previous state
}
func (vm VMImpl) HaltIfRunning() error {
running, err := vm.IsRunning()
if err != nil {
return err
}
if running {
_, err = vm.driver.Execute("controlvm", vm.id, "poweroff")
}
return err
}
func (vm VMImpl) IsRunning() (bool, error) {
state, err := vm.State()
if err != nil {
return false, err
}
return state == "running", nil
}
func (vm VMImpl) State() (string, error) {
output, err := vm.driver.Execute("showvminfo", vm.id, "--machinereadable")
if err != nil {
if vm.driver.IsMissingVMErr(output) {
return "missing", nil
}
return "", err
}
if vmStateInaccessible.MatchString(output) {
return "inaccessible", nil
}
matches := vmStateMatch.FindStringSubmatch(output)
if len(matches) == 2 {
return matches[1], nil
}
return "", bosherr.Errorf("Unknown VM state:\nOutput: '%s'", output)
}