vagrant-vsphere 0.7.0 → 0.7.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (40) hide show
  1. data/.gitignore +8 -6
  2. data/Gemfile +10 -10
  3. data/LICENSE.txt +23 -23
  4. data/README.md +180 -175
  5. data/Rakefile +16 -16
  6. data/example_box/metadata.json +2 -2
  7. data/lib/vSphere/action.rb +172 -172
  8. data/lib/vSphere/action/clone.rb +131 -127
  9. data/lib/vSphere/action/close_vsphere.rb +23 -23
  10. data/lib/vSphere/action/connect_vsphere.rb +25 -25
  11. data/lib/vSphere/action/destroy.rb +37 -37
  12. data/lib/vSphere/action/get_ssh_info.rb +37 -37
  13. data/lib/vSphere/action/get_state.rb +45 -45
  14. data/lib/vSphere/action/is_created.rb +15 -15
  15. data/lib/vSphere/action/is_running.rb +20 -20
  16. data/lib/vSphere/action/message_already_created.rb +17 -17
  17. data/lib/vSphere/action/message_not_created.rb +17 -17
  18. data/lib/vSphere/action/message_not_running.rb +18 -18
  19. data/lib/vSphere/action/power_off.rb +27 -27
  20. data/lib/vSphere/action/power_on.rb +31 -31
  21. data/lib/vSphere/action/sync_folders.rb +94 -97
  22. data/lib/vSphere/config.rb +37 -37
  23. data/lib/vSphere/errors.rb +14 -11
  24. data/lib/vSphere/plugin.rb +29 -29
  25. data/lib/vSphere/provider.rb +38 -38
  26. data/lib/vSphere/util/machine_helpers.rb +15 -15
  27. data/lib/vSphere/util/vim_helpers.rb +37 -37
  28. data/lib/vSphere/version.rb +5 -5
  29. data/lib/vagrant-vsphere.rb +17 -17
  30. data/locales/en.yml +66 -65
  31. data/spec/action_spec.rb +116 -116
  32. data/spec/clone_spec.rb +31 -31
  33. data/spec/connect_vsphere_spec.rb +23 -23
  34. data/spec/destroy_spec.rb +30 -30
  35. data/spec/get_ssh_info_spec.rb +30 -30
  36. data/spec/get_state_spec.rb +54 -54
  37. data/spec/is_created_spec.rb +28 -28
  38. data/spec/spec_helper.rb +98 -98
  39. data/vSphere.gemspec +29 -28
  40. metadata +14 -8
