fog-libvirt 0.10.1 → 0.12.0

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b0eeb036772c096dd44785f75d40342a54ba904b25bdc1a9a4fcd6618c5e68d2
4
- data.tar.gz: 6724150fb122ed80117725f1ee72d87de38d29ba7e3b10e5da2e752d302c2b92
3
+ metadata.gz: 173406401f8c728989e70e75ae9765bffc53d84e14ae838db08576f34ba44539
4
+ data.tar.gz: 58c5ac60c88a3a2cbdca2744231f939d5a4871db89d35e4cbf7483d5a2ef638b
5
5
  SHA512:
6
- metadata.gz: e793caef5c183c003807f4d1d080575a47c0a64051ff84e76063863beae0e8bf253acf4b5dfb0054125343230578f0ce1f6e7871ca16ae249ace8b3d8c76d82e
7
- data.tar.gz: 262443398fed1548bbcec936781cddc5e5f0664f0744021db5f47ed076b245e69b7061c5bcb35ae38270314b0a64e189896b6e923309d39277abf2538b139a45
6
+ metadata.gz: 1d23624637ceb4b353a83cbd5f0b49917adf1d8dc20a471eb05bfd04259a6b39fe40f3c689278a31c13e708d9a5e599b11da7bdf67fbaec622316a2ec2ed7082
7
+ data.tar.gz: 00abab82645d5f8f9a176d2188c7e5c2d6004118f87195994a65b4ce4c949b0d3b52a23ca6dab19d4a9c83134bb8dc59742e9e81ecc41982306903b5290a32b7
data/fog-libvirt.gemspec CHANGED
@@ -36,11 +36,11 @@ Gem::Specification.new do |s|
36
36
  s.add_development_dependency("minitest-stub-const")
37
37
  s.add_development_dependency("pry")
38
38
  s.add_development_dependency("rake")
39
- s.add_development_dependency("rubocop") if RUBY_VERSION > "2.0"
39
+ s.add_development_dependency("rubocop")
40
40
  s.add_development_dependency("shindo", "~> 0.3.4")
41
41
  s.add_development_dependency("simplecov")
42
42
  s.add_development_dependency("yard")
43
- s.add_development_dependency("mocha", "~> 1.15.0")
43
+ s.add_development_dependency("mocha", ">= 1.15", "< 3")
44
44
 
45
45
  # Let's not ship dot files and gemfiles
46
46
  git_files = `git ls-files`.split("\n")
@@ -92,7 +92,7 @@ module Fog
92
92
 
93
93
  def destroy(options={ :destroy_volumes => false, :flags => 0 })
94
94
  poweroff unless stopped?
95
- if options[:flags].zero?
95
+ if options.fetch(:flags, 0).zero?
96
96
  service.vm_action(uuid, :undefine)
97
97
  else
98
98
  service.vm_action(uuid, :undefine, options[:flags])
@@ -147,7 +147,7 @@ module Fog
147
147
 
148
148
  def volumes
149
149
  # lazy loading of volumes
150
- @volumes ||= (@volumes_path || []).map{|path| service.volumes.all(:path => path).first }
150
+ @volumes ||= (@volumes_path || []).map{ |path| service.volumes.all(:path => path).first }.compact
151
151
  end
152
152
 
153
153
  def private_ip_address
@@ -267,9 +267,179 @@ module Fog
267
267
  "#{name}-cloud-init.iso"
268
268
  end
269
269
 
