vagrant-libvirt 0.0.25 → 0.0.26

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 6a9f2dc33e98d6a6508eef0d5f08104cf021f9f7
4
- data.tar.gz: b42c0511ec12193843ebae0bd285598327847810
3
+ metadata.gz: 8c21fb27cb9d1d69b36af2d3b057639381ad6e2c
4
+ data.tar.gz: c02977b68b33bab4a2786634e9ba9f3f53ed256a
5
5
  SHA512:
6
- metadata.gz: f2a7909225e3a571d75c96cfa4221baca176e17c48afc725c6d499f3eb6e63a33983a222492d64c043d7565b0623f3ca87c00d33ca27e0e51b55db0a14c33922
7
- data.tar.gz: a997be0c048ea6708a40462074a5468c1f466e2a2cc1fc64b5ca76866b97ecf7909ec10bc29c04eae6fd635ec483a305b7e70b81caae1f5f568893295f0a88a5
6
+ metadata.gz: 8a41f855485a0a6330d5252ce38bcb0575f2b6c05448109c9be316f884ba2b5a5fa4ea2761e9535f253ef4efc2fff8799a168f9f574825e5d46601251c23b0af
7
+ data.tar.gz: 4413ab7c72460e77df91097458176ba93e85f1544dd7c86f262abc792d2762cb83e5bebb5a292825b60cfd2ced501868b084116163e5d416678dbf095a2af601
data/Gemfile CHANGED
@@ -8,6 +8,7 @@ group :development do
8
8
  # gem dependency because we expect to be installed within the
9
9
  # Vagrant environment itself using `vagrant plugin`.
10
10
  gem "vagrant", :git => "git://github.com/mitchellh/vagrant.git"
11
+ gem 'pry'
11
12
  end
12
13
 
13
14
  group :plugins do
data/README.md CHANGED
@@ -64,7 +64,7 @@ a `config.vm.provider` block. So first, add Libvirt box using any name you
64
64
  want. This is just an example of Libvirt CentOS 6.4 box available:
65
65
 
66
66
  ```
67
- $ vagrant box add centos64 http://kwok.cz/centos64.box
67
+ vagrant box add centos64 http://citozin.com/centos64.box
68
68
  ```
69
69
 
70
70
  ### Create Vagrantfile
@@ -92,6 +92,7 @@ $ vagrant up --provider=libvirt
92
92
  Vagrant needs to know that we want to use Libvirt and not default VirtualBox.
93
93
  That's why there is `--provider=libvirt` option specified. Other way to tell
94
94
  Vagrant to use Libvirt provider is to setup environment variable
95
+
95
96
  `export VAGRANT_DEFAULT_PROVIDER=libvirt`.
96
97
 
97
98
  ### How Project Is Created
@@ -120,7 +121,7 @@ Although it should work without any configuration for most people, this provider
120
121
  * `connect_via_ssh` - If use ssh tunnel to connect to Libvirt.
121
122
  * `username` - Username and password to access Libvirt.
122
123
  * `password` - Password to access Libvirt.
123
- * `id_ssh_key_file` - The id ssh key file name to access Libvirt (eg: id_dsa or id_rsa or ... in the user .ssh directory)
124
+ * `id_ssh_key_file` - If not nil, uses this ssh private key to access Libvirt. Default is $HOME/.ssh/id_rsa. Prepends $HOME/.ssh/ if no directory.
124
125
  * `socket` - Path to the libvirt unix socket (eg: /var/run/libvirt/libvirt-sock)
125
126
  * `uri` - For advanced usage. Directly specifies what libvirt connection URI vagrant-libvirt should use. Overrides all other connection configuration options.
126
127
 
@@ -156,7 +157,9 @@ end
156
157
  * `graphics_ip` - Sets the IP for the display protocol to bind to. Defaults to "127.0.0.0.1".
157
158
  * `graphics_passwd` - Sets the password for the display protocol. Working for vnc and spice. by default working without passsword.
