spec/unit/action/destroy_domain_spec.rb in vagrant-libvirt-0.7.0 vs spec/unit/action/destroy_domain_spec.rb in vagrant-libvirt-0.8.0

- old
+ new

@@ -15,84 +15,188 @@ let(:driver) { double('driver') } let(:libvirt_domain) { double('libvirt_domain') } let(:libvirt_client) { double('libvirt_client') } let(:servers) { double('servers') } + let(:domain_xml) { File.read(File.join(File.dirname(__FILE__), File.basename(__FILE__, '.rb'), domain_xml_file)) } + before do allow(machine.provider).to receive('driver').and_return(driver) allow(driver).to receive(:connection).and_return(connection) + allow(logger).to receive(:info) end describe '#call' do before do allow(connection).to receive(:client).and_return(libvirt_client) allow(libvirt_client).to receive(:lookup_domain_by_uuid) .and_return(libvirt_domain) + allow(libvirt_domain).to receive(:name).and_return('vagrant-test_default') allow(connection).to receive(:servers).and_return(servers) allow(servers).to receive(:get).and_return(domain) + # always see this at the start of #call expect(ui).to receive(:info).with('Removing domain...') end context 'when no snapshots' do let(:root_disk) { double('libvirt_root_disk') } before do allow(libvirt_domain).to receive(:list_snapshots).and_return([]) allow(libvirt_domain).to receive(:has_managed_save?).and_return(nil) - allow(root_disk).to receive(:name).and_return('test.img') + allow(root_disk).to receive(:name).and_return('vagrant-test_default.img') end - context 'when only has root disk' do + context 'when box only has one root disk' do it 'calls fog to destroy volumes' do expect(domain).to receive(:destroy).with(destroy_volumes: true) expect(subject.call(env)).to be_nil end - end - context 'when has additional disks' do - let(:vagrantfile) do - <<-EOF - Vagrant.configure('2') do |config| - config.vm.define :test - config.vm.provider :libvirt do |libvirt| - libvirt.storage :file - end + context 'when has additional disks' do + let(:vagrantfile_providerconfig) do + <<-EOF + libvirt.storage :file + EOF end - EOF - end + let(:domain_xml_file) { 'additional_disks_domain.xml' } + let(:extra_disk) { double('libvirt_extra_disk') } - let(:extra_disk) { double('libvirt_extra_disk') } - before do - allow(extra_disk).to receive(:name).and_return('test-vdb.qcow2') + before do + allow(extra_disk).to receive(:name).and_return('vagrant-test_default-vdb.qcow2') + allow(domain).to receive(:volumes).and_return([root_disk, extra_disk]) + expect(libvirt_domain).to receive(:xml_desc).and_return(domain_xml) + end + + it 'destroys disks individually' do + expect(domain).to receive(:destroy).with(destroy_volumes: false) + expect(extra_disk).to receive(:destroy) # extra disk remove + expect(root_disk).to receive(:destroy) # root disk remove + expect(subject.call(env)).to be_nil + end end + end - it 'destroys disks individually' do - allow(libvirt_domain).to receive(:name).and_return('test') - allow(domain).to receive(:volumes).and_return([extra_disk], [root_disk]) + context 'when box has multiple disks' do + let(:domain_xml_file) { 'box_multiple_disks.xml' } - expect(domain).to receive(:destroy).with(destroy_volumes: false) - expect(extra_disk).to receive(:destroy) # extra disk remove - expect(root_disk).to receive(:destroy) # root disk remove + it 'calls fog to destroy volumes' do + expect(domain).to receive(:destroy).with(destroy_volumes: true) expect(subject.call(env)).to be_nil end + + context 'when has additional disks' do + let(:domain_xml_file) { 'box_multiple_disks_and_additional_disks.xml' } + let(:vagrantfile_providerconfig) do + <<-EOF + libvirt.storage :file + libvirt.storage :file + EOF + end + let(:domain_disks) {[ + [double('box-disk-1'), 'vagrant-test_default.img'], + [double('box-disk-2'), 'vagrant-test_default_1.img'], + [double('box-disk-3'), 'vagrant-test_default_2.img'], + [double('additional-disk-1'), 'vagrant-test_default-vdd.qcow2'], + [double('additional-disk-2'), 'vagrant-test_default-vde.qcow2'], + ]} + + before do + allow(libvirt_domain).to receive(:xml_desc).and_return(domain_xml) + allow(domain).to receive(:volumes).and_return(domain_disks.map { |a| a.first }) + end + + it 'destroys disks individually' do + domain_disks.each do |disk, name| + expect(disk).to receive(:name).and_return(name).at_least(:once) + expect(disk).to receive(:destroy) + end + expect(domain).to receive(:destroy).with(destroy_volumes: false) + expect(subject.call(env)).to be_nil + end + + context 'when has disks added via custom virsh commands' do + let(:domain_xml_file) { 'box_multiple_disks_and_additional_and_custom_disks.xml' } + let(:domain_disks) {[ + [double('box-disk-1'), 'vagrant-test_default.img'], + [double('box-disk-2'), 'vagrant-test_default_1.img'], + [double('box-disk-3'), 'vagrant-test_default_2.img'], + [double('additional-disk-1'), 'vagrant-test_default-vdd.qcow2'], + [double('additional-disk-2'), 'vagrant-test_default-vde.qcow2'], + [double('custom-disk-1'), 'vagrant-test_default-vdf.qcow2'], + ]} + + it 'only destroys expected disks' do + expect(ui).to receive(:warn).with(/Unexpected number of volumes detected.*/) + domain_disks.each do |disk, name| + expect(disk).to receive(:name).and_return(name).at_least(:once) + next if disk == domain_disks.last.first + expect(disk).to receive(:destroy) + end + expect(domain).to receive(:destroy).with(destroy_volumes: false) + expect(subject.call(env)).to be_nil + end + + context 'without aliases' do + let(:domain_xml_file) { 'box_multiple_disks_and_additional_and_custom_disks_no_aliases.xml' } + + it 'only destroys expected disks' do + expect(ui).to receive(:warn).with(/Destroying machine that was originally created without device aliases.*/) + expect(ui).to receive(:warn).with(/Unexpected number of volumes detected/) + expect(ui).to receive(:warn).with(/box metadata not available to get volume list during destroy, assuming inferred list/) + domain_disks.each do |disk, name| + expect(disk).to receive(:name).and_return(name).at_least(:once) + # ignore box disks 2 and 3 and the last custom disk + next if domain_disks.last.first == disk + expect(disk).to receive(:destroy) + end + expect(domain).to receive(:destroy).with(destroy_volumes: false) + expect(subject.call(env)).to be_nil + end + + context 'with box metadata' do + let(:box) { instance_double(::Vagrant::Box) } + before do + allow(env[:machine]).to receive(:box).and_return(box) + allow(box).to receive(:metadata).and_return(Hash[ + 'disks' => [ + {:name => 'box-disk-1'}, + {:name => 'box-disk-2'}, + {:name => 'box-disk-3'}, + ] + ]) + end + + it 'only destroys expected disks' do + expect(ui).to receive(:warn).with(/Destroying machine that was originally created without device aliases.*/) + expect(ui).to receive(:warn).with(/Unexpected number of volumes detected/) + domain_disks.each do |disk, name| + expect(disk).to receive(:name).and_return(name).at_least(:once) + # ignore box disks 2 and 3 and the last custom disk + next if domain_disks.last.first == disk + expect(disk).to receive(:destroy) + end + expect(domain).to receive(:destroy).with(destroy_volumes: false) + expect(subject.call(env)).to be_nil + end + end + end + end + end end context 'when has CDROMs attached' do - let(:vagrantfile) do + let(:vagrantfile_providerconfig) do <<-EOF - Vagrant.configure('2') do |config| - config.vm.define :test - config.vm.provider :libvirt do |libvirt| libvirt.storage :file, :device => :cdrom - end - end EOF end + let(:domain_xml_file) { 'cdrom_domain.xml' } it 'uses explicit removal of disks' do - allow(libvirt_domain).to receive(:name).and_return('test') - allow(domain).to receive(:volumes).and_return([root_disk, nil]) + expect(domain).to receive(:volumes).and_return([root_disk, nil]) + expect(libvirt_domain).to receive(:xml_desc).and_return(domain_xml) expect(domain).to_not receive(:destroy).with(destroy_volumes: true) expect(root_disk).to receive(:destroy) # root disk remove expect(subject.call(env)).to be_nil end