270
+ # rubocop:disable Metrics
271
+ def to_xml
272
+ builder = Nokogiri::XML::Builder.new do |xml|
273
+ xml.domain(:type => domain_type) do
274
+ xml.name(name)
275
+ xml.memory(memory_size)
276
+
277
+ if hugepages
278
+ xml.memoryBacking do
279
+ xml.hugepages
280
+ end
281
+ end
282
+
283
+ xml.vcpu(cpus)
284
+ xml.os do
285
+ type = xml.type(os_type, :arch => arch)
286
+ type[:machine] = "q35" if ["i686", "x86_64"].include?(arch)
287
+
288
+ boot_order.each do |dev|
289
+ xml.boot(:dev => dev)
290
+ end
291
+ end
292
+ xml.features do
293
+ xml.acpi
294
+ xml.apic
295
+ end
296
+
297
+ unless cpu.empty?
298
+ if cpu.dig(:model, :name)
299
+ xml.cpu do
300
+ xml.model(cpu.dig(:model, :name), :fallback => cpu.dig(:model, :fallback) || "allow")
301
+ end
302
+ else
303
+ xml.cpu(
304
+ :mode => cpu.dig(:model, :name) || "host-passthrough",
305
+ :check => cpu.fetch(:check, "none"),
306
+ :migratable => cpu.fetch(:migratable, "on")
307
+ )
308
+ end
309
+ end
310
+
311
+ xml.clock(:offset => "utc") do
312
+ xml.timer(:name => "rtc", :tickpolicy => "catchup")
313
+ xml.timer(:name => "pit", :tickpolicy => "delay")
314
+ xml.timer(:name => "hpet", :present => "no")
315
+ end
316
+
317
+ xml.devices do
318
+ ceph_args = read_ceph_args
319
+
320
+ volumes.each_with_index do |volume, index|
321
+ target_device = "vd#{('a'..'z').to_a[index]}"
322
+ if ceph_args && volume.pool_name.include?(ceph_args["libvirt_ceph_pool"])
323
+ xml.disk(:type => "network", :device => "disk") do
324
+ xml.driver(:name => "qemu", :type => volume.format_type, :cache => "writeback", :discard => "unmap")
325
+ xml.source(:protocol => "rbd", :name => volume.path)
326
+
327
+ ceph_args["monitor"]&.split(",")&.each do |monitor|
328
+ xml.host(:name => monitor, :port => ceph_args["port"])
329
+ end
330
+
331
+ xml.auth(:username => ceph_args["auth_username"]) do
332
+ if ceph_args.key?("auth_uuid")
333
+ xml.secret(:type => "ceph", :uuid => ceph_args["auth_uuid"])
334
+ else
335
+ xml.secret(:type => "ceph", :usage => ceph_args["auth_usage"])
336
+ end
337
+ end
338
+
339
+ xml.target(:dev => target_device, :bus => args["bus_type"] == "virtio" ? "virtio" : "scsi")
340
+ end
341
+ else
342
+ is_block = volume.path.start_with?("/dev/")
343
+ xml.disk(:type => is_block ? "block" : "file", :device => "disk") do
344
+ xml.driver(:name => "qemu", :type => volume.format_type)
345
+ if is_block
346
+ xml.source(:dev => volume.path)
347
+ else
348
+ xml.source(:file => volume.path)
349
+ end
350
+ xml.target(:dev => target_device, :bus => "virtio")
351
+ end
352
+ end
353
+ end
354
+
355
+ if iso_file
356
+ xml.disk(:type => "file", :device => "cdrom") do
357
+ xml.driver(:name => "qemu", :type => "raw")
358
+ xml.source(:file => "#{iso_dir}/#{iso_file}")
359
+ xml.target(:dev => "hdc", :bus => "ide")
360
+ xml.readonly
361
+ xml.address(:type => "drive", :controller => 0, :bus => 1, :unit => 0)
362
+ end
363
+ end
364
+
365
+ nics.each do |nic|
366
+ xml.interface(:type => nic.type) do
367
+ if nic.type == "bridge"
368
+ xml.source(:bridge => nic.bridge)
369
+ else
370
+ xml.source(:network => nic.network)
371
+ end
372
+ xml.model(:type => nic.model)
373
+ end
374
+ end
375
+
376
+ if guest_agent
377
+ xml.channel(:type => "unix") do
378
+ xml.target(:type => "virtio", :name => "org.qemu.guest_agent.0")
379
+ end
380
+ end
381
+
382
+ xml.rng(:model => "virtio") do
383
+ xml.backend(virtio_rng[:backend_path], :model => virtio_rng.fetch(:backend_model, "random"))
384
+ end
385
+
386
+ if arch == "s390x"
387
+ xml.controller(:type => "scsi", :index => "0", :model => "virtio-scsi")
388
+ xml.console(:type => "pty") do
389
+ xml.target(:type => "sclp")
390
+ end
391
+ xml.memballoon(:model => "virtio")
392
+ else
393
+ xml.serial(:type => "pty") do
394
+ xml.target(:port => 0)
395
+ end
396
+ xml.console(:type => "pty") do
397
+ xml.target(:port => 0)
398
+ end
399
+ xml.input(:type => "tablet", :bus => "usb")
400
+ xml.input(:type => "mouse", :bus => "ps2")
401
+
402
+ graphics = xml.graphics(:type => display[:type])
403
+ if display[:port].empty?
404
+ graphics.port = display[:port]
405
+ graphics.autoport = "no"
406
+ else
407
+ graphics.port = -1
408
+ graphics.autoport = "yes"
409
+ end
410
+ graphics.listen = display[:listen] unless display[:listen].empty?
411
+ graphics.password = display[:password] unless display[:password].empty?
412
+
413
+ xml.video do
414
+ xml.model(:type => "cirrus", :vram => 9216, :heads => 1)
415
+ end
416
+ end
417
+ end
418
+ end
419
+ end
420
+
421
+ builder.to_xml
422
+ end
423
+ # rubocop:enable Metrics
424
+
270
425
  private