158
159
  * `video_type` - Sets the graphics card type exposed to the guest. Defaults to "cirrus". [Possible values](http://libvirt.org/formatdomain.html#elementsVideo) are "vga", "cirrus", "vmvga", "xen", "vbox", or "qxl".
160
+ * `keymap` - Set keymap for vm. default: en-us
159
161
  * `video_vram` - Used by some graphics card types to vary the amount of RAM dedicated to video. Defaults to 9216.
162
+ * `machine` - Sets machine type. Equivalent to qemu `-machine`. Use `qemu-system-x86_64 -machine help` to get a list of supported machines.
160
163
 
161
164
 
162
165
  Specific domain settings can be set for each domain separately in multi-VM
@@ -199,7 +202,10 @@ An examples of network interface definitions:
199
202
 
200
203
  # Public Network
201
204
  config.vm.define :test_vm1 do |test_vm1|
202
- test_vm1.vm.network :public_network, :dev => "eth0", :mode => 'bridge'
205
+ test_vm1.vm.network :public_network,
206
+ :dev => "virbr0",
207
+ :mode => "bridge",
208
+ :type => "bridge"
203
209
  end
204
210
  ```
205
211
 
@@ -235,23 +241,31 @@ starts with 'libvirt__' string. Here is a list of those options:
235
241
  * `:libvirt__dhcp_enabled` - If DHCP will offer addresses, or not. Used only
236
242
  when creating new network. Default is true.
237
243
  * `:libvirt__adapter` - Number specifiyng sequence number of interface.
238
- * `:libvirt__forward_mode` - Specify one of `none`, `nat` or `route` options.
244
+ * `:libvirt__forward_mode` - Specify one of `veryisolated`, `none`, `nat` or `route` options.
239
245
  This option is used only when creating new network. Mode `none` will create
240
246
  isolated network without NATing or routing outside. You will want to use
241
247
  NATed forwarding typically to reach networks outside of hypervisor. Routed
242
248
  forwarding is typically useful to reach other networks within hypervisor.
249
+ `veryisolated` described [here](https://libvirt.org/formatnetwork.html#examplesNoGateway).
243
250
  By default, option `nat` is used.
244
251
  * `:libvirt__forward_device` - Name of interface/device, where network should
245
252
  be forwarded (NATed or routed). Used only when creating new network. By
246
253
  default, all physical interfaces are used.
247
254
  * `:mac` - MAC address for the interface.
248
- * `model_type` - parameter specifies the model of the network adapter when you create a domain value by default virtio KVM believe possible values, see the documentation for libvirt
255
+ * `:model_type` - parameter specifies the model of the network adapter when you create a domain value by default virtio KVM believe possible values, see the documentation for libvirt
256
+
257
+ When the option `:libvirt__dhcp_enabled` is to to 'false' it shouldn't matter
258
+ whether the virtual network contains a DHCP server or not and vagrant-libvirt
259
+ should not fail on it. The only situation where vagrant-libvirt should fail
260
+ is when DHCP is requested but isn't configured on a matching already existing
261
+ virtual network.
249
262
 
250
263
  ### Public Network Options
251
264
  * `:dev` - Physical device that the public interface should use. Default is 'eth0'.
252
265
  * `:mode` - The mode in which the public interface should operate in. Supported
253
266
  modes are available from the [libvirt documentation](http://www.libvirt.org/formatdomain.html#elementsNICSDirect).
254
267
  Default mode is 'bridge'.
268
+ * `:type` - is type of interface.(`<interface type="#{@type}">`)
255
269
  * `:mac` - MAC address for the interface.
256
270
  * `:ovs` - Support to connect to an open vSwitch bridge device. Default is 'false'.
257
271
 
@@ -296,13 +310,33 @@ Vagrant.configure("2") do |config|
296
310
  end
297
311
  ```
298
312
 
313
+ ## CDROMs
314
+
315
+ You can attach up to four (4) CDROMs to a VM via `libvirt.storage :file, :device => :cdrom`. Available options are:
316
+
317
+ * `path` - The path to the iso to be used for the CDROM drive.
318
+ * `dev` - The device to use (`hda`, `hdb`, `hdc`, or `hdd`). This will be automatically determined if unspecified.
319
+ * `bus` - The bus to use for the CDROM drive. Defaults to `ide`
320
+
321
+ The following example creates three CDROM drives in the VM:
322
+
323
+ ```ruby
324
+ Vagrant.configure("2") do |config|
325
+ config.vm.provider :libvirt do |libvirt|
326
+ libvirt.storage :file, :device => :cdrom, :path => '/path/to/iso1.iso'
327
+ libvirt.storage :file, :device => :cdrom, :path => '/path/to/iso2.iso'
328
+ libvirt.storage :file, :device => :cdrom, :path => '/path/to/iso3.iso'
329
+ end
330
+ end
331
+ ```
332
+
299
333
  ## SSH Access To VM
300
334
 
301
335
  vagrant-libvirt supports vagrant's [standard ssh settings](https://docs.vagrantup.com/v2/vagrantfile/ssh_settings.html).
302
336
 
303
337
  ## Forwarded Ports
304
338
 
305
- vagrant-libvirt supports Forwarded Ports via ssh port forwarding. Please note that due to a well known limitation only the TCP protocol is supported. For each `forwarded_port` directive you specify in your Vagrantfile, vagrant-libvirt will maintain an active ssh process for the lifetime of the VM.
339
+ vagrant-libvirt supports Forwarded Ports via ssh port forwarding. Please note that due to a well known limitation only the TCP protocol is supported. For each `forwarded_port` directive you specify in your Vagrantfile, vagrant-libvirt will maintain an active ssh process for the lifetime of the VM.
306
340
 
307
341
  vagrant-libvirt supports an additional `forwarded_port` option
308
342
  `gateway_ports` which defaults to `false`, but can be set to `true` if
@@ -350,6 +384,14 @@ The box is a tarball containing:
350
384
  * `metadata.json` file describing box image (provider, virtual_size, format).
351
385
  * `Vagrantfile` that does default settings for the provider-specific configuration for this provider.
352
386
 
387
+ ## Create Box
388
+ This script creates a vagrant-libvirt box from a qcow2 file:
389
+
390
+ Usage:
391
+
392
+ ```create_box.sh ubuntu14.qcow2```
393
+ Used Packer to create the qcow2 images, templates available at https://github.com/jakobadam/packer-qemu-templates
394
+
353
395
  ## Development
354
396
 
355
397
  To work on the `vagrant-libvirt` plugin, clone this repository out, and use
@@ -6,7 +6,7 @@ module VagrantPlugins
6
6
  module Action
7
7
  # Include the built-in modules so we can use them as top-level things.
8
8
  include Vagrant::Action::Builtin
9
- @logger = Log4r::Logger.new('vagrant_libvirt::action')
9
+ @logger = Log4r::Logger.new('vagrant_libvirt::action')
10
10
 
11
11
  # This action is called to bring the box up from nothing.
12
12
  def self.action_up
@@ -38,7 +38,7 @@ module VagrantPlugins
38
38
  b2.use StartDomain
39
39
  b2.use WaitTillUp
40
40
 
41
-
41
+
42
42
 
43
43
 
44
44
  b2.use ForwardPorts
@@ -145,6 +145,13 @@ module VagrantPlugins
145
145
  end
146
146
  end
147
147
 
148
+ # not implemented and looks like not require
149
+ def self.action_package
150
+ lambda do |env|
151
+ raise Errors::PackageNotSupported
152
+ end
153
+ end
154
+
148
155
  # This is the action that is primarily responsible for completely
149
156
  # freeing the resources of the underlying virtual machine.
150
157
  def self.action_destroy
@@ -279,6 +286,14 @@ module VagrantPlugins
279
286
  end
280
287
  end
281
288
 
289
+ def self.action_read_mac_addresses
290
+ Vagrant::Action::Builder.new.tap do |b|
291
+ b.use ConfigValidate
292
+ b.use ConnectLibvirt
293
+ b.use ReadMacAddresses
294
+ end
295
+ end
296
+
282
297
  # This is the action that will run a single SSH command.
283
298
  def self.action_ssh_run
284
299
  Vagrant::Action::Builder.new.tap do |b|
@@ -329,11 +344,12 @@ module VagrantPlugins
329
344
  autoload :PruneNFSExports, action_root.join('prune_nfs_exports')
330
345
 
331
346
  autoload :ReadSSHInfo, action_root.join('read_ssh_info')
347
+ autoload :ReadMacAddresses, action_root.join('read_mac_addresses')
332
348
  autoload :ReadState, action_root.join('read_state')
333
349
  autoload :ResumeDomain, action_root.join('resume_domain')
334
350
  autoload :SetNameOfDomain, action_root.join('set_name_of_domain')
335
-
336
- # I don't think we need it anymore
351
+
352
+ # I don't think we need it anymore
337
353
  autoload :ShareFolders, action_root.join('share_folders')
338
354
  autoload :StartDomain, action_root.join('start_domain')
339
355
  autoload :SuspendDomain, action_root.join('suspend_domain')
@@ -3,7 +3,6 @@ require 'log4r'
3
3
  module VagrantPlugins
4
4
  module ProviderLibvirt
5
5
  module Action
6
-
7
6
  class CreateDomain
8
7
  include VagrantPlugins::ProviderLibvirt::Util::ErbTemplate
9
8
 
@@ -13,11 +12,17 @@ module VagrantPlugins
13
12
  end
14
13
 
15
14
  def _disk_name(name, disk)
16
- return "#{name}-#{disk[:device]}.#{disk[:type]}" # disk name
15
+ "#{name}-#{disk[:device]}.#{disk[:type]}" # disk name
17
16
  end
18
17
 
19
18
  def _disks_print(disks)
20
- return disks.collect{ |x| x[:device]+'('+x[:type]+','+x[:size]+')' }.join(', ')
19
+ disks.collect do |x|
20
+ x[:device] + '(' + x[:type] + ',' + x[:size] + ')'
21
+ end.join(', ')
22
+ end
23
+
24
+ def _cdroms_print(cdroms)
25
+ cdroms.collect { |x| x[:dev] }.join(', ')
21
26
  end
22
27
 
23
28
  def call(env)
@@ -28,9 +33,10 @@ module VagrantPlugins
28
33
  @name = env[:domain_name]
29
34
  @cpus = config.cpus.to_i
30
35
  @cpu_mode = config.cpu_mode
36
+ @machine_type = config.machine_type
31
37
  @disk_bus = config.disk_bus
32
38
  @nested = config.nested
33
- @memory_size = config.memory.to_i*1024
39
+ @memory_size = config.memory.to_i * 1024
34
40
  @domain_volume_cache = config.volume_cache
35
41
  @kernel = config.kernel
36
42
  @cmd_line = config.cmd_line
@@ -46,10 +52,12 @@ module VagrantPlugins
46
52
  end
47
53
  @video_type = config.video_type
48
54
  @video_vram = config.video_vram
55
+ @keymap = config.keymap
49
56
 
50
57
  # Storage
51
58
  @storage_pool_name = config.storage_pool_name
52
59
  @disks = config.disks
60
+ @cdroms = config.cdroms
53
61
 
54
62
  config = env[:machine].provider_config
55
63
  @domain_type = config.driver
@@ -63,10 +71,9 @@ module VagrantPlugins
63
71
  @domain_volume_path = domain_volume.path
64
72
 
65
73
  # the default storage prefix is typically: /var/lib/libvirt/images/
66
- storage_prefix = File.dirname(@domain_volume_path)+'/' # steal
74
+ storage_prefix = File.dirname(@domain_volume_path) + '/' # steal
67
75
 
68
76
  @disks.each do |disk|
69
-
70
77
  disk[:path] ||= _disk_name(@name, disk)
71
78
 
72
79
  # On volume creation, the <path> element inside <target>
@@ -81,15 +88,15 @@ module VagrantPlugins
81
88
  # qemu-img create -f qcow2 <path> 5g
82
89
  begin
83
90
  domain_volume_disk = env[:libvirt_compute].volumes.create(
84
- :name => disk[:name],
85
- :format_type => disk[:type],
86
- :path => disk[:absolute_path],
87
- :capacity => disk[:size],
91
+ name: disk[:name],
92
+ format_type: disk[:type],
93
+ path: disk[:absolute_path],
94
+ capacity: disk[:size],
88
95
  #:allocation => ?,
89
- :pool_name => @storage_pool_name)
96
+ pool_name: @storage_pool_name)
90
97
  rescue Fog::Errors::Error => e
