mirror of
https://github.com/vagrant-libvirt/vagrant-libvirt.git
synced 2025-02-25 18:55:27 -06:00
Restore handling of disk_device domain setting (#1365)
Re-enable handling of the disk_device domain volume setting to ensure it can be overridden from the default of vda to a value chosen. Provide a disk resolver to resolve devices after the box has been downloaded so that initial devices can be correctly allocated and avoid conflicts with additional disks added that would otherwise get assigned the same device. Removes hack for destroy domain when more than one disk, as now devices in the config are only present if provided by the configuration. Fixes: #1353
This commit is contained in:
parent
f8eff3d7a9
commit
91401a6559
@ -2,6 +2,8 @@
|
||||
|
||||
require 'log4r'
|
||||
|
||||
require 'vagrant-libvirt/util/resolvers'
|
||||
|
||||
module VagrantPlugins
|
||||
module ProviderLibvirt
|
||||
module Action
|
||||
@ -140,6 +142,8 @@ module VagrantPlugins
|
||||
|
||||
@os_type = 'hvm'
|
||||
|
||||
resolver = ::VagrantPlugins::ProviderLibvirt::Util::DiskDeviceResolver.new(prefix=@disk_device[0..1])
|
||||
|
||||
# Get path to domain image from the storage pool selected if we have a box.
|
||||
if env[:machine].config.vm.box
|
||||
if @snapshot_pool_name != @storage_pool_name
|
||||
@ -147,6 +151,12 @@ module VagrantPlugins
|
||||
else
|
||||
pool_name = @storage_pool_name
|
||||
end
|
||||
|
||||
# special handling for domain volume
|
||||
env[:box_volumes][0][:device] = env[:box_volumes][0].fetch(:device, @disk_device)
|
||||
|
||||
resolver.resolve!(env[:box_volumes])
|
||||
|
||||
@logger.debug "Search for volumes in pool: #{pool_name}"
|
||||
env[:box_volumes].each_index do |index|
|
||||
suffix_index = index > 0 ? "_#{index}" : ''
|
||||
@ -154,14 +164,16 @@ module VagrantPlugins
|
||||
name: "#{@name}#{suffix_index}.img"
|
||||
).find { |x| x.pool_name == pool_name }
|
||||
raise Errors::DomainVolumeExists if domain_volume.nil?
|
||||
|
||||
@domain_volumes.push({
|
||||
:dev => (index+1).vdev.to_s,
|
||||
:dev => env[:box_volumes][index][:device],
|
||||
:cache => @domain_volume_cache,
|
||||
:bus => @disk_bus,
|
||||
:path => domain_volume.path,
|
||||
:virtual_size => env[:box_volumes][index][:virtual_size]
|
||||
})
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
# If we have a box, take the path from the domain volume and set our storage_prefix.
|
||||
@ -173,19 +185,7 @@ module VagrantPlugins
|
||||
storage_prefix = get_disk_storage_prefix(env, @storage_pool_name)
|
||||
end
|
||||
|
||||
@serials = config.serials
|
||||
|
||||
@serials.each do |serial|
|
||||
next unless serial[:source] && serial[:source][:path]
|
||||
|
||||
dir = File.dirname(serial[:source][:path])
|
||||
begin
|
||||
FileUtils.mkdir_p(dir)
|
||||
rescue ::Errno::EACCES
|
||||
raise Errors::SerialCannotCreatePathError,
|
||||
path: dir
|
||||
end
|
||||
end
|
||||
resolver.resolve!(@disks)
|
||||
|
||||
@disks.each do |disk|
|
||||
disk[:path] ||= _disk_name(@name, disk)
|
||||
@ -235,6 +235,20 @@ module VagrantPlugins
|
||||
end
|
||||
end
|
||||
|
||||
@serials = config.serials
|
||||
|
||||
@serials.each do |serial|
|
||||
next unless serial[:source] && serial[:source][:path]
|
||||
|
||||
dir = File.dirname(serial[:source][:path])
|
||||
begin
|
||||
FileUtils.mkdir_p(dir)
|
||||
rescue ::Errno::EACCES
|
||||
raise Errors::SerialCannotCreatePathError,
|
||||
path: dir
|
||||
end
|
||||
end
|
||||
|
||||
# Output the settings we're going to use to the user
|
||||
env[:ui].info(I18n.t('vagrant_libvirt.creating_domain'))
|
||||
env[:ui].info(" -- Name: #{@name}")
|
||||
@ -284,7 +298,7 @@ module VagrantPlugins
|
||||
end
|
||||
env[:ui].info(" -- Storage pool: #{@storage_pool_name}")
|
||||
@domain_volumes.each do |volume|
|
||||
env[:ui].info(" -- Image(#{volume[:device]}): #{volume[:path]}, #{volume[:virtual_size].to_GB}G")
|
||||
env[:ui].info(" -- Image(#{volume[:dev]}): #{volume[:path]}, #{volume[:virtual_size].to_GB}G")
|
||||
end
|
||||
|
||||
if not @disk_driver_opts.empty?
|
||||
|
@ -128,12 +128,7 @@ module VagrantPlugins
|
||||
else
|
||||
# otherwise fallback to find the disk by device if specified by user
|
||||
# and finally index counting with offset and hope the match is correct
|
||||
if offset > 1
|
||||
# Currently disk devices are resolved incorrectly if the box has more than one device
|
||||
# this should be solved subsequently by delaying the resolution, however for now
|
||||
# default to using offset when more than one box volume.
|
||||
domain_disk = disks_xml[offset + index]
|
||||
elsif !disk[:device].nil?
|
||||
if !disk[:device].nil?
|
||||
domain_disk = REXML::XPath.match(disks_xml, './target[@dev="' + disk[:device] + '"]').first
|
||||
domain_disk = domain_disk.parent if !domain_disk.nil?
|
||||
else
|
||||
|
@ -4,15 +4,8 @@ require 'cgi'
|
||||
|
||||
require 'vagrant'
|
||||
|
||||
class Numeric
|
||||
Alphabet = ('a'..'z').to_a
|
||||
def vdev
|
||||
s = String.new
|
||||
q = self
|
||||
(q, r = (q - 1).divmod(26)) && s.prepend(Alphabet[r]) until q.zero?
|
||||
"vd#{s}"
|
||||
end
|
||||
end
|
||||
require 'vagrant-libvirt/errors'
|
||||
require 'vagrant-libvirt/util/resolvers'
|
||||
|
||||
module VagrantPlugins
|
||||
module ProviderLibvirt
|
||||
@ -353,17 +346,6 @@ module VagrantPlugins
|
||||
@boot_order << device # append
|
||||
end
|
||||
|
||||
def _get_device(disks)
|
||||
# skip existing devices and also the first one (vda)
|
||||
exist = disks.collect { |x| x[:device] } + [1.vdev.to_s]
|
||||
skip = 1 # we're 1 based, not 0 based...
|
||||
loop do
|
||||
dev = skip.vdev # get lettered device
|
||||
return dev unless exist.include?(dev)
|
||||
skip += 1
|
||||
end
|
||||
end
|
||||
|
||||
def _get_cdrom_dev(cdroms)
|
||||
exist = Hash[cdroms.collect { |x| [x[:dev], true] }]
|
||||
# hda - hdc
|
||||
@ -914,10 +896,6 @@ module VagrantPlugins
|
||||
|
||||
# Storage
|
||||
@disks = [] if @disks == UNSET_VALUE
|
||||
@disks.map! do |disk|
|
||||
disk[:device] = _get_device(@disks) if disk[:device].nil?
|
||||
disk
|
||||
end
|
||||
@cdroms = [] if @cdroms == UNSET_VALUE
|
||||
@cdroms.map! do |cdrom|
|
||||
cdrom[:dev] = _get_cdrom_dev(@cdroms) if cdrom[:dev].nil?
|
||||
@ -998,7 +976,6 @@ module VagrantPlugins
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
machine.provider_config.disks.each do |disk|
|
||||
if disk[:path] && (disk[:path][0] == '/')
|
||||
errors << "absolute volume paths like '#{disk[:path]}' not yet supported"
|
||||
@ -1011,6 +988,16 @@ module VagrantPlugins
|
||||
end
|
||||
end
|
||||
|
||||
# this won't be able to fully resolve the disks until the box has
|
||||
# been downloaded and any devices that need to be assigned to the
|
||||
# disks contained have been allocated
|
||||
disk_resolver = ::VagrantPlugins::ProviderLibvirt::Util::DiskDeviceResolver.new
|
||||
begin
|
||||
disk_resolver.resolve(machine.provider_config.disks)
|
||||
rescue Errors::VagrantLibvirtError => e
|
||||
errors << "#{e}"
|
||||
end
|
||||
|
||||
machine.config.vm.networks.each do |_type, opts|
|
||||
if opts[:mac]
|
||||
if opts[:mac] =~ /\A([0-9a-fA-F]{12})\z/
|
||||
|
@ -18,6 +18,14 @@ module VagrantPlugins
|
||||
error_key(:package_not_supported)
|
||||
end
|
||||
|
||||
class DuplicateDiskDevice < VagrantLibvirtError
|
||||
error_key(:duplicate_disk_device)
|
||||
end
|
||||
|
||||
class NoDiskDeviceAvailable < VagrantLibvirtError
|
||||
error_key(:no_disk_device_available)
|
||||
end
|
||||
|
||||
# Storage pools and volumes exceptions
|
||||
class NoStoragePool < VagrantLibvirtError
|
||||
error_key(:no_storage_pool)
|
||||
|
80
lib/vagrant-libvirt/util/resolvers.rb
Normal file
80
lib/vagrant-libvirt/util/resolvers.rb
Normal file
@ -0,0 +1,80 @@
|
||||
# frozen_string_literal: true
|
||||
|
||||
require 'log4r'
|
||||
|
||||
require 'vagrant-libvirt/errors'
|
||||
|
||||
module VagrantPlugins
|
||||
module ProviderLibvirt
|
||||
module Util
|
||||
class DiskDeviceResolver
|
||||
attr_reader :existing
|
||||
|
||||
def initialize(prefix='vd')
|
||||
@default_prefix = prefix
|
||||
|
||||
@device_indicies = Hash.new
|
||||
@existing = Hash.new
|
||||
end
|
||||
|
||||
def resolve!(disks, options={})
|
||||
# check for duplicate device entries and raise an exception if one found
|
||||
# with enough details that the user should be able to determine what
|
||||
# to do to resolve.
|
||||
disks.select { |x| !x[:device].nil? }.each do |x|
|
||||
if @existing.has_key?(x[:device])
|
||||
raise Errors::DuplicateDiskDevice, new_disk: x, existing_disk: @existing[x[:device]]
|
||||
end
|
||||
|
||||
@existing[x[:device]] = x
|
||||
end
|
||||
|
||||
disks.each_index do |index|
|
||||
dev = disks[index][:device]
|
||||
if dev.nil?
|
||||
prefix = options.fetch(:prefix, @default_prefix)
|
||||
dev = next_device(prefix=prefix)
|
||||
if dev.nil?
|
||||
raise Errors::NoDiskDeviceAvailable, prefix: prefix
|
||||
end
|
||||
|
||||
disks[index][:device] = dev
|
||||
@existing[dev] = disks[index]
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def resolve(disks)
|
||||
new_disks = []
|
||||
disks.each do |disk|
|
||||
new_disks.push disk.dup
|
||||
end
|
||||
|
||||
resolve!(new_disks)
|
||||
|
||||
new_disks
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def next_device(prefix)
|
||||
curr = device_index(prefix)
|
||||
while curr <= 'z'.ord
|
||||
dev = prefix + curr.chr
|
||||
if !@existing[dev].nil?
|
||||
curr += 1
|
||||
next
|
||||
else
|
||||
@device_indicies[prefix] = curr
|
||||
return dev
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def device_index(prefix)
|
||||
@device_indicies[prefix] ||= 'a'.ord
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
@ -81,6 +81,8 @@ en:
|
||||
errors:
|
||||
call_chain_error: Invalid action chain, must ensure that '%{require_action}' is called prior to calling '%{current_action}'
|
||||
package_not_supported: No support for package with Libvirt. Create box manually.
|
||||
duplicate_disk_device: Disk with details '%{new_disk}' duplicates :device attribute of disk '%{existing_disk}'
|
||||
no_disk_device_available: All available devices allocated under '%{prefix}x', try a different type
|
||||
fog_error: |-
|
||||
There was an error talking to Libvirt. The error message is shown
|
||||
below:
|
||||
|
@ -33,7 +33,6 @@ describe VagrantPlugins::ProviderLibvirt::Action::CreateDomain do
|
||||
allow(connection).to receive(:volumes).and_return(volumes)
|
||||
allow(volumes).to receive(:all).and_return([domain_volume])
|
||||
allow(domain_volume).to receive(:pool_name).and_return('default')
|
||||
allow(domain_volume).to receive(:[]).with('name').and_return('vagrant-test_default.img')
|
||||
allow(domain_volume).to receive(:path).and_return('/var/lib/libvirt/images/vagrant-test_default.img')
|
||||
allow(machine).to receive_message_chain("box.name") { 'vagrant-libvirt/test' }
|
||||
|
||||
@ -117,6 +116,48 @@ describe VagrantPlugins::ProviderLibvirt::Action::CreateDomain do
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context 'with custom disk device setting' do
|
||||
let(:domain_xml_file) { 'custom_disk_settings.xml' }
|
||||
let(:vagrantfile_providerconfig) {
|
||||
<<-EOF
|
||||
libvirt.disk_device = 'sda'
|
||||
EOF
|
||||
}
|
||||
|
||||
it 'should set the domain device' do
|
||||
expect(ui).to receive(:info).with(/ -- Image\(sda\):.*/)
|
||||
expect(servers).to receive(:create).with(xml: domain_xml).and_return(machine)
|
||||
|
||||
expect(subject.call(env)).to be_nil
|
||||
end
|
||||
end
|
||||
|
||||
context 'with two domain disks' do
|
||||
let(:domain_xml_file) { 'two_disk_settings.xml' }
|
||||
let(:domain_volume_2) { double('domain_volume 2') }
|
||||
|
||||
before do
|
||||
expect(volumes).to receive(:all).and_return([domain_volume])
|
||||
expect(volumes).to receive(:all).and_return([domain_volume_2])
|
||||
expect(domain_volume_2).to receive(:pool_name).and_return('default')
|
||||
expect(domain_volume_2).to receive(:path).and_return('/var/lib/libvirt/images/vagrant-test_default_1.img')
|
||||
|
||||
env[:box_volumes].push({
|
||||
:path=>"/test/box_1.img",
|
||||
:name=>"test_vagrant_box_image_1.1.1_1.img",
|
||||
:virtual_size=> ByteNumber.new(5),
|
||||
})
|
||||
end
|
||||
|
||||
it 'should correctly assign device entries' do
|
||||
expect(ui).to receive(:info).with(/ -- Image\(vda\):.*/)
|
||||
expect(ui).to receive(:info).with(/ -- Image\(vdb\):.*/)
|
||||
expect(servers).to receive(:create).with(xml: domain_xml).and_return(machine)
|
||||
|
||||
expect(subject.call(env)).to be_nil
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context 'no default pool' do
|
||||
|
55
spec/unit/action/create_domain_spec/custom_disk_settings.xml
Normal file
55
spec/unit/action/create_domain_spec/custom_disk_settings.xml
Normal file
@ -0,0 +1,55 @@
|
||||
<domain type='kvm' xmlns:qemu='http://libvirt.org/schemas/domain/qemu/1.0'>
|
||||
<name>vagrant-test_default</name>
|
||||
<title></title>
|
||||
<description>Source: /rootpath/Vagrantfile</description>
|
||||
<uuid></uuid>
|
||||
<memory>524288</memory>
|
||||
<vcpu>1</vcpu>
|
||||
|
||||
|
||||
<cpu mode='host-model'>
|
||||
<model fallback='allow'></model>
|
||||
</cpu>
|
||||
|
||||
|
||||
<os>
|
||||
<type>hvm</type>
|
||||
<kernel></kernel>
|
||||
<initrd></initrd>
|
||||
<cmdline></cmdline>
|
||||
</os>
|
||||
<features>
|
||||
<acpi/>
|
||||
<apic/>
|
||||
<pae/>
|
||||
</features>
|
||||
<clock offset='utc'>
|
||||
</clock>
|
||||
<devices>
|
||||
<disk type='file' device='disk'>
|
||||
<alias name='ua-box-volume-0'/>
|
||||
<driver name='qemu' type='qcow2' cache='default'/>
|
||||
<source file='/var/lib/libvirt/images/vagrant-test_default.img'/>
|
||||
<target dev='sda' bus='virtio'/>
|
||||
</disk>
|
||||
|
||||
|
||||
<serial type='pty'>
|
||||
<target port='0'/>
|
||||
</serial>
|
||||
<console type='pty'>
|
||||
<target port='0'/>
|
||||
</console>
|
||||
|
||||
|
||||
<input type='mouse' bus='ps2'/>
|
||||
|
||||
<graphics type='vnc' port='-1' autoport='yes' listen='127.0.0.1' keymap='en-us' />
|
||||
<video>
|
||||
<model type='cirrus' vram='9216' heads='1'/>
|
||||
</video>
|
||||
|
||||
|
||||
</devices>
|
||||
|
||||
</domain>
|
61
spec/unit/action/create_domain_spec/two_disk_settings.xml
Normal file
61
spec/unit/action/create_domain_spec/two_disk_settings.xml
Normal file
@ -0,0 +1,61 @@
|
||||
<domain type='kvm' xmlns:qemu='http://libvirt.org/schemas/domain/qemu/1.0'>
|
||||
<name>vagrant-test_default</name>
|
||||
<title></title>
|
||||
<description>Source: /rootpath/Vagrantfile</description>
|
||||
<uuid></uuid>
|
||||
<memory>524288</memory>
|
||||
<vcpu>1</vcpu>
|
||||
|
||||
|
||||
<cpu mode='host-model'>
|
||||
<model fallback='allow'></model>
|
||||
</cpu>
|
||||
|
||||
|
||||
<os>
|
||||
<type>hvm</type>
|
||||
<kernel></kernel>
|
||||
<initrd></initrd>
|
||||
<cmdline></cmdline>
|
||||
</os>
|
||||
<features>
|
||||
<acpi/>
|
||||
<apic/>
|
||||
<pae/>
|
||||
</features>
|
||||
<clock offset='utc'>
|
||||
</clock>
|
||||
<devices>
|
||||
<disk type='file' device='disk'>
|
||||
<alias name='ua-box-volume-0'/>
|
||||
<driver name='qemu' type='qcow2' cache='default'/>
|
||||
<source file='/var/lib/libvirt/images/vagrant-test_default.img'/>
|
||||
<target dev='vda' bus='virtio'/>
|
||||
</disk>
|
||||
<disk type='file' device='disk'>
|
||||
<alias name='ua-box-volume-1'/>
|
||||
<driver name='qemu' type='qcow2' cache='default'/>
|
||||
<source file='/var/lib/libvirt/images/vagrant-test_default_1.img'/>
|
||||
<target dev='vdb' bus='virtio'/>
|
||||
</disk>
|
||||
|
||||
|
||||
<serial type='pty'>
|
||||
<target port='0'/>
|
||||
</serial>
|
||||
<console type='pty'>
|
||||
<target port='0'/>
|
||||
</console>
|
||||
|
||||
|
||||
<input type='mouse' bus='ps2'/>
|
||||
|
||||
<graphics type='vnc' port='-1' autoport='yes' listen='127.0.0.1' keymap='en-us' />
|
||||
<video>
|
||||
<model type='cirrus' vram='9216' heads='1'/>
|
||||
</video>
|
||||
|
||||
|
||||
</devices>
|
||||
|
||||
</domain>
|
@ -606,11 +606,11 @@ describe VagrantPlugins::ProviderLibvirt::Config do
|
||||
end
|
||||
|
||||
context 'without devices given' do
|
||||
it 'should merge disks with different devices assigned automatically' do
|
||||
it 'should merge disks without assigning devices automatically' do
|
||||
one.storage(:file)
|
||||
two.storage(:file)
|
||||
subject.finalize!
|
||||
expect(subject.disks).to include(include(device: 'vdb'),
|
||||
expect(subject.disks).to_not include(include(device: 'vdb'),
|
||||
include(device: 'vdc'))
|
||||
end
|
||||
end
|
||||
|
@ -59,13 +59,13 @@
|
||||
<alias name='ua-disk-volume-0'/>
|
||||
<driver name='qemu' type='qcow2' cache='default'/>
|
||||
<source file='/var/lib/libvirt/images/test-disk1.qcow2'/>
|
||||
<target dev='vdb' bus='virtio'/>
|
||||
<target dev='vdc' bus='virtio'/>
|
||||
</disk>
|
||||
<disk type='file' device='disk'>
|
||||
<alias name='ua-disk-volume-1'/>
|
||||
<driver name='qemu' type='qcow2' cache='default' io='threads' copy_on_read='on' discard='unmap' detect_zeroes='on'/>
|
||||
<source file='/var/lib/libvirt/images/test-disk2.qcow2'/>
|
||||
<target dev='vdc' bus='virtio'/>
|
||||
<target dev='vdd' bus='virtio'/>
|
||||
</disk>
|
||||
|
||||
<disk type='file' device='cdrom'>
|
||||
|
@ -59,13 +59,13 @@ describe 'templates/domain' do
|
||||
domain.disk_device = 'vda'
|
||||
domain.disk_driver(:cache => 'unsafe', :io => 'threads', :copy_on_read => 'on', :discard => 'unmap', :detect_zeroes => 'on')
|
||||
domain.domain_volumes.push({
|
||||
:dev => 1.vdev.to_s,
|
||||
:dev => 'vda',
|
||||
:cache => 'unsafe',
|
||||
:bus => domain.disk_bus,
|
||||
:path => '/var/lib/libvirt/images/test.qcow2'
|
||||
})
|
||||
domain.domain_volumes.push({
|
||||
:dev => 2.vdev.to_s,
|
||||
:dev => 'vdb',
|
||||
:cache => 'unsafe',
|
||||
:bus => domain.disk_bus,
|
||||
:path => '/var/lib/libvirt/images/test2.qcow2'
|
||||
@ -118,6 +118,13 @@ describe 'templates/domain' do
|
||||
let(:test_file) { 'domain_all_settings.xml' }
|
||||
it 'renders template' do
|
||||
domain.finalize!
|
||||
# resolving is now done during create domain, so need to recreate
|
||||
# the same behaviour before calling the template until that
|
||||
# is separated out from create domain.
|
||||
resolver = ::VagrantPlugins::ProviderLibvirt::Util::DiskDeviceResolver.new(prefix=domain.disk_device[0..1])
|
||||
resolver.resolve!(domain.domain_volumes.dup.each { |volume| volume[:device] = volume[:dev] })
|
||||
resolver.resolve!(domain.disks)
|
||||
|
||||
expect(domain.to_xml('domain')).to eq xml_expected
|
||||
end
|
||||
end
|
||||
|
116
spec/unit/util/resolvers_spec.rb
Normal file
116
spec/unit/util/resolvers_spec.rb
Normal file
@ -0,0 +1,116 @@
|
||||
# frozen_string_literal: true
|
||||
|
||||
require 'spec_helper'
|
||||
|
||||
require 'vagrant-libvirt/util/resolvers'
|
||||
|
||||
describe VagrantPlugins::ProviderLibvirt::Util::DiskDeviceResolver do
|
||||
subject { described_class.new }
|
||||
|
||||
def deep_clone_disks(disk_array)
|
||||
new_array = []
|
||||
disk_array.each do |disk|
|
||||
new_array.push disk.dup
|
||||
end
|
||||
|
||||
new_array
|
||||
end
|
||||
|
||||
describe '#resolve!' do
|
||||
context 'when using default prefix' do
|
||||
[
|
||||
[
|
||||
[{:name => 'single-disk'}],
|
||||
[{:name => 'single-disk', :device => 'vda'}],
|
||||
],
|
||||
[
|
||||
[{:name => 'disk1'}, {:name => 'disk2'}],
|
||||
[{:name => 'disk1', :device => 'vda'}, {:name => 'disk2', :device => 'vdb'}],
|
||||
],
|
||||
[
|
||||
[{:name => 'disk1'}, {:name => 'disk2', :device => 'vdc'}],
|
||||
[{:name => 'disk1', :device => 'vda'}, {:name => 'disk2', :device => 'vdc'}],
|
||||
],
|
||||
[
|
||||
[{:name => 'disk1', :device => 'sda'}, {:name => 'disk2'}],
|
||||
[{:name => 'disk1', :device => 'sda'}, {:name => 'disk2', :device => 'vda'}],
|
||||
],
|
||||
].each do |input_disks, output_disks, options={}|
|
||||
opts = {}.merge!(options)
|
||||
it "should handle inputs: #{input_disks}" do
|
||||
disks = deep_clone_disks(input_disks)
|
||||
expect(subject.resolve!(disks)).to eq(output_disks)
|
||||
expect(disks).to_not eq(input_disks)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context 'when using different default prefix' do
|
||||
let(:subject) { described_class.new('sd') }
|
||||
[
|
||||
[
|
||||
[{:name => 'single-disk'}],
|
||||
[{:name => 'single-disk', :device => 'sda'}],
|
||||
],
|
||||
[
|
||||
[{:name => 'disk1'}, {:name => 'disk2'}],
|
||||
[{:name => 'disk1', :device => 'sda'}, {:name => 'disk2', :device => 'sdb'}],
|
||||
],
|
||||
[
|
||||
[{:name => 'disk1'}, {:name => 'disk2', :device => 'vdc'}],
|
||||
[{:name => 'disk1', :device => 'sda'}, {:name => 'disk2', :device => 'vdc'}],
|
||||
],
|
||||
[
|
||||
[{:name => 'disk1', :device => 'sda'}, {:name => 'disk2'}],
|
||||
[{:name => 'disk1', :device => 'sda'}, {:name => 'disk2', :device => 'sdb'}],
|
||||
],
|
||||
[
|
||||
[{:name => 'disk1'}, {:name => 'disk2', :device => 'sda'}],
|
||||
[{:name => 'disk1', :device => 'sdb'}, {:name => 'disk2', :device => 'sda'}],
|
||||
],
|
||||
].each do |input_disks, output_disks, options={}|
|
||||
opts = {}.merge!(options)
|
||||
it "should handle inputs: #{input_disks}" do
|
||||
disks = deep_clone_disks(input_disks)
|
||||
expect(subject.resolve!(disks)).to eq(output_disks)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context 'when using custom prefix' do
|
||||
[
|
||||
[
|
||||
[{:name => 'existing-disk', :device => 'vda'}],
|
||||
[{:name => 'single-disk'}],
|
||||
[{:name => 'single-disk', :device => 'sda'}],
|
||||
{:prefix => 'sd'},
|
||||
],
|
||||
[
|
||||
[{:name => 'existing-disk', :device => 'vda'}],
|
||||
[{:name => 'disk1', :device => 'sda'}, {:name => 'disk2'}],
|
||||
[{:name => 'disk1', :device => 'sda'}, {:name => 'disk2', :device => 'sdb'}],
|
||||
{:prefix => 'sd'},
|
||||
],
|
||||
].each do |existing, input_disks, output_disks, options={}|
|
||||
opts = {}.merge!(options)
|
||||
it "should handle inputs: #{input_disks} with opts: #{opts}" do
|
||||
disks = deep_clone_disks(input_disks)
|
||||
subject.resolve(existing)
|
||||
expect(subject.resolve!(disks, opts)).to eq(output_disks)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
describe '#resolve' do
|
||||
let(:input_disks) { [{:name => 'single-disk'}] }
|
||||
let(:output_disks) { [{:name => 'single-disk', :device => 'vda'}] }
|
||||
|
||||
it "should resolve without modifying" do
|
||||
disks = deep_clone_disks(input_disks)
|
||||
expect(subject.resolve(disks)).to eq(output_disks)
|
||||
expect(disks).to_not eq(output_disks)
|
||||
expect(disks).to eq(input_disks)
|
||||
end
|
||||
end
|
||||
end
|
Loading…
Reference in New Issue
Block a user