Merge "Add ability to zfssa driver to create multiple initiator groups"

This commit is contained in:
Jenkins 2014-12-05 16:35:27 +00:00 committed by Gerrit Code Review
commit 2c764a07ac
4 changed files with 141 additions and 63 deletions

View File

@ -214,12 +214,17 @@ class FakeZFSSA(object):
return out
def get_initiator_initiatorgroup(self, initiator):
ret = ['test-init-grp1']
return ret
class TestZFSSAISCSIDriver(test.TestCase):
test_vol = {
'name': 'cindervol',
'size': 1
'size': 1,
'id': 1
}
test_snap = {
@ -259,6 +264,9 @@ class TestZFSSAISCSIDriver(test.TestCase):
'iqn.1-0.org.deb:01:d7, iqn.1-0.org.deb:01:d9'
self.configuration.zfssa_initiator_user = ''
self.configuration.zfssa_initiator_password = ''
self.configuration.zfssa_initiator_config = "{'test-init-grp1':[{'iqn':\
'iqn.1-0.org.deb:01:d7','user':'','password':''}],'test-init-grp\
2':[{'iqn':'iqn.1-0.org.deb:01:d9','user':'','password':''}]}"
self.configuration.zfssa_target_group = 'test-target-grp1'
self.configuration.zfssa_target_user = ''
self.configuration.zfssa_target_password = ''
@ -283,14 +291,20 @@ class TestZFSSAISCSIDriver(test.TestCase):
self.test_snap)
self.drv.delete_volume(self.test_vol)
def test_create_export(self):
self.drv.create_volume(self.test_vol)
self.drv.create_export({}, self.test_vol)
self.drv.delete_volume(self.test_vol)
def test_remove_export(self):
self.drv.create_volume(self.test_vol)
self.drv.remove_export({}, self.test_vol)
self.drv.terminate_connection(self.test_vol, '')
self.drv.delete_volume(self.test_vol)
def test_volume_attach_detach(self):
self.drv.create_volume(self.test_vol)
connector = dict(initiator='iqn.1-0.org.deb:01:d7')
props = self.drv.initialize_connection(self.test_vol, connector)
self.assertEqual('iscsi', props['driver_volume_type'])
self.assertEqual(self.test_vol['id'], props['data']['volume_id'])
self.drv.terminate_connection(self.test_vol, '')
self.drv.delete_volume(self.test_vol)
def test_get_volume_stats(self):

View File