@@ -1,3 +1,3 @@
1
- {
2
- "provider": "vSphere"
1
+ {
2
+ "provider": "vSphere"
3
3
  }
@@ -1,172 +1,172 @@
1
- require 'vagrant'
2
- require 'vagrant/action/builder'
3
-
4
- module VagrantPlugins
5
- module VSphere
6
- module Action
7
- include Vagrant::Action::Builtin
8
-
9
- #Vagrant commands
10
- def self.action_destroy
11
- Vagrant::Action::Builder.new.tap do |b|
12
- b.use ConfigValidate
13
- b.use ConnectVSphere
14
- b.use Call, IsRunning do |env, b2|
15
- if [:result]
16
- b2.use PowerOff
17
- next
18
- end
19
- end
20
- b.use Destroy
21
- end
22
- end
23
-
24
- def self.action_provision
25
- Vagrant::Action::Builder.new.tap do |b|
26
- b.use ConfigValidate
27
- b.use Call, IsCreated do |env, b2|
28
- if !env[:result]
29
- b2.use MessageNotCreated
30
- next
31
- end
32
-
33
- b2.use Call, IsRunning do |env, b3|
34
- if !env[:result]
35
- b3.use MessageNotRunning
36
- next
37
- end
38
-
39
- b3.use Provision
40
- b3.use SyncFolders
41
- end
42
- end
43
- end
44
- end
45
-
46
- def self.action_ssh
47
- Vagrant::Action::Builder.new.tap do |b|
48
- b.use ConfigValidate
49
- b.use Call, IsCreated do |env, b2|
50
- if !env[:result]
51
- b2.use MessageNotCreated
52
- next
53
- end
54
-
55
- b2.use Call, IsRunning do |env, b3|
56
- if !env[:result]
57
- b3.use MessageNotRunning
58
- next
59
- end
60
-
61
- b3.use SSHExec
62
- end
63
- end
64
- end
65
- end
66
-
67
- def self.action_ssh_run
68
- Vagrant::Action::Builder.new.tap do |b|
69
- b.use ConfigValidate
70
- b.use Call, IsCreated do |env, b2|
71
- if !env[:result]
72
- b2.use MessageNotCreated
73
- next
74
- end
75
-
76
- b2.use Call, IsRunning do |env, b3|
77
- if !env[:result]
78
- b3.use MessageNotRunning
79
- next
80
- end
81
-
82
- b3.use SSHRun
83
- end
84
- end
85
- end
86
- end
87
-
88
- def self.action_up
89
- Vagrant::Action::Builder.new.tap do |b|
90
- b.use ConfigValidate
91
- b.use ConnectVSphere
92
- b.use Call, IsCreated do |env, b2|
93
- if env[:result]
94
- b2.use MessageAlreadyCreated
95
- next
96
- end
97
-
98
- b2.use Clone
99
- end
100
- b.use Call, IsRunning do |env, b2|
101
- if !env[:result]
102
- b2.use PowerOn
103
- end
104
- end
105
- b.use CloseVSphere
106
- b.use Provision
107
- b.use SyncFolders
108
- end
109
- end
110
-
111
- def self.action_halt
112
- Vagrant::Action::Builder.new.tap do |b|
113
- b.use ConfigValidate
114
- b.use ConnectVSphere
115
- b.use Call, IsCreated do |env, b2|
116
- if !env[:result]
117
- b2.use MessageNotCreated
118
- next
119
- end
120
-
121
- b2.use Call, IsRunning do |env, b3|
122
- if !env[:result]
123
- b3.use MessageNotRunning
124
- next
125
- end
126
-
127
- b3.use PowerOff
128
- end
129
- end
130
- b.use CloseVSphere
131
- end
132
- end
133
-
134
- #vSphere specific actions
135
- def self.action_get_state
136
- Vagrant::Action::Builder.new.tap do |b|
137
- b.use ConfigValidate
138
- b.use ConnectVSphere
139
- b.use GetState
140
- b.use CloseVSphere
141
- end
142
- end
143
-
144
- def self.action_get_ssh_info
145
- Vagrant::Action::Builder.new.tap do |b|
146
- b.use ConfigValidate
147
- b.use ConnectVSphere
148
- b.use GetSshInfo
149
- b.use CloseVSphere
150
- end
151
- end
152
-
153
- #autoload
154
- action_root = Pathname.new(File.expand_path('../action', __FILE__))
155
- autoload :Clone, action_root.join('clone')
156
- autoload :CloseVSphere, action_root.join('close_vsphere')
157
- autoload :ConnectVSphere, action_root.join('connect_vsphere')
158
- autoload :Destroy, action_root.join('destroy')
159
- autoload :GetSshInfo, action_root.join('get_ssh_info')
160
- autoload :GetState, action_root.join('get_state')
161
- autoload :IsCreated, action_root.join('is_created')
162
- autoload :IsRunning, action_root.join('is_running')
163
- autoload :MessageAlreadyCreated, action_root.join('message_already_created')
164
- autoload :MessageNotCreated, action_root.join('message_not_created')
165
- autoload :MessageNotRunning, action_root.join('message_not_running')
166
- autoload :PowerOff, action_root.join('power_off')
167
- autoload :PowerOn, action_root.join('power_on')
168
- autoload :SyncFolders, action_root.join('sync_folders')
169
- end
170
- end
171
- end
172
-
1
+ require 'vagrant'
2
+ require 'vagrant/action/builder'
3
+
4
+ module VagrantPlugins
5
+ module VSphere
6
+ module Action
7
+ include Vagrant::Action::Builtin
8
+
9
+ #Vagrant commands
10
+ def self.action_destroy
11
+ Vagrant::Action::Builder.new.tap do |b|
12
+ b.use ConfigValidate
13
+ b.use ConnectVSphere
14
+ b.use Call, IsRunning do |env, b2|
15
+ if [:result]
16
+ b2.use PowerOff
17
+ next
18
+ end
19
+ end
20
+ b.use Destroy
21
+ end
22
+ end
23
+
24
+ def self.action_provision
25
+ Vagrant::Action::Builder.new.tap do |b|
26
+ b.use ConfigValidate
27
+ b.use Call, IsCreated do |env, b2|
28
+ if !env[:result]
29
+ b2.use MessageNotCreated
30
+ next
31
+ end
32
+
33
+ b2.use Call, IsRunning do |env, b3|
34
+ if !env[:result]
35
+ b3.use MessageNotRunning
36
+ next
37
+ end
38
+
39
+ b3.use Provision
40
+ b3.use SyncFolders
41
+ end
42
+ end
43
+ end
44
+ end
45
+
46
+ def self.action_ssh
47
+ Vagrant::Action::Builder.new.tap do |b|
48
+ b.use ConfigValidate
49
+ b.use Call, IsCreated do |env, b2|
50
+ if !env[:result]
51
+ b2.use MessageNotCreated
52
+ next
53
+ end
54
+
55
+ b2.use Call, IsRunning do |env, b3|
56
+ if !env[:result]
57
+ b3.use MessageNotRunning
58
+ next
59
+ end
60
+
61
+ b3.use SSHExec
62
+ end
63
+ end
64
+ end
65
+ end
66
+
67
+ def self.action_ssh_run
68
+ Vagrant::Action::Builder.new.tap do |b|
69
+ b.use ConfigValidate
70
+ b.use Call, IsCreated do |env, b2|
71
+ if !env[:result]
72
+ b2.use MessageNotCreated
73
+ next
74
+ end
75
+
76
+ b2.use Call, IsRunning do |env, b3|
77
+ if !env[:result]
78
+ b3.use MessageNotRunning
79
+ next
80
+ end
81
+
82
+ b3.use SSHRun
83
+ end
84
+ end
85
+ end
86
+ end
87
+
88
+ def self.action_up
89
+ Vagrant::Action::Builder.new.tap do |b|
90
+ b.use ConfigValidate
91
+ b.use ConnectVSphere
92
+ b.use Call, IsCreated do |env, b2|
93
+ if env[:result]
94
+ b2.use MessageAlreadyCreated
95
+ next
96
+ end
97
+
98
+ b2.use Clone
99
+ end
100
+ b.use Call, IsRunning do |env, b2|
101
+ if !env[:result]
102
+ b2.use PowerOn
103
+ end
104
+ end
105
+ b.use CloseVSphere
106
+ b.use Provision
107
+ b.use SyncFolders
108
+ end
109
+ end
110
+
111
+ def self.action_halt
112
+ Vagrant::Action::Builder.new.tap do |b|
113
+ b.use ConfigValidate
114
+ b.use ConnectVSphere
115
+ b.use Call, IsCreated do |env, b2|
116
+ if !env[:result]
117
+ b2.use MessageNotCreated
118
+ next
119
+ end
120
+
121
+ b2.use Call, IsRunning do |env, b3|
122
+ if !env[:result]
123
+ b3.use MessageNotRunning
124
+ next
125
+ end
126
+
127
+ b3.use PowerOff
128
+ end
129
+ end
130
+ b.use CloseVSphere
131
+ end
132
+ end
133
+
134
+ #vSphere specific actions
135
+ def self.action_get_state
136
+ Vagrant::Action::Builder.new.tap do |b|
137
+ b.use ConfigValidate
138
+ b.use ConnectVSphere
139
+ b.use GetState
140
+ b.use CloseVSphere
141
+ end
142
+ end
143
+
144
+ def self.action_get_ssh_info
145
+ Vagrant::Action::Builder.new.tap do |b|
146
+ b.use ConfigValidate
147
+ b.use ConnectVSphere
148
+ b.use GetSshInfo
149
+ b.use CloseVSphere
150
+ end
151
+ end
152
+
153
+ #autoload
154
+ action_root = Pathname.new(File.expand_path('../action', __FILE__))
155
+ autoload :Clone, action_root.join('clone')
156
+ autoload :CloseVSphere, action_root.join('close_vsphere')
157
+ autoload :ConnectVSphere, action_root.join('connect_vsphere')
158
+ autoload :Destroy, action_root.join('destroy')
159
+ autoload :GetSshInfo, action_root.join('get_ssh_info')
160
+ autoload :GetState, action_root.join('get_state')
161
+ autoload :IsCreated, action_root.join('is_created')
162
+ autoload :IsRunning, action_root.join('is_running')
163
+ autoload :MessageAlreadyCreated, action_root.join('message_already_created')
164
+ autoload :MessageNotCreated, action_root.join('message_not_created')
165
+ autoload :MessageNotRunning, action_root.join('message_not_running')
166
+ autoload :PowerOff, action_root.join('power_off')
167
+ autoload :PowerOn, action_root.join('power_on')
168
+ autoload :SyncFolders, action_root.join('sync_folders')
169
+ end
170
+ end
171
+ end
172
+
@@ -1,127 +1,131 @@
1
- require 'rbvmomi'
2
- require 'i18n'
3
- require 'vSphere/util/vim_helpers'
4
- require 'vSphere/util/machine_helpers'
5
-
6
- module VagrantPlugins
7
- module VSphere
8
- module Action
9
- class Clone
10
- include Util::VimHelpers
11
- include Util::MachineHelpers
12
-
13
- def initialize(app, env)
14
- @app = app
15
- end
16
-
17
- def call(env)
18
- machine = env[:machine]
19
- config = machine.provider_config
20
- connection = env[:vSphere_connection]
21
- name = get_name machine, config
22
-
23
- dc = get_datacenter connection, machine
24
- template = dc.find_vm config.template_name
25
-
26
- raise Error::VSphereError, :message => I18n.t('errors.missing_template') if template.nil?
27
-
28
- begin
29
- if config.linked_clone
30
- # The API for linked clones is quite strange. We can't create a linked
31
- # straight from any VM. The disks of the VM for which we can create a
32
- # linked clone need to be read-only and thus VC demands that the VM we
33
- # are cloning from uses delta-disks. Only then it will allow us to
34
- # share the base disk.
35
- #
36
- # Thus, this code first create a delta disk on top of the base disk for
37
- # the to-be-cloned VM, if delta disks aren't used already.
38
- disks = template.config.hardware.device.grep(RbVmomi::VIM::VirtualDisk)
39
- disks.select { |disk| disk.backing.parent == nil }.each do |disk|
40
- spec = {
41
- :deviceChange => [
42
- {
43
- :operation => :remove,
44
- :device => disk
45
- },
46
- {
47
- :operation => :add,
48
- :fileOperation => :create,
49
- :device => disk.dup.tap { |new_disk|
50
- new_disk.backing = new_disk.backing.dup
51
- new_disk.backing.fileName = "[#{disk.backing.datastore.name}]"
52
- new_disk.backing.parent = disk.backing
53
- },
54
- }
55
- ]
56
- }
57
- template.ReconfigVM_Task(:spec => spec).wait_for_completion
58
- end
59
-
60
- location = RbVmomi::VIM.VirtualMachineRelocateSpec(:diskMoveType => :moveChildMostDiskBacking)
61
- else
62
- location = RbVmomi::VIM.VirtualMachineRelocateSpec
63
- location[:pool] = get_resource_pool(connection, machine) unless config.clone_from_vm
64
-
65
- datastore = get_datastore connection, machine
66
- location[:datastore] = datastore unless datastore.nil?
67
- end
68
-
69
- spec = RbVmomi::VIM.VirtualMachineCloneSpec :location => location, :powerOn => true, :template => false
70
-
71
- customization = get_customization_spec_info_by_name connection, machine
72
- spec[:customization] = configure_networks(customization.spec, machine) unless customization.nil?
73
-
74
- env[:ui].info I18n.t('vsphere.creating_cloned_vm')
75
- env[:ui].info " -- #{config.clone_from_vm ? "Source" : "Template"} VM: #{config.template_name}"
76
- env[:ui].info " -- Name: #{name}"
77
-
78
- new_vm = template.CloneVM_Task(:folder => template.parent, :name => name, :spec => spec).wait_for_completion
79
- rescue Exception => e
80
- puts e.message
81
- raise Errors::VSphereError, :message => e.message
82
- end
83
-
84
- #TODO: handle interrupted status in the environment, should the vm be destroyed?
85
-
86
- machine.id = new_vm.config.uuid
87
-
88
- # wait for SSH to be available
89
- wait_for_ssh env
90
-
91
- env[:ui].info I18n.t('vsphere.vm_clone_success')
92
-
93
- @app.call env
94
- end
95
-
96
- private
97
-
98
- def configure_networks(spec, machine)
99
- customization_spec = spec.clone
100
-
101
- # find all the configured private networks
102
- private_networks = machine.config.vm.networks.find_all { |n| n[0].eql? :private_network }
103
- return customization_spec if private_networks.nil?
104
-
105
- # make sure we have enough NIC settings to override with the private network settings
106
- raise Error::VSphereError, :message => I18n.t('errors.too_many_private_networks') if private_networks.length > customization_spec.nicSettingMap.length
107
-
108
- # assign the private network IP to the NIC
109
- private_networks.each_index do |idx|
110
- customization_spec.nicSettingMap[idx].adapter.ip.ipAddress = private_networks[idx][1][:ip]
111
- end
112
-
113
- customization_spec
114
- end
115
-
116
- def get_name(machine, config)
117
- return config.name unless config.name.nil?
118
-
119
- prefix = "#{machine.name}"
120
- prefix.gsub!(/[^-a-z0-9_]/i, "")
121
- # milliseconds + random number suffix to allow for simultaneous `vagrant up` of the same box in different dirs
122
- prefix + "_#{(Time.now.to_f * 1000.0).to_i}_#{rand(100000)}"
123
- end
124
- end
125
- end
126
- end
127
- end
1
+ require 'rbvmomi'
2
+ require 'i18n'
3
+ require 'vSphere/util/vim_helpers'
4
+ require 'vSphere/util/machine_helpers'
5
+
6
+ module VagrantPlugins
7
+ module VSphere
8
+ module Action
9
+ class Clone
10
+ include Util::VimHelpers
11
+ include Util::MachineHelpers
12
+
13
+ def initialize(app, env)
14
+ @app = app
15
+ end
16
+
17
+ def call(env)
18
+ machine = env[:machine]
19
+ config = machine.provider_config
20
+ connection = env[:vSphere_connection]
21
+ name = get_name machine, config
22
+ dc = get_datacenter connection, machine
23
+ template = dc.find_vm config.template_name
24
+
25
+ raise Error::VSphereError, :message => I18n.t('vsphere.errors.missing_template') if template.nil?
26
+
27
+ begin
28
+ location = get_location connection, machine, config
29
+ spec = RbVmomi::VIM.VirtualMachineCloneSpec :location => location, :powerOn => true, :template => false
30
+ customization_info = get_customization_spec_info_by_name connection, machine
31
+
32
+ spec[:customization] = get_customization_spec(machine, customization_info) unless customization_info.nil?
33
+
34
+ env[:ui].info I18n.t('vsphere.creating_cloned_vm')
35
+ env[:ui].info " -- #{config.clone_from_vm ? "Source" : "Template"} VM: #{config.template_name}"
36
+ env[:ui].info " -- Name: #{name}"
37
+
38
+ new_vm = template.CloneVM_Task(:folder => template.parent, :name => name, :spec => spec).wait_for_completion
39
+ rescue Exception => e
40
+ puts e.message
41
+ raise Errors::VSphereError, :message => e.message
42
+ end
43
+
44
+ #TODO: handle interrupted status in the environment, should the vm be destroyed?
45
+
46
+ machine.id = new_vm.config.uuid
47
+
48
+ # wait for SSH to be available
49
+ wait_for_ssh env
50
+
51
+ env[:ui].info I18n.t('vsphere.vm_clone_success')
52
+
53
+ @app.call env
54
+ end
55
+
56
+ private
57
+
58
+ def get_customization_spec(machine, spec_info)
59
+ customization_spec = spec_info.spec.clone
60
+
61
+ # find all the configured private networks
62
+ private_networks = machine.config.vm.networks.find_all { |n| n[0].eql? :private_network }
63
+ return customization_spec if private_networks.nil?
64
+
65
+ # make sure we have enough NIC settings to override with the private network settings
66
+ raise Error::VSphereError, :message => I18n.t('vsphere.errors.too_many_private_networks') if private_networks.length > customization_spec.nicSettingMap.length
67
+
68
+ # assign the private network IP to the NIC
69
+ private_networks.each_index do |idx|
70
+ customization_spec.nicSettingMap[idx].adapter.ip.ipAddress = private_networks[idx][1][:ip]
71
+ end
72
+
73
+ customization_spec
74
+ end
75
+
76
+ def get_location(connection, machine, config)
77
+ if config.linked_clone
78
+ # The API for linked clones is quite strange. We can't create a linked
79
+ # straight from any VM. The disks of the VM for which we can create a
80
+ # linked clone need to be read-only and thus VC demands that the VM we
81
+ # are cloning from uses delta-disks. Only then it will allow us to
82
+ # share the base disk.
83
+ #
84
+ # Thus, this code first create a delta disk on top of the base disk for
85
+ # the to-be-cloned VM, if delta disks aren't used already.
86
+ disks = template.config.hardware.device.grep(RbVmomi::VIM::VirtualDisk)
87
+ disks.select { |disk| disk.backing.parent == nil }.each do |disk|
88
+ spec = {
89
+ :deviceChange => [
90
+ {
91
+ :operation => :remove,
92
+ :device => disk
93
+ },
94
+ {
95
+ :operation => :add,
96
+ :fileOperation => :create,
97
+ :device => disk.dup.tap { |new_disk|
98
+ new_disk.backing = new_disk.backing.dup
99
+ new_disk.backing.fileName = "[#{disk.backing.datastore.name}]"
100
+ new_disk.backing.parent = disk.backing
101
+ },
102
+ }
103
+ ]
104
+ }
105
+ template.ReconfigVM_Task(:spec => spec).wait_for_completion
106
+ end
107
+
108
+ RbVmomi::VIM.VirtualMachineRelocateSpec(:diskMoveType => :moveChildMostDiskBacking)
109
+ else
110
+ location = RbVmomi::VIM.VirtualMachineRelocateSpec
111
+ location[:pool] = get_resource_pool(connection, machine) unless config.clone_from_vm
112
+
113
+ datastore = get_datastore connection, machine
114
+ location[:datastore] = datastore unless datastore.nil?
115
+
116
+ location
117
+ end
118
+ end
119
+
120
+ def get_name(machine, config)
121
+ return config.name unless config.name.nil?
122
+
123
+ prefix = "#{machine.name}"
124
+ prefix.gsub!(/[^-a-z0-9_]/i, "")
125
+ # milliseconds + random number suffix to allow for simultaneous `vagrant up` of the same box in different dirs
126
+ prefix + "_#{(Time.now.to_f * 1000.0).to_i}_#{rand(100000)}"
127
+ end
128
+ end
129
+ end
130
+ end
131
+ end