Merge "Fix HP LeftHand migration with snapshots"
This commit is contained in:
@@ -1230,6 +1230,8 @@ class TestHPLeftHandRESTISCSIDriver(HPLeftHandBaseDriver, test.TestCase):
|
||||
|
||||
mock_client.getVolumeByName.return_value = {'id': self.volume_id,
|
||||
'iscsiSessions': None}
|
||||
mock_client.getVolume.return_value = {'snapshots': {
|
||||
'resource': None}}
|
||||
|
||||
location = (self.driver.proxy.DRIVER_LOCATION % {
|
||||
'cluster': 'New_CloudCluster',
|
||||
@@ -1247,6 +1249,9 @@ class TestHPLeftHandRESTISCSIDriver(HPLeftHandBaseDriver, test.TestCase):
|
||||
expected = self.driver_startup_call_stack + [
|
||||
mock.call.getClusterByName('New_CloudCluster'),
|
||||
mock.call.getVolumeByName('fakevolume'),
|
||||
mock.call.getVolume(
|
||||
1,
|
||||
'fields=snapshots,snapshots[resource[members[name]]]'),
|
||||
mock.call.modifyVolume(1, {'clusterName': 'New_CloudCluster'})]
|
||||
|
||||
mock_client.assert_has_calls(expected)
|
||||
@@ -1254,3 +1259,44 @@ class TestHPLeftHandRESTISCSIDriver(HPLeftHandBaseDriver, test.TestCase):
|
||||
self.assertEqual(
|
||||
len(expected),
|
||||
len(mock_client.method_calls))
|
||||
|
||||
def test_migrate_with_Snapshots(self):
|
||||
# setup drive with default configuration
|
||||
# and return the mock HTTP LeftHand client
|
||||
mock_client = self.setup_driver()
|
||||
mock_client.getClusterByName.return_value = {
|
||||
"virtualIPAddresses": [{
|
||||
"ipV4Address": "10.10.10.111",
|
||||
"ipV4NetMask": "255.255.240.0"}]}
|
||||
|
||||
mock_client.getVolumeByName.return_value = {
|
||||
'id': self.volume_id,
|
||||
'iscsiSessions': None}
|
||||
mock_client.getVolume.return_value = {'snapshots': {
|
||||
'resource': 'snapfoo'}}
|
||||
|
||||
location = (self.driver.proxy.DRIVER_LOCATION % {
|
||||
'cluster': 'New_CloudCluster',
|
||||
'vip': '10.10.10.111'})
|
||||
|
||||
host = {
|
||||
'host': self.serverName,
|
||||
'capabilities': {'location_info': location}}
|
||||
(migrated, update) = self.driver.migrate_volume(
|
||||
None,
|
||||
self.volume,
|
||||
host)
|
||||
self.assertFalse(migrated)
|
||||
|
||||
expected = self.driver_startup_call_stack + [
|
||||
mock.call.getClusterByName('New_CloudCluster'),
|
||||
mock.call.getVolumeByName('fakevolume'),
|
||||
mock.call.getVolume(
|
||||
1,
|
||||
'fields=snapshots,snapshots[resource[members[name]]]')]
|
||||
|
||||
mock_client.assert_has_calls(expected)
|
||||
# and nothing else
|
||||
self.assertEqual(
|
||||
len(expected),
|
||||
len(mock_client.method_calls))
|
||||
|
||||
@@ -85,9 +85,11 @@ class HPLeftHandRESTProxy(ISCSIDriver):
|
||||
1.0.0 - Initial REST iSCSI proxy
|
||||
1.0.1 - Added support for retype
|
||||
1.0.2 - Added support for volume migrate
|
||||
1.0.3 - Fixed bug #1285829, HP LeftHand backend assisted migration
|
||||
should check for snapshots
|
||||
"""
|
||||
|
||||
VERSION = "1.0.2"
|
||||
VERSION = "1.0.3"
|
||||
|
||||
device_stats = {}
|
||||
|
||||
@@ -467,38 +469,49 @@ class HPLeftHandRESTProxy(ISCSIDriver):
|
||||
virtual_ips = cluster_info['virtualIPAddresses']
|
||||
|
||||
if driver != self.__class__.__name__:
|
||||
LOG.info(_("Can not provide backend assisted migration for "
|
||||
"volume:%s because volume is from a different "
|
||||
LOG.info(_("Cannot provide backend assisted migration for "
|
||||
"volume: %s because volume is from a different "
|
||||
"backend.") % volume['name'])
|
||||
return false_ret
|
||||
if vip != virtual_ips[0]['ipV4Address']:
|
||||
LOG.info(_("Can not provide backend assisted migration for "
|
||||
"volume:%s because cluster exists in different "
|
||||
LOG.info(_("Cannot provide backend assisted migration for "
|
||||
"volume: %s because cluster exists in different "
|
||||
"management group.") % volume['name'])
|
||||
return false_ret
|
||||
|
||||
except hpexceptions.HTTPNotFound:
|
||||
LOG.info(_("Can not provide backend assisted migration for "
|
||||
"volume:%s because cluster exists in different "
|
||||
LOG.info(_("Cannot provide backend assisted migration for "
|
||||
"volume: %s because cluster exists in different "
|
||||
"management group.") % volume['name'])
|
||||
return false_ret
|
||||
|
||||
try:
|
||||
options = {'clusterName': cluster}
|
||||
volume_info = self.client.getVolumeByName(volume['name'])
|
||||
LOG.debug(_('Volume info: %s') % volume_info)
|
||||
|
||||
# can't migrate if server is attached
|
||||
if volume_info['iscsiSessions'] is not None:
|
||||
LOG.info(_("Can not provide backend assisted migration "
|
||||
"for volume:%s because the volume has been "
|
||||
LOG.info(_("Cannot provide backend assisted migration "
|
||||
"for volume: %s because the volume has been "
|
||||
"exported.") % volume['name'])
|
||||
return false_ret
|
||||
|
||||
# can't migrate if volume has snapshots
|
||||
snap_info = self.client.getVolume(
|
||||
volume_info['id'],
|
||||
'fields=snapshots,snapshots[resource[members[name]]]')
|
||||
LOG.debug(_('Snapshot info: %s') % snap_info)
|
||||
if snap_info['snapshots']['resource'] is not None:
|
||||
LOG.info(_("Cannot provide backend assisted migration "
|
||||
"for volume: %s because the volume has "
|
||||
"snapshots.") % volume['name'])
|
||||
return false_ret
|
||||
|
||||
options = {'clusterName': cluster}
|
||||
self.client.modifyVolume(volume_info['id'], options)
|
||||
except hpexceptions.HTTPNotFound:
|
||||
LOG.info(_("Can not provide backend assisted migration for "
|
||||
"volume:%s because volume does not exist in this "
|
||||
LOG.info(_("Cannot provide backend assisted migration for "
|
||||
"volume: %s because volume does not exist in this "
|
||||
"management group.") % volume['name'])
|
||||
return false_ret
|
||||
except hpexceptions.HTTPServerError as ex:
|
||||
|
||||
Reference in New Issue
Block a user