@ -14,13 +14,14 @@
"""
ZFS Storage Appliance Cinder Volume Driver
"""
import ast
import base64
from oslo.config import cfg
from oslo.utils import units
from cinder import exception
from cinder.i18n import _, _LE
from cinder.i18n import _, _LE, _LW
from cinder.openstack.common import log
from cinder.volume import driver
from cinder.volume.drivers.san import san
@ -50,6 +51,8 @@ ZFSSA_OPTS = [
help='iSCSI initiator CHAP user.'),
cfg.StrOpt('zfssa_initiator_password', default='',
help='iSCSI initiator CHAP password.'),
cfg.StrOpt('zfssa_initiator_config', default='',
help='iSCSI initiators configuration.'),
cfg.StrOpt('zfssa_target_group', default='tgt-grp',
help='iSCSI target group name.'),
cfg.StrOpt('zfssa_target_user', default='',
@ -107,30 +110,46 @@ class ZFSSAISCSIDriver(driver.ISCSIDriver):
compression=lcfg.zfssa_lun_compression,
logbias=lcfg.zfssa_lun_logbias)
if (lcfg.zfssa_initiator != '' and
(lcfg.zfssa_initiator_group == '' or
lcfg.zfssa_initiator_group == 'default')):
msg = (_('zfssa_initiator: %(ini)s'
' wont be used on '
'zfssa_initiator_group= %(inigrp)s.')
% {'ini': lcfg.zfssa_initiator,
'inigrp': lcfg.zfssa_initiator_group})
if (lcfg.zfssa_initiator_config != ''):
initiator_config = ast.literal_eval(lcfg.zfssa_initiator_config)
for initiator_group in initiator_config:
zfssa_initiator_group = initiator_group
for zfssa_initiator in initiator_config[zfssa_initiator_group]:
self.zfssa.create_initiator(zfssa_initiator['iqn'],
zfssa_initiator_group + '-' +
zfssa_initiator['iqn'],
chapuser=
zfssa_initiator['user'],
chapsecret=
zfssa_initiator['password'])
if (zfssa_initiator_group != 'default'):
self.zfssa.add_to_initiatorgroup(
zfssa_initiator['iqn'],
zfssa_initiator_group)
else:
LOG.warning(_LW('zfssa_initiator_config not found. '
'Using deprecated configuration options.'))
if (lcfg.zfssa_initiator != '' and
(lcfg.zfssa_initiator_group == '' or
lcfg.zfssa_initiator_group == 'default')):
LOG.warning(_LW('zfssa_initiator: %(ini)s'
' wont be used on '
'zfssa_initiator_group= %(inigrp)s.')
% {'ini': lcfg.zfssa_initiator,
'inigrp': lcfg.zfssa_initiator_group})
# Setup initiator and initiator group
if (lcfg.zfssa_initiator != '' and
lcfg.zfssa_initiator_group != '' and
lcfg.zfssa_initiator_group != 'default'):
for initiator in lcfg.zfssa_initiator.split(','):
self.zfssa.create_initiator(
initiator, lcfg.zfssa_initiator_group + '-' +
initiator, chapuser=lcfg.zfssa_initiator_user,
chapsecret=lcfg.zfssa_initiator_password)
self.zfssa.add_to_initiatorgroup(
initiator, lcfg.zfssa_initiator_group)
LOG.warning(msg)
# Setup initiator and initiator group
if (lcfg.zfssa_initiator != '' and
lcfg.zfssa_initiator_group != '' and
lcfg.zfssa_initiator_group != 'default'):
for initiator in lcfg.zfssa_initiator.split(','):
self.zfssa.create_initiator(initiator,
lcfg.zfssa_initiator_group + '-' +
initiator,
chapuser=
lcfg.zfssa_initiator_user,
chapsecret=
lcfg.zfssa_initiator_password)
self.zfssa.add_to_initiatorgroup(initiator,
lcfg.zfssa_initiator_group)
# Parse interfaces
interfaces = []
for interface in lcfg.zfssa_target_interfaces.split(','):
@ -158,11 +177,18 @@ class ZFSSAISCSIDriver(driver.ISCSIDriver):
self.zfssa.verify_pool(lcfg.zfssa_pool)
self.zfssa.verify_project(lcfg.zfssa_pool, lcfg.zfssa_project)
if (lcfg.zfssa_initiator != '' and
lcfg.zfssa_initiator_group != '' and
lcfg.zfssa_initiator_group != 'default'):
for initiator in lcfg.zfssa_initiator.split(','):
self.zfssa.verify_initiator(initiator)
if (lcfg.zfssa_initiator_config != ''):
initiator_config = ast.literal_eval(lcfg.zfssa_initiator_config)
for initiator_group in initiator_config:
zfssa_initiator_group = initiator_group
for zfssa_initiator in initiator_config[zfssa_initiator_group]:
self.zfssa.verify_initiator(zfssa_initiator['iqn'])
else:
if (lcfg.zfssa_initiator != '' and
lcfg.zfssa_initiator_group != '' and
lcfg.zfssa_initiator_group != 'default'):
for initiator in lcfg.zfssa_initiator.split(','):
self.zfssa.verify_initiator(initiator)
self.zfssa.verify_target(self._get_target_alias())
@ -197,8 +223,6 @@ class ZFSSAISCSIDriver(driver.ISCSIDriver):
compression=lcfg.zfssa_lun_compression,
logbias=lcfg.zfssa_lun_logbias)
return self._get_provider_info(volume)
def delete_volume(self, volume):
"""Deletes a volume with the given volume['name']."""
LOG.debug('zfssa.delete_volume: name=' + volume['name'])
@ -308,35 +332,14 @@ class ZFSSAISCSIDriver(driver.ISCSIDriver):
self._update_volume_status()
return self._stats
def _export_volume(self, volume):
"""Export the volume - set the initiatorgroup property."""
LOG.debug('_export_volume: volume name: %s' % volume['name'])
lcfg = self.configuration
self.zfssa.set_lun_initiatorgroup(lcfg.zfssa_pool,
lcfg.zfssa_project,
volume['name'],
lcfg.zfssa_initiator_group)
return self._get_provider_info(volume)
def create_export(self, context, volume):
"""Driver entry point to get the export info for a new volume."""
LOG.debug('create_export: volume name: %s' % volume['name'])
return self._export_volume(volume)
pass
def remove_export(self, context, volume):
"""Driver entry point to remove an export for a volume."""
LOG.debug('remove_export: volume name: %s' % volume['name'])
lcfg = self.configuration
self.zfssa.set_lun_initiatorgroup(lcfg.zfssa_pool,
lcfg.zfssa_project,
volume['name'],
'')
pass
def ensure_export(self, context, volume):
"""Driver entry point to get the export info for an existing volume."""
LOG.debug('ensure_export: volume name: %s' % volume['name'])
return self._export_volume(volume)
pass
def copy_image_to_volume(self, context, volume, image_service, image_id):
self.ensure_export(context, volume)
@ -387,3 +390,42 @@ class ZFSSAISCSIDriver(driver.ISCSIDriver):
lcfg.zfssa_project,
snapshot['volume_name'])
return lun['size'] == size
def initialize_connection(self, volume, connector):
lcfg = self.configuration
init_groups = self.zfssa.get_initiator_initiatorgroup(
connector['initiator'])
for initiator_group in init_groups:
self.zfssa.set_lun_initiatorgroup(lcfg.zfssa_pool,
lcfg.zfssa_project,
volume['name'],
initiator_group)
iscsi_properties = {}
provider = self._get_provider_info(volume)
(target_portal, iqn, lun) = provider['provider_location'].split()
iscsi_properties['target_discovered'] = False
iscsi_properties['target_portal'] = target_portal
iscsi_properties['target_iqn'] = iqn
iscsi_properties['target_lun'] = lun
iscsi_properties['volume_id'] = volume['id']
if 'provider_auth' in provider:
(auth_method, auth_username, auth_password) = provider[
'provider_auth'].split()
iscsi_properties['auth_method'] = auth_method
iscsi_properties['auth_username'] = auth_username
iscsi_properties['auth_password'] = auth_password
return {
'driver_volume_type': 'iscsi',
'data': iscsi_properties
}
def terminate_connection(self, volume, connector, **kwargs):
"""Driver entry point to terminate a connection for a volume."""
LOG.debug('terminate_connection: volume name: %s.' % volume['name'])
lcfg = self.configuration
self.zfssa.set_lun_initiatorgroup(lcfg.zfssa_pool,
lcfg.zfssa_project,
volume['name'],
'')