91
98
  raise Errors::FogDomainVolumeCreateError,
92
- :error_message => e.message
99
+ error_message: e.message
93
100
  end
94
101
  end
95
102
 
@@ -98,7 +105,7 @@ module VagrantPlugins
98
105
  env[:ui].info(" -- Name: #{@name}")
99
106
  env[:ui].info(" -- Domain type: #{@domain_type}")
100
107
  env[:ui].info(" -- Cpus: #{@cpus}")
101
- env[:ui].info(" -- Memory: #{@memory_size/1024}M")
108
+ env[:ui].info(" -- Memory: #{@memory_size / 1024}M")
102
109
  env[:ui].info(" -- Base box: #{env[:machine].box.name}")
103
110
  env[:ui].info(" -- Storage pool: #{@storage_pool_name}")
104
111
  env[:ui].info(" -- Image: #{@domain_volume_path}")
@@ -108,9 +115,10 @@ module VagrantPlugins
108
115
  env[:ui].info(" -- Graphics Type: #{@graphics_type}")
109
116
  env[:ui].info(" -- Graphics Port: #{@graphics_port}")
110
117
  env[:ui].info(" -- Graphics IP: #{@graphics_ip}")
111
- env[:ui].info(" -- Graphics Password: #{@graphics_passwd.empty? ? 'Not defined': 'Defined'}")
118
+ env[:ui].info(" -- Graphics Password: #{@graphics_passwd.empty? ? 'Not defined' : 'Defined'}")
112
119
  env[:ui].info(" -- Video Type: #{@video_type}")