271
426
  attr_accessor :volumes_path
272
427
 
428
+ def read_ceph_args(path = "/etc/foreman/ceph.conf")
429
+ return unless File.file?(path)
430
+
431
+ args = {}
432
+
433
+ File.readlines(path).each do |line|
434
+ pair = line.strip.split("=")
435
+ key = pair[0]
436
+ value = pair[1]
437
+ args[key] = value
438
+ end
439
+
440
+ args
441
+ end
442
+
273
443
  # This tests the library version before redefining the address
274
444
  # method for this instance to use a method compatible with
275
445
  # earlier libvirt libraries, or uses the dhcp method from more
@@ -479,7 +649,7 @@ module Fog
479
649
  {
480
650
  :persistent => true,
481
651
  :cpus => 1,
482
- :memory_size => 256 *1024,
652
+ :memory_size => 256 * 1024,
483
653
  :name => randomized_name,
484
654
  :os_type => "hvm",
485
655
  :arch => "x86_64",
@@ -39,13 +39,9 @@ module Fog
39
39
  end
40
40
 
41
41
  def domain_volumes xml
42
- vols_by_file = xml_elements(xml, "domain/devices/disk/source", "file")
43
- vols_by_name = xml_elements(xml, "domain/devices/disk/source", "name")
44
- vols = []
45
- vols_by_file.zip(vols_by_name).each do |by_file,by_name|
46
- vols.push(by_file.nil? ? by_name : by_file)
42
+ xml_elements(xml, "domain/devices/disk/source").map do |element|
43
+ element[:file] || element[:dev] || element[:name]
47
44
  end
48
- vols
49
45
  end
50
46
 
51
47
  def boot_order xml
@@ -113,7 +109,7 @@ module Fog
113
109
  :memory_size => 6,
114
110
  :cpus => 5,
115
111
  :autostart => false,
116
- :os_type => "RHEL6",
112
+ :os_type => "hvm",
117
113
  :active => false,
118
114
  :vnc_port => 5910,
119
115
  :boot_order => boot_order(xml),
@@ -1,5 +1,5 @@
1
1
  module Fog
2
2
  module Libvirt
3
- VERSION = '0.10.1'
3
+ VERSION = '0.12.0'
4
4
  end
5
5
  end
@@ -36,8 +36,8 @@ class ServerTest < Minitest::Test
36
36
  end
37
37
 
38
38
  def test_ssh_ip_command_success
39
- fog_ssh = MiniTest::Mock.new
40
- result = MiniTest::Mock.new
39
+ fog_ssh = Minitest::Mock.new
40
+ result = Minitest::Mock.new
41
41
  result.expect(:status, 0)
42
42
  result.expect(:stdout, "any_ip")
43
43
  fog_ssh.expect(:run, [result], [String])
@@ -49,10 +49,10 @@ class ServerTest < Minitest::Test
49
49
  end
50
50
 
51
51
  def test_local_ip_command_success
52
- proc_info = MiniTest::Mock.new
52
+ proc_info = Minitest::Mock.new
53
53
  proc_info.expect(:each_line, "127.0.0.1")
54
54
  proc_info.expect(:pid, 0)
55
- status = MiniTest::Mock.new
55
+ status = Minitest::Mock.new
56
56
  status.expect(:exitstatus, 0)
57
57
  Process.stubs(:waitpid2).returns([0, status])
58
58
  IO.stub(:popen, true, proc_info) do
@@ -59,5 +59,25 @@ Shindo.tests('Fog::Compute[:libvirt] | server model', ['libvirt']) do
59
59
  end
60
60
  end
61
61
  test('be a kind of Fog::Libvirt::Compute::Server') { server.kind_of? Fog::Libvirt::Compute::Server }
62
+ tests("serializes to xml") do
63
+ test("with memory") { server.to_xml.match?(%r{<memory>\d+</memory>}) }
64
+ test("with disk of type file") do
65
+ xml = server.to_xml
66
+ xml.match?(/<disk type="file" device="disk">/) && xml.match?(%r{<source file="path/to/disk"/>})
67
+ end
68
+ test("with disk of type block") do
69
+ server = Fog::Libvirt::Compute::Server.new(
70
+ {
71
+ :nics => [],
72
+ :volumes => [
73
+ Fog::Libvirt::Compute::Volume.new({ :path => "/dev/sda", :pool_name => "dummy" })
74
+ ]
75
+ }
76
+ )
77
+ xml = server.to_xml
78
+ xml.match?(/<disk type="block" device="disk">/) && xml.match?(%r{<source dev="/dev/sda"/>})
79
+ end
80
+ test("with q35 machine type on x86_64") { server.to_xml.match?(%r{<type arch="x86_64" machine="q35">hvm</type>}) }
81
+ end
62
82
  end
63
83
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: fog-libvirt
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.10.1
4
+ version: 0.12.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - geemus (Wesley Beary)
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-12-02 00:00:00.000000000 Z
11
+ date: 2023-11-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: fog-core
@@ -210,16 +210,22 @@ dependencies:
210
210
  name: mocha
211
211
  requirement: !ruby/object:Gem::Requirement
212
212
  requirements:
213
- - - "~>"
213
+ - - ">="
214
+ - !ruby/object:Gem::Version
215
+ version: '1.15'
216
+ - - "<"
214
217
  - !ruby/object:Gem::Version
215
- version: 1.15.0
218
+ version: '3'
216
219
  type: :development
217
220
  prerelease: false
218
221
  version_requirements: !ruby/object:Gem::Requirement
219
222
  requirements:
220
- - - "~>"
223
+ - - ">="
224
+ - !ruby/object:Gem::Version
225
+ version: '1.15'
226
+ - - "<"
221
227
  - !ruby/object:Gem::Version
222
- version: 1.15.0
228
+ version: '3'
223
229
  description: This library can be used as a module for 'fog' or as standalone libvirt
224
230
  provider.
225
231
  email: geemus@gmail.com
@@ -252,7 +258,6 @@ files:
252
258
  - lib/fog/libvirt/models/compute/servers.rb
253
259
  - lib/fog/libvirt/models/compute/templates/network.xml.erb
254
260
  - lib/fog/libvirt/models/compute/templates/pool.xml.erb
255
- - lib/fog/libvirt/models/compute/templates/server.xml.erb
256
261
  - lib/fog/libvirt/models/compute/templates/volume.xml.erb
257
262
  - lib/fog/libvirt/models/compute/util/uri.rb
258
263
  - lib/fog/libvirt/models/compute/util/util.rb
@@ -329,7 +334,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
329
334
  - !ruby/object:Gem::Version
330
335
  version: '0'
331
336
  requirements: []
332
- rubygems_version: 3.3.7
337
+ rubygems_version: 3.4.10
333
338
  signing_key:
334
339
  specification_version: 2
335
340
  summary: Module for the 'fog' gem to support libvirt
@@ -1,155 +0,0 @@
1
- <domain type='<%= domain_type %>'>
2
- <name><%= name %></name>
3
- <memory><%= memory_size %></memory>
4
- <% if hugepages -%>
5
- <memoryBacking>
6
- <hugepages/>
7
- </memoryBacking>
8
- <% end -%>
9
- <vcpu><%= cpus %></vcpu>
10
- <os>
11
- <type arch='<%= arch %>'><%= os_type %></type>
12
- <% boot_order.each do |dev| -%>
13
- <boot dev='<%= dev %>'/>
14
- <% end -%>
15
- </os>
16
- <features>
17
- <acpi/>
18
- <apic/>
19
- <pae/>
20
- </features>
21
- <% if !cpu.empty? -%>
22
- <% if cpu[:mode] -%>
23
- <cpu mode='<%= cpu[:mode] %>'>
24
- <% else -%>
25
- <cpu>
26
- <% end -%>
27
- <%
28
- fallback = 'allow'
29
- model = ''
30
- if cpu[:model]
31
- fallback = cpu[:model][:fallback] if cpu[:model][:fallback]
32
- model = cpu[:model][:name] if cpu[:model][:name]
33
- end
34
- -%>
35
- <model fallback='<%= fallback %>'><%= model %></model>
36
- </cpu>
37
- <% end -%>
38
- <clock offset='utc'/>
39
- <devices>
40
- <% args = {}
41
- if File.file?('/etc/foreman/ceph.conf')
42
- File.readlines('/etc/foreman/ceph.conf').each do |line|
43
- pair = line.strip.split("=")
44
- key = pair[0]
45
- value = pair[1]
46
- args[key] = value
47
- end
48
- end
49
- %>
50
- <% volumes.each do |vol| -%>
51
- <% if File.file?('/etc/foreman/ceph.conf') && vol.pool_name.include?(args["libvirt_ceph_pool"]) %>
52
- <disk type='network' device='disk'>
53
- <driver name='qemu' type='<%= vol.format_type %>' cache='writeback' discard='unmap'/>
54
- <source protocol='rbd' name='<%= vol.path %>'>
55
- <% if args.key?("monitor") -%>
56
- <% args["monitor"].split(",").each do |mon| %>
57
- <host name='<%= mon %>' port='<%= args["port"] %>'/>
58
- <% end %>
59
- <% end %>
60
- </source>
61
- <auth username='<%= args["auth_username"] %>'>
62
- <% if args.key?("auth_uuid") -%>
63
- <secret type='ceph' uuid='<%= args["auth_uuid"] %>'/>
64
- <% else -%>
65
- <secret type='ceph' usage='<%= args["auth_usage"] %>'/>
66
- <% end -%>
67
- </auth>
68
- <% if args['bus_type'] == 'virtio' %>
69
- <target dev='vd<%= ('a'..'z').to_a[volumes.index(vol)] %>' bus='virtio'/>
70
- <% else %>
71
- <target dev='sd<%= ('a'..'z').to_a[volumes.index(vol)] %>' bus='scsi'/>
72
- <% end %>
73
- </disk>
74
- <% else %>
75
- <disk type='file' device='disk'>
76
- <driver name='qemu' type='<%= vol.format_type %>'/>
77
- <source file='<%= vol.path %>'/>
78
- <%# we need to ensure a unique target dev -%>
79
- <target dev='vd<%= ('a'..'z').to_a[volumes.index(vol)] %>' bus='virtio'/>
80
- </disk>
81
- <% end %>
82
- <% end -%>
83
- <% if iso_file -%>
84
- <disk type='file' device='cdrom'>
85
- <driver name='qemu' type='raw'/>
86
- <source file='<%= "#{iso_dir}/#{iso_file}" %>'/>
87
- <target dev='hdc' bus='ide'/>
88
- <readonly/>
89
- <address type='drive' controller='0' bus='1' unit='0'/>
90
- </disk>
91
- <% end -%>
92
- <% nics.each do |nic| -%>
93
- <interface type='<%= nic.type %>'>
94
- <source <%= nic.type == 'bridge' ? "bridge='#{nic.bridge}'" : "network='#{nic.network}'" %> />
95
- <model type='<%= nic.model %>'/>
96
- </interface>
97
- <% end -%>
98
- <% if guest_agent -%>
99
- <channel type='unix'>
100
- <target type='virtio' name='org.qemu.guest_agent.0'/>
101
- </channel>
102
- <% end -%>
103
- <rng model='virtio'>
104
- <%
105
- rng_backend_model = virtio_rng[:backend_model] ? virtio_rng[:backend_model] : 'random'
106
- -%>
107
- <% if virtio_rng[:backend_path] -%>
108
- <backend model='<%= rng_backend_model %>'><%= virtio_rng[:backend_path] %></backend>
109
- <% else -%>
110
- <backend model='<%= rng_backend_model %>'/>
111
- <% end -%>
112
- </rng>
113
- <% if arch == "s390x" -%>
114
- <controller type="scsi" index="0" model="virtio-scsi"/>
115
- <console type="pty">
116
- <target type="sclp"/>
117
- </console>
118
- <memballoon model="virtio"/>
119
- <% else -%>
120
- <serial type='pty'>
121
- <target port='0'/>
122
- </serial>
123
- <console type='pty'>
124
- <target port='0'/>
125
- </console>
126
- <input type='tablet' bus='usb'/>
127
- <input type='mouse' bus='ps2'/>
128
- <% end -%>
129
- <%
130
- display_type = display[:type]
131
-
132
- if display[:port].empty?
133
- display_port = display[:port]
134
- autoport = 'no'
135
- else
136
- display_port = '-1'
137
- autoport = 'yes'
138
- end
139
-
140
- unless display[:listen].empty?
141
- display_listen = "listen='#{display[:listen]}'"
142
- end
143
-
144
- unless display[:password].empty?
145
- display_password = "passwd='#{display[:password]}'"
146
- end
147
- -%>
148
- <% if arch != "s390x" -%>
149
- <graphics type='<%= display_type %>' port='<%= display_port %>' autoport='<%= autoport %>' <%= display_listen %> <%= display_password %> />
150
- <video>
151
- <model type='cirrus' vram='9216' heads='1'/>
152
- </video>
153
- <% end -%>
154
- </devices>
155
- </domain>