Allow vios to be filtered for rebuild
During rebuild process all the active VIOS are considered as valid. In case of some powervm env a VIOS might not own any IO and is not a valid candiate for rebuild. Adding a vios_uuids method to define the valid vios for a given volume driver. This property can be used further in all the connect and disconnect operations as well. That will be done as part of a future changeset. Change-Id: I936c12a8b1fff431fcf3098aca57cedcdbf32b0b
This commit is contained in:
parent
fecc5ec0db
commit
c614c3a9a7
|
@ -121,6 +121,32 @@ class TestSwiftSlotManager(test.TestCase):
|
|||
p_exc.InvalidRebuild, self.slot_mgr.init_recreate_map, mock.Mock(),
|
||||
self._vol_drv_iter())
|
||||
|
||||
@mock.patch('pypowervm.tasks.slot_map.RebuildSlotMap')
|
||||
@mock.patch('pypowervm.tasks.storage.ComprehensiveScrub')
|
||||
def test_init_recreate_map_fileio(self, mock_ftsk, mock_rebuild_slot):
|
||||
vios1, vios2 = mock.Mock(uuid='uuid1'), mock.Mock(uuid='uuid2')
|
||||
mock_ftsk.return_value.feed = [vios1, vios2]
|
||||
expected_vio_wrap = [vios1, vios2]
|
||||
self.slot_mgr.init_recreate_map(mock.Mock(), self._vol_drv_iter_2())
|
||||
self.assertEqual(1, mock_ftsk.call_count)
|
||||
mock_rebuild_slot.assert_called_once_with(
|
||||
self.slot_mgr, expected_vio_wrap,
|
||||
{'udidvscsi': ['uuid1'], 'udid': ['uuid1']}, [])
|
||||
|
||||
def _vol_drv_iter_2(self):
|
||||
mock_fileio = mock.Mock()
|
||||
mock_fileio.vol_type.return_value = 'fileio'
|
||||
mock_fileio.is_volume_on_vios.side_effect = ((True, 'udid'),
|
||||
(False, None))
|
||||
mock_scsi = mock.Mock()
|
||||
mock_scsi.vol_type.return_value = 'vscsi'
|
||||
mock_scsi.is_volume_on_vios.side_effect = ((True, 'udidvscsi'),
|
||||
(False, None))
|
||||
|
||||
vol_drv = [mock_fileio, mock_scsi]
|
||||
for type in vol_drv:
|
||||
yield mock.Mock(), type
|
||||
|
||||
def _vol_drv_iter(self):
|
||||
mock_scsi = mock.Mock()
|
||||
mock_scsi.vol_type.return_value = 'vscsi'
|
||||
|
|
|
@ -162,3 +162,12 @@ class TestFileIOVolumeAdapter(test_vol.TestVolumeAdapter):
|
|||
self.assertRaises(
|
||||
p_exc.VolumePreMigrationFailed,
|
||||
self.vol_drv.pre_live_migration_on_destination, mock.ANY)
|
||||
|
||||
@mock.patch('nova_powervm.virt.powervm.volume.fileio.FileIOVolumeAdapter.'
|
||||
'vios_uuids', new_callable=mock.PropertyMock)
|
||||
def test_is_volume_on_vios(self, mock_vios_uuids):
|
||||
mock_vios_uuids.return_value = ['uuid1']
|
||||
vol_found, vol_path = self.vol_drv.is_volume_on_vios(
|
||||
mock.Mock(uuid='uuid2'))
|
||||
self.assertFalse(vol_found)
|
||||
self.assertIsNone(vol_path)
|
||||
|
|
|
@ -17,6 +17,7 @@
|
|||
import abc
|
||||
import six
|
||||
|
||||
from pypowervm.tasks import partition as pvm_partition
|
||||
from pypowervm.utils import transaction as pvm_tx
|
||||
from pypowervm.wrappers import virtual_io_server as pvm_vios
|
||||
|
||||
|
@ -108,6 +109,12 @@ class PowerVMVolumeAdapter(object):
|
|||
"""List of pypowervm XAGs needed to support this adapter."""
|
||||
raise NotImplementedError()
|
||||
|
||||
@property
|
||||
def vios_uuids(self):
|
||||
"""List the UUIDs of the Virtual I/O Servers hosting the storage."""
|
||||
vios_wraps = pvm_partition.get_active_vioses(self.adapter)
|
||||
return [wrap.uuid for wrap in vios_wraps]
|
||||
|
||||
@classmethod
|
||||
def vol_type(cls):
|
||||
"""The type of volume supported by this driver."""
|
||||
|
|
|
@ -40,6 +40,12 @@ LOG = logging.getLogger(__name__)
|
|||
class FileIOVolumeAdapter(v_driver.PowerVMVolumeAdapter):
|
||||
"""Base class for connecting file based Cinder Volumes to PowerVM VMs."""
|
||||
|
||||
def __init__(self, adapter, host_uuid, instance, connection_info,
|
||||
stg_ftsk=None):
|
||||
super(FileIOVolumeAdapter, self).__init__(
|
||||
adapter, host_uuid, instance, connection_info, stg_ftsk=stg_ftsk)
|
||||
self._nl_vios_ids = None
|
||||
|
||||
@classmethod
|
||||
def min_xags(cls):
|
||||
return [pvm_const.XAG.VIO_SMAP]
|
||||
|
@ -54,6 +60,15 @@ class FileIOVolumeAdapter(v_driver.PowerVMVolumeAdapter):
|
|||
"""Return the path to the file to connect."""
|
||||
pass
|
||||
|
||||
@property
|
||||
def vios_uuids(self):
|
||||
"""List the UUIDs of the Virtual I/O Servers hosting the storage."""
|
||||
# Get the hosting UUID
|
||||
if self._nl_vios_ids is None:
|
||||
nl_vios_wrap = partition.get_mgmt_partition(self.adapter)
|
||||
self._nl_vios_ids = [nl_vios_wrap.uuid]
|
||||
return self._nl_vios_ids
|
||||
|
||||
def pre_live_migration_on_destination(self, mig_data):
|
||||
"""Perform pre live migration steps for the volume on the target host.
|
||||
|
||||
|
@ -78,9 +93,6 @@ class FileIOVolumeAdapter(v_driver.PowerVMVolumeAdapter):
|
|||
volume_id=self.volume_id, instance_name=self.instance.name)
|
||||
|
||||
def _connect_volume(self, slot_mgr):
|
||||
# Get the hosting UUID
|
||||
nl_vios_wrap = partition.get_mgmt_partition(self.adapter)
|
||||
vios_uuid = nl_vios_wrap.uuid
|
||||
path = self._get_path()
|
||||
# Get the File Path
|
||||
fio = pvm_stg.FileIO.bld(
|
||||
|
@ -89,7 +101,7 @@ class FileIOVolumeAdapter(v_driver.PowerVMVolumeAdapter):
|
|||
|
||||
def add_func(vios_w):
|
||||
# If the vios doesn't match, just return
|
||||
if vios_w.uuid != vios_uuid:
|
||||
if vios_w.uuid not in self.vios_uuids:
|
||||
return None
|
||||
|
||||
LOG.info(_LI("Adding logical volume disk connection between VM "
|
||||
|
@ -126,9 +138,6 @@ class FileIOVolumeAdapter(v_driver.PowerVMVolumeAdapter):
|
|||
set_slot_info, name='file_io_slot_%s' % path))
|
||||
|
||||
def _disconnect_volume(self, slot_mgr):
|
||||
# Get the hosting UUID
|
||||
nl_vios_wrap = partition.get_mgmt_partition(self.adapter)
|
||||
vios_uuid = nl_vios_wrap.uuid
|
||||
# Build the match function
|
||||
match_func = tsk_map.gen_match_func(pvm_stg.VDisk,
|
||||
names=[self._get_path()])
|
||||
|
@ -136,7 +145,7 @@ class FileIOVolumeAdapter(v_driver.PowerVMVolumeAdapter):
|
|||
# Make sure the remove function will run within the transaction manager
|
||||
def rm_func(vios_w):
|
||||
# If the vios doesn't match, just return
|
||||
if vios_w.uuid != vios_uuid:
|
||||
if vios_w.uuid not in self.vios_uuids:
|
||||
return None
|
||||
|
||||
LOG.info(_LI("Disconnecting instance %(inst)s from storage "
|
||||
|
@ -150,7 +159,7 @@ class FileIOVolumeAdapter(v_driver.PowerVMVolumeAdapter):
|
|||
|
||||
self.stg_ftsk.add_functor_subtask(rm_func)
|
||||
# Find the disk directly.
|
||||
vios_w = self.stg_ftsk.wrapper_tasks[vios_uuid].wrapper
|
||||
vios_w = self.stg_ftsk.wrapper_tasks[self.vios_uuids[0]].wrapper
|
||||
mappings = tsk_map.find_maps(vios_w.scsi_mappings,
|
||||
client_lpar_id=self.vm_uuid,
|
||||
match_func=match_func)
|
||||
|
@ -168,6 +177,9 @@ class FileIOVolumeAdapter(v_driver.PowerVMVolumeAdapter):
|
|||
otherwise.
|
||||
:return: The file path.
|
||||
"""
|
||||
if vios_w.uuid not in self.vios_uuids:
|
||||
return False, None
|
||||
|
||||
vol_path = self._get_path()
|
||||
vol_found = os.path.exists(vol_path)
|
||||
return vol_found, vol_path
|
||||
|
|
Loading…
Reference in New Issue