113
120
  env[:ui].info(" -- Video VRAM: #{@video_vram}")
121
+ env[:ui].info(" -- Keymap: #{@keymap}")
114
122
 
115
123
  if @disks.length > 0
116
124
  env[:ui].info(" -- Disks: #{_disks_print(@disks)}")
@@ -118,6 +126,13 @@ module VagrantPlugins
118
126
  @disks.each do |disk|
119
127
  env[:ui].info(" -- Disk(#{disk[:device]}): #{disk[:absolute_path]}")
120
128
  end
129
+
130
+ if @cdroms.length > 0
131
+ env[:ui].info(" -- CDROMS: #{_cdroms_print(@cdroms)}")
132
+ end
133
+ @cdroms.each do |cdrom|
134
+ env[:ui].info(" -- CDROM(#{cdrom[:dev]}): #{cdrom[:path]}")
135
+ end
121
136
  env[:ui].info(" -- Command line : #{@cmd_line}")
122
137
 
123
138
  # Create libvirt domain.
@@ -125,10 +140,9 @@ module VagrantPlugins
125
140
  # existing volume? Use domain creation from template..
126
141
  begin
127
142
  server = env[:libvirt_compute].servers.create(
128
- :xml => to_xml('domain'))
143
+ xml: to_xml('domain'))
129
144
  rescue Fog::Errors::Error => e
130
- raise Errors::FogCreateServerError,
131
- :error_message => e.message
145
+ raise Errors::FogCreateServerError, error_message: e.message
132
146
  end
133
147
 
134
148
  # Immediately save the ID since it is created at this point.
@@ -137,7 +151,6 @@ module VagrantPlugins
137
151
  @app.call(env)
138
152
  end
139
153
  end
140
-
141
154
  end
142
155
  end
143
156
  end
@@ -17,8 +17,8 @@ module VagrantPlugins
17
17
  def initialize(app, env)
18
18
  @logger = Log4r::Logger.new('vagrant_libvirt::action::create_network_interfaces')
19
19
  @management_network_name = env[:machine].provider_config.management_network_name
20
- config = env[:machine].provider_config
21
- @nic_model_type = config.nic_model_type
20
+ config = env[:machine].provider_config
21
+ @nic_model_type = config.nic_model_type
22
22
  @app = app
23
23
  end
24
24
 
@@ -74,8 +74,8 @@ module VagrantPlugins
74
74
  # Configuration for public interfaces which use the macvtap driver
75
75
  if iface_configuration[:iface_type] == :public_network
76
76
  @device = iface_configuration.fetch(:dev, 'eth0')
77
- @type = iface_configuration.fetch(:type, 'direct')
78
77
  @mode = iface_configuration.fetch(:mode, 'bridge')
78
+ @type = iface_configuration.fetch(:type, 'direct')
79
79
  @model_type = iface_configuration.fetch(:model_type, @nic_model_type)
80
80
  template_name = 'public_interface'
81
81
  @logger.info("Setting up public interface using device #{@device} in mode #{@mode}")
@@ -156,9 +156,7 @@ module VagrantPlugins
156
156
  # Get list of all (active and inactive) libvirt networks.
157
157
  available_networks = libvirt_networks(libvirt_client)
158
158
 
159
- if options[:iface_type] == :public_network
160
- return 'public'
161
- end
159
+ return 'public' if options[:iface_type] == :public_network
162
160
 
163
161
  if options[:ip]
164
162
  address = network_address(options[:ip], options[:netmask])
@@ -100,8 +100,10 @@ module VagrantPlugins
100
100
  # match what was configured in the vagrantfile
101
101
  # since we always enable dhcp for the management network
102
102
  # this ensures we wont start a vm vagrant cant reach
103
+ # Allow the situation where DHCP is not requested (:libvirt__dhcp_enabled == false)
104
+ # but where it is enabled on the virtual network
103
105
  def verify_dhcp
104
- unless @options[:dhcp_enabled] == @interface_network[:dhcp_enabled]
106
+ if @interface_network[:dhcp_enabled] == true && @options[:dhcp_enabled] == false
105
107
  raise Errors::DHCPMismatch,
106
108
  network_name: @interface_network[:name],
107
109
  requested: @options[:dhcp_enabled] ? 'enabled' : 'disabled'
@@ -35,7 +35,7 @@ module VagrantPlugins
35
35
  config = env[:machine].provider_config
36
36
  box_image_file = env[:machine].box.directory.join('box.img').to_s
37
37
  env[:box_volume_name] = env[:machine].box.name.to_s.dup.gsub("/", "-VAGRANTSLASH-")
38
- env[:box_volume_name] << '_vagrant_box_image.img'
38
+ env[:box_volume_name] << "_vagrant_box_image_#{env[:machine].box.version.to_s rescue ''}.img"
39
39
 
40
40
  @@lock.synchronize do
41
41
  # Don't continue if image already exists in storage pool.