View File

@ -17,7 +17,7 @@ ZFS Storage Appliance Proxy
import json
from cinder import exception
from cinder.i18n import _
from cinder.i18n import _, _LE
from cinder.openstack.common import log
from cinder.volume.drivers.zfssa import restclient
@ -628,3 +628,22 @@ class ZFSSAApi(object):
val = json.loads(ret.data)
return val['snapshot']['numclones'] != 0
def get_initiator_initiatorgroup(self, initiator):
"""Returns the initiator group of the initiator."""
groups = []
svc = "/api/san/v1/iscsi/initiator-groups"
ret = self.rclient.get(svc)
if ret.status != restclient.Status.OK:
LOG.error(_LE('Error getting initiator groups.'))
exception_msg = (_('Error getting initiator groups.'))
raise exception.VolumeBackendAPIException(data=exception_msg)
val = json.loads(ret.data)
for initiator_group in val['groups']:
if initiator in initiator_group['initiators']:
groups.append(initiator_group["name"])
if len(groups) == 0:
LOG.debug("Initiator group not found. Attaching volume to "
"default initiator group.")
groups.append('default')
return groups

View File

@ -2315,6 +2315,9 @@
# iSCSI initiator CHAP password. (string value)
#zfssa_initiator_password=
# iSCSI initiators configuration. (string value)
#zfssa_initiator_config=
# iSCSI target group name. (string value)
#zfssa_target_group=tgt-grp