@@ -47,6 +47,7 @@ module VagrantPlugins
47
47
  env[:ui].info(I18n.t('vagrant_libvirt.uploading_volume'))
48
48
 
49
49
  # Create new volume in storage pool
50
+ raise Errors::BoxNotFound if !File.exists?(box_image_file)
50
51
  box_image_size = File.size(box_image_file) # B
51
52
  message = "Creating volume #{env[:box_volume_name]}"
52
53
  message << " in storage pool #{config.storage_pool_name}."
@@ -0,0 +1,42 @@
1
+ require "log4r"
2
+
3
+ module VagrantPlugins
4
+ module ProviderLibvirt
5
+ module Action
6
+ class ReadMacAddresses
7
+ def initialize(app, env)
8
+ @app = app
9
+ @logger = Log4r::Logger.new("vagrant_libvirt::action::read_mac_addresses")
10
+ end
11
+
12
+ def call(env)
13
+ env[:machine_mac_addresses] = read_mac_addresses(env[:libvirt_compute], env[:machine])
14
+ end
15
+
16
+ def read_mac_addresses(libvirt, machine)
17
+ return nil if machine.id.nil?
18
+
19
+ domain = libvirt.client.lookup_domain_by_uuid(machine.id)
20
+
21
+ if domain.nil?
22
+ @logger.info("Machine could not be found, assuming it got destroyed")
23
+ machine.id = nil
24
+ return nil
25
+ end
26
+
27
+ xml = Nokogiri::XML(domain.xml_desc)
28
+ mac = xml.xpath("/domain/devices/interface/mac/@address")
29
+
30
+ if mac.length == 0
31
+ return {}
32
+ end
33
+
34
+ Hash[mac.each_with_index.map do |x,i|
35
+ @logger.debug("interface[#{i}] = #{x.value}")
36
+ [i,x.value]
37
+ end]
38
+ end
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,11 @@
1
+ module VagrantPlugins
2
+ module ProviderLibvirt
3
+ module Cap
4
+ class NicMacAddresses
5
+ def self.nic_mac_addresses(machine)
6
+ machine.provider.mac_addresses
7
+ end
8
+ end
9
+ end
10
+ end
11
+ end
@@ -55,6 +55,7 @@ module VagrantPlugins
55
55
  attr_accessor :memory
56
56
  attr_accessor :cpus
57
57
  attr_accessor :cpu_mode
58
+ attr_accessor :machine_type
58
59
  attr_accessor :disk_bus
59
60
  attr_accessor :nic_model_type
60
61
  attr_accessor :nested
@@ -69,9 +70,11 @@ module VagrantPlugins
69
70
  attr_accessor :graphics_ip
70
71
  attr_accessor :video_type
71
72
  attr_accessor :video_vram
73
+ attr_accessor :keymap
72
74
 
73
75
  # Storage
74
76
  attr_accessor :disks
77
+ attr_accessor :cdroms
75
78
 
76
79
  def initialize
77
80
  @uri = UNSET_VALUE
@@ -91,6 +94,7 @@ module VagrantPlugins
91
94
  @memory = UNSET_VALUE
92
95
  @cpus = UNSET_VALUE
93
96
  @cpu_mode = UNSET_VALUE
97
+ @machine_type = UNSET_VALUE
94
98
  @disk_bus = UNSET_VALUE
95
99
  @nic_model_type = UNSET_VALUE
96
100
  @nested = UNSET_VALUE
@@ -105,13 +109,14 @@ module VagrantPlugins
105
109
  @graphics_passwd = UNSET_VALUE
106
110
  @video_type = UNSET_VALUE
107
111
  @video_vram = UNSET_VALUE
112
+ @keymap = UNSET_VALUE
108
113
 
109
114
  # Storage
110
- @disks = UNSET_VALUE
115
+ @disks = []
116
+ @cdroms = []
111
117
  end
112
118
 
113
119
  def _get_device(disks)
114
- disks = [] if disks == UNSET_VALUE
115
120
  # skip existing devices and also the first one (vda)
116
121
  exist = disks.collect {|x| x[:device]}+[1.vdev.to_s]
117
122
  skip = 1 # we're 1 based, not 0 based...
@@ -124,8 +129,62 @@ module VagrantPlugins
124
129
  end
125
130
  end
126
131
 
132
+ def _get_cdrom_dev(cdroms)
133
+ exist = Hash[cdroms.collect{|x| [x[:dev],true]}]
134
+ # hda - hdc
135
+ curr = "a".ord
136
+ while curr <= "d".ord
137
+ dev = "hd" + curr.chr
138
+ if exist[dev]
139
+ curr += 1
140
+ next
141
+ else
142
+ return dev
143
+ end
144
+ end
145
+
146
+ # is it better to raise our own error, or let libvirt cause the exception?
147
+ raise "Only four cdroms may be attached at a time"
148
+ end
149
+
127
150
  # NOTE: this will run twice for each time it's needed- keep it idempotent
128
151
  def storage(storage_type, options={})
152
+ if storage_type == :file
153
+ if options[:device] == :cdrom
154
+ _handle_cdrom_storage(options)
155
+ else
156
+ _handle_disk_storage(options)
157
+ end
158
+ end
159
+ end
160
+
161
+ def _handle_cdrom_storage(options={})
162
+ # <disk type="file" device="cdrom">
163
+ # <source file="/home/user/virtio-win-0.1-100.iso"/>
164
+ # <target dev="hdc"/>
165
+ # <readonly/>
166
+ # <address type='drive' controller='0' bus='1' target='0' unit='0'/>
167
+ # </disk>
168
+ #
169
+ # note the target dev will need to be changed with each cdrom drive (hdc, hdd, etc),
170
+ # as will the address unit number (unit=0, unit=1, etc)
171
+
172
+ options = {
173
+ :dev => self._get_cdrom_dev(@cdroms),
174
+ :bus => "ide",
175
+ :path => nil,
176
+ }.merge(options)
177
+
178
+ cdrom = {
179
+ :dev => options[:dev],
180
+ :bus => options[:bus],
181
+ :path => options[:path]
182
+ }
183
+
184
+ @cdroms << cdrom
185
+ end
186
+
187
+ def _handle_disk_storage(options={})
129
188
  options = {
130
189
  :device => _get_device(@disks),
131
190
  :type => 'qcow2',
@@ -134,9 +193,6 @@ module VagrantPlugins
134
193
  :bus => 'virtio'
135
194
  }.merge(options)
136
195
 
137
- #puts "storage(#{storage_type} --- #{options.to_s})"
138
- @disks = [] if @disks == UNSET_VALUE
139
-
140
196
  disk = {
141
197
  :device => options[:device],
142
198
  :type => options[:type],
@@ -146,9 +202,7 @@ module VagrantPlugins
146
202
  :cache => options[:cache] || 'default',
147
203
  }
148
204
 
149
- if storage_type == :file
150
- @disks << disk # append
151
- end
205
+ @disks << disk # append
152
206
  end
153
207
 
154
208
  # code to generate URI from a config moved out of the connect action
@@ -191,8 +245,10 @@ module VagrantPlugins
191
245
 
192
246
  if @id_ssh_key_file
193
247
  # set ssh key for access to libvirt host
194
- home_dir = `echo ${HOME}`.chomp
195
- uri << "\&keyfile=#{home_dir}/.ssh/"+@id_ssh_key_file
248
+ uri << "\&keyfile="
249
+ # if no slash, prepend $HOME/.ssh/
250
+ uri << "#{`echo ${HOME}`.chomp}/.ssh/" if @id_ssh_key_file !~ /\A\//
251
+ uri << @id_ssh_key_file
196
252
  end
197
253
  # set path to libvirt socket
198
254
  uri << "\&socket="+@socket if @socket
@@ -219,6 +275,7 @@ module VagrantPlugins
219
275
  @memory = 512 if @memory == UNSET_VALUE
220
276
  @cpus = 1 if @cpus == UNSET_VALUE
221
277
  @cpu_mode = 'host-model' if @cpu_mode == UNSET_VALUE
278
+ @machine_type = nil if @machine_type == UNSET_VALUE
222
279
  @disk_bus = 'virtio' if @disk_bus == UNSET_VALUE
223
280
  @nic_model_type = 'virtio' if @nic_model_type == UNSET_VALUE
224
281
  @nested = false if @nested == UNSET_VALUE
@@ -237,9 +294,11 @@ module VagrantPlugins
237
294
  @graphics_ip = '127.0.0.1' if @graphics_ip == UNSET_VALUE
238
295
  @video_type = 'cirrus' if @video_type == UNSET_VALUE
239
296
  @video_vram = 9216 if @video_vram == UNSET_VALUE
297
+ @keymap = 'en-us' if @keymap == UNSET_VALUE
240
298
 
241
299
  # Storage
242
300
  @disks = [] if @disks == UNSET_VALUE
301
+ @cdroms = [] if @cdroms == UNSET_VALUE
243
302
  end
244
303
 
245
304
  def validate(machine)
@@ -254,7 +313,13 @@ module VagrantPlugins
254
313
  { "Libvirt Provider" => errors }
255
314
  end
256
315
 
316
+ def merge(other)
317
+ super.tap do |result|
318
+ c = disks.dup
319
+ c += other.disks
320
+ result.disks = c
321
+ end
322
+ end
257
323
  end
258
324
  end
259
325
  end
260
-
@@ -7,6 +7,11 @@ module VagrantPlugins
7
7
  error_namespace('vagrant_libvirt.errors')
8
8
  end
9
9
 
10
+ # package not supported
11
+ class PackageNotSupported < VagrantLibvirtError
12
+ error_key(:package_not_supported)
13
+ end
14
+
10
15
  # Storage pools and volumes exceptions
11
16
  class NoStoragePool < VagrantLibvirtError
12
17
  error_key(:no_storage_pool)
@@ -37,6 +37,11 @@ module VagrantPlugins
37
37
  Cap::MountP9
38
38
  end
39
39
 
40
+ provider_capability(:libvirt, :nic_mac_addresses) do
41
+ require_relative "cap/nic_mac_addresses"
42
+ Cap::NicMacAddresses
43
+ end
44
+
40
45
  # lower priority than nfs or rsync
41
46
  # https://github.com/pradels/vagrant-libvirt/pull/170
42
47
  synced_folder("9p", 4) do
@@ -49,6 +49,18 @@ module VagrantPlugins
49
49
  env[:machine_ssh_info]
50
50
  end
51
51
 
52
+ def mac_addresses
53
+ # Run a custom action called "read_mac_addresses" which will return
54
+ # a list of mac addresses used by the machine. The returned data will
55
+ # be in the following format:
56
+ #
57
+ # {
58
+ # <ADAPTER_ID>: <MAC>
59
+ # }
60
+ env = @machine.action('read_mac_addresses')
61
+ env[:machine_mac_addresses]
62
+ end
63
+
52
64
  # This should return the state of the machine within this provider.
53
65
  # The state must be an instance of {MachineState}.
54
66
  def state
@@ -14,7 +14,11 @@
14
14
  <% end %>
15
15
 
16
16
  <os>
17
+ <% if @machine_type %>
18
+ <type machine='<%= @machine_type %>'>hvm</type>
19
+ <% else %>
17
20
  <type>hvm</type>
21
+ <% end %>
18
22
  <boot dev='hd'/>
19
23
  <kernel><%= @kernel %></kernel>
20
24
  <initrd><%= @initrd %></initrd>
@@ -44,6 +48,15 @@
44
48
  -%>
45
49
  </disk>
46
50
  <% end -%>
51
+
52
+ <% @cdroms.each do |c| %>
53
+ <disk type='file' device='cdrom'>
54
+ <source file='<%= c[:path] %>'/>
55
+ <target dev='<%= c[:dev] %>' bus='<%= c[:bus] %>'/>
56
+ <readonly/>
57
+ </disk>
58
+ <% end %>
59
+
47
60
  <serial type='pty'>
48
61
  <target port='0'/>
49
62
  </serial>
@@ -52,7 +65,7 @@
52
65
  </console>
53
66
  <input type='mouse' bus='ps2'/>
54
67
  <%# Video device -%>
55
- <graphics type='<%= @graphics_type %>' port='<%= @graphics_port %>' autoport='<%= @graphics_autoport %>' listen='<%= @graphics_ip %>' keymap='en-us' <%= @graphics_passwd%> />
68
+ <graphics type='<%= @graphics_type %>' port='<%= @graphics_port %>' autoport='<%= @graphics_autoport %>' listen='<%= @graphics_ip %>' keymap='<%= @keymap %>' <%= @graphics_passwd%> />
56
69
  <video>
57
70
  <model type='<%= @video_type %>' vram='<%= @video_vram %>' heads='1'/>
58
71
  </video>
@@ -2,7 +2,7 @@
2
2
  <name><%= @network_name %></name>
3
3
  <bridge name="<%= @network_bridge_name %>" />
4
4
 
5
- <% if @network_forward_mode != 'none' %>
5
+ <% if (@network_forward_mode != 'none' && @network_forward_mode != 'veryisolated') %>
6
6
  <% if @network_forward_device %>
7
7
  <forward mode="<%= @network_forward_mode %>" dev="<%= @network_forward_device %>" />
8
8
  <% else %>
@@ -10,12 +10,14 @@
10
10
  <% end %>
11
11
  <% end %>
12
12
 
13
- <ip address="<%= @network_address %>" netmask="<%= @network_netmask %>">
14
- <% if @network_dhcp_enabled %>
15
- <dhcp>
16
- <range start="<%= @network_range_start %>" end="<%= @network_range_stop %>" />
17
- </dhcp>
13
+ <% if @network_forward_mode != 'veryisolated' %>
14
+ <ip address="<%= @network_address %>" netmask="<%= @network_netmask %>">
15
+ <% if @network_dhcp_enabled %>
16
+ <dhcp>
17
+ <range start="<%= @network_range_start %>" end="<%= @network_range_stop %>" />
18
+ </dhcp>
19
+ <% end %>
20
+ </ip>
18
21
  <% end %>
19
- </ip>
20
22
 
21
23
  </network>
@@ -1,5 +1,5 @@
1
1
  module VagrantPlugins
2
2
  module ProviderLibvirt
3
- VERSION = '0.0.25'
3
+ VERSION = '0.0.26'
4
4
  end
5
5
  end
data/locales/en.yml CHANGED
@@ -46,6 +46,7 @@ en:
46
46
  Machine is booted and ready for use!
47
47
 
48
48
  errors:
49
+ package_not_supported: Not support package for libvirt. Create box manualy.
49
50
  fog_error: |-
50
51
  There was an error talking to Libvirt. The error message is shown
51
52
  below:
@@ -11,6 +11,20 @@ class EnvironmentHelper
11
11
  self.send(value.to_sym)
12
12
  end
13
13
 
14
+ def cpus
15
+ 4
16
+ end
17
+
18
+ def memory
19
+ 1024
20
+ end
21
+
22
+ %w(cpus cpu_mode machine_type disk_bus nested volume_cache kernel cmd_line initrd graphics_type graphics_autoport graphics_port graphics_ip graphics_passwd video_type video_vram keymap storage_pool_name disks cdroms driver).each do |name|
23
+ define_method(name.to_sym) do
24
+ nil
25
+ end
26
+ end
27
+
14
28
  def machine
15
29
  self
16
30
  end
@@ -10,12 +10,12 @@ describe VagrantPlugins::ProviderLibvirt::Action::SetNameOfDomain do
10
10
  dmn = VagrantPlugins::ProviderLibvirt::Action::SetNameOfDomain.new(Object.new, @env)
11
11
  first = dmn.build_domain_name(@env)
12
12
  second = dmn.build_domain_name(@env)
13
- first.should_not eq(second)
13
+ first.should_not eq(second)
14
14
  end
15
15
 
16
16
  it "builds simple domain name" do
17
17
  @env.default_prefix= 'pre'
18
18
  dmn = VagrantPlugins::ProviderLibvirt::Action::SetNameOfDomain.new(Object.new, @env)
19
- dmn.build_domain_name(@env).should eq('pre_')
19
+ dmn.build_domain_name(@env).should eq('pre_')
20
20
  end
21
21
  end
@@ -0,0 +1,115 @@
1
+ #!/usr/bin/env bash
2
+ #set -xu
3
+
4
+ error() {
5
+ local msg="${1}"
6
+ echo "==> ${msg}"
7
+ exit 1
8
+ }
9
+
10
+ usage() {
11
+ echo "Usage: ${0} IMAGE [BOX]"
12
+ echo
13
+ echo "Package a qcow2 image into a vagrant-libvirt reusable box"
14
+ }
15
+
16
+ # Print the image's backing file
17
+ backing(){
18
+ local img=${1}
19
+ qemu-img info "$img" | grep 'backing file:' | cut -d ':' -f2
20
+ }
21
+
22
+ # Rebase the image
23
+ rebase(){
24
+ local img=${1}
25
+ qemu-img rebase -p -b "" "$img"
26
+ [[ "$?" -ne 0 ]] && error "Error during rebase"
27
+ }
28
+
29
+ # Is absolute path
30
+ isabspath(){
31
+ local path=${1}
32
+ [[ "$path" =~ ^/.* ]]
33
+ }
34
+
35
+ if [ -z "$1" ]; then
36
+ usage
37
+ exit 1
38
+ fi
39
+
40
+ IMG=$(readlink -e "$1")
41
+ [[ "$?" -ne 0 ]] && error "'$1': No such image"
42
+
43
+ IMG_DIR=$(dirname "$IMG")
44
+ IMG_BASENAME=$(basename "$IMG")
45
+
46
+ BOX=${2:-}
47
+ # If no box name is supplied infer one from image name
48
+ if [[ -z "$BOX" ]]; then
49
+ BOX_NAME=${IMG_BASENAME%.*}
50
+ BOX=$BOX_NAME.box
51
+ else
52
+ BOX_NAME=$(basename "${BOX%.*}")
53
+ fi
54
+
55
+ [[ -f "$BOX" ]] && error "'$BOX': Already exists"
56
+
57
+ CWD=$(pwd)
58
+ TMP_DIR="$CWD/_tmp_package"
59
+ TMP_IMG="$TMP_DIR/box.img"
60
+
61
+ mkdir -p "$TMP_DIR"
62
+
63
+ [[ ! -w "$IMG" ]] && error "'$IMG': Permission denied"
64
+
65
+ # We move / copy (when the image has master) the image to the tempdir
66
+ # ensure that it's moved back / removed again
67
+ if [[ -n $(backing "$IMG") ]]; then
68
+ echo "==> Image has backing image, copying image and rebasing ..."
69
+ trap "rm -rf $TMP_DIR" EXIT
70
+ cp "$IMG" "$TMP_IMG"
71
+ rebase "$TMP_IMG"
72
+ else
73
+ # move the image to get a speed-up and use less space on disk
74
+ trap 'mv "$TMP_IMG" "$IMG"; rm -rf "$TMP_DIR"' EXIT
75
+ mv "$IMG" "$TMP_IMG"
76
+ fi
77
+
78
+ cd "$TMP_DIR"
79
+
80
+ IMG_SIZE=$(qemu-img info "$TMP_IMG" | grep 'virtual size' | awk '{print $3;}' | tr -d 'G')
81
+
82
+ cat > metadata.json <<EOF
83
+ {
84
+ "provider": "libvirt",
85
+ "format": "qcow2",
86
+ "virtual_size": ${IMG_SIZE}
87
+ }
88
+ EOF
89
+
90
+ cat > Vagrantfile <<EOF
91
+ Vagrant.configure("2") do |config|
92
+
93
+ config.vm.provider :libvirt do |libvirt|
94
+
95
+ libvirt.driver = "kvm"
96
+ libvirt.host = ""
97
+ libvirt.connect_via_ssh = false
98
+ libvirt.storage_pool_name = "default"
99
+
100
+ end
101
+ end
102
+ EOF
103
+
104
+ echo "==> Creating box, tarring and gzipping"
105
+
106
+ tar cvzf "$BOX" --totals ./metadata.json ./Vagrantfile ./box.img
107
+
108
+ # if box is in tmpdir move it to CWD before removing tmpdir
109
+ if ! isabspath "$BOX"; then
110
+ mv "$BOX" "$CWD"
111
+ fi
112
+
113
+ echo "==> ${BOX} created"
114
+ echo "==> You can now add the box:"
115
+ echo "==> 'vagrant box add ${BOX} --name ${BOX_NAME}'"
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: vagrant-libvirt
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.25
4
+ version: 0.0.26
5
5
  platform: ruby
6
6
  authors:
7
7
  - Lukas Stanek
@@ -10,7 +10,7 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2015-03-04 00:00:00.000000000 Z
13
+ date: 2015-04-15 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: rspec-core
@@ -151,6 +151,7 @@ files:
151
151
  - lib/vagrant-libvirt/action/prepare_nfs_settings.rb
152
152
  - lib/vagrant-libvirt/action/prepare_nfs_valid_ids.rb
153
153
  - lib/vagrant-libvirt/action/prune_nfs_exports.rb
154
+ - lib/vagrant-libvirt/action/read_mac_addresses.rb
154
155
  - lib/vagrant-libvirt/action/read_ssh_info.rb
155
156
  - lib/vagrant-libvirt/action/read_state.rb
156
157
  - lib/vagrant-libvirt/action/resume_domain.rb
@@ -160,6 +161,7 @@ files:
160
161
  - lib/vagrant-libvirt/action/suspend_domain.rb
161
162
  - lib/vagrant-libvirt/action/wait_till_up.rb
162
163
  - lib/vagrant-libvirt/cap/mount_p9.rb
164
+ - lib/vagrant-libvirt/cap/nic_mac_addresses.rb
163
165
  - lib/vagrant-libvirt/cap/synced_folder.rb
164
166
  - lib/vagrant-libvirt/config.rb
165
167
  - lib/vagrant-libvirt/errors.rb
@@ -183,6 +185,7 @@ files:
183
185
  - spec/spec_helper.rb
184
186
  - spec/support/environment_helper.rb
185
187
  - spec/vagrant-libvirt/action/set_name_of_domain_spec.rb
188
+ - tools/create_box.sh
186
189
  - tools/prepare_redhat_for_box.sh
187
190
  - vagrant-libvirt.gemspec
188
191
  homepage: https://github.com/pradels/vagrant-libvirt
@@ -205,7 +208,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
205
208
  version: '0'
206
209
  requirements: []
207
210
  rubyforge_project:
208
- rubygems_version: 2.2.0
211
+ rubygems_version: 2.4.6
209
212
  signing_key:
210
213
  specification_version: 4
211
214
  summary: libvirt provider for Vagrant.