Merge "libvirt: move the LibvirtQuobyteVolumeDriver into the quobyte module"
This commit is contained in:
commit
31396bc1b1
|
@ -22,11 +22,14 @@ from oslo_utils import fileutils
|
|||
|
||||
from nova import exception
|
||||
from nova import test
|
||||
from nova.tests.unit.virt.libvirt.volume import test_volume
|
||||
from nova import utils
|
||||
from nova.virt.libvirt import utils as libvirt_utils
|
||||
from nova.virt.libvirt.volume import quobyte
|
||||
|
||||
|
||||
class QuobyteTestCase(test.NoDBTestCase):
|
||||
"""Tests the nova.virt.libvirt.volume.quobyte module utilities."""
|
||||
|
||||
@mock.patch.object(fileutils, "ensure_tree")
|
||||
@mock.patch.object(utils, "execute")
|
||||
|
@ -181,3 +184,182 @@ class QuobyteTestCase(test.NoDBTestCase):
|
|||
self.assertRaises(exception.NovaException,
|
||||
quobyte.validate_volume,
|
||||
export_mnt_base)
|
||||
|
||||
|
||||
class LibvirtQuobyteVolumeDriverTestCase(
|
||||
test_volume.LibvirtVolumeBaseTestCase):
|
||||
"""Tests the LibvirtQuobyteVolumeDriver class."""
|
||||
|
||||
@mock.patch.object(quobyte, 'validate_volume')
|
||||
@mock.patch.object(quobyte, 'mount_volume')
|
||||
@mock.patch.object(libvirt_utils, 'is_mounted', return_value=False)
|
||||
def test_libvirt_quobyte_driver_mount(self,
|
||||
mock_is_mounted,
|
||||
mock_mount_volume,
|
||||
mock_validate_volume
|
||||
):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = quobyte.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
quobyte_volume = '192.168.1.1/volume-00001'
|
||||
export_mnt_base = os.path.join(mnt_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
file_path = os.path.join(export_mnt_base, self.name)
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': self.name}}
|
||||
libvirt_driver.connect_volume(connection_info, self.disk_info)
|
||||
|
||||
conf = libvirt_driver.get_config(connection_info, self.disk_info)
|
||||
tree = conf.format_dom()
|
||||
|
||||
self._assertFileTypeEquals(tree, file_path)
|
||||
|
||||
mock_mount_volume.assert_called_once_with(quobyte_volume,
|
||||
export_mnt_base,
|
||||
mock.ANY)
|
||||
mock_validate_volume.assert_called_with(export_mnt_base)
|
||||
|
||||
@mock.patch.object(quobyte, 'validate_volume')
|
||||
@mock.patch.object(quobyte, 'umount_volume')
|
||||
@mock.patch.object(libvirt_utils, 'is_mounted', return_value=True)
|
||||
def test_libvirt_quobyte_driver_umount(self, mock_is_mounted,
|
||||
mock_umount_volume,
|
||||
mock_validate_volume):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = quobyte.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
quobyte_volume = '192.168.1.1/volume-00001'
|
||||
export_mnt_base = os.path.join(mnt_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
file_path = os.path.join(export_mnt_base, self.name)
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': self.name}}
|
||||
libvirt_driver.connect_volume(connection_info, self.disk_info)
|
||||
|
||||
conf = libvirt_driver.get_config(connection_info, self.disk_info)
|
||||
tree = conf.format_dom()
|
||||
self._assertFileTypeEquals(tree, file_path)
|
||||
|
||||
libvirt_driver.disconnect_volume(connection_info, "vde")
|
||||
|
||||
mock_validate_volume.assert_called_once_with(export_mnt_base)
|
||||
mock_umount_volume.assert_called_once_with(export_mnt_base)
|
||||
|
||||
@mock.patch.object(quobyte, 'validate_volume')
|
||||
@mock.patch.object(quobyte, 'umount_volume')
|
||||
def test_libvirt_quobyte_driver_already_mounted(self,
|
||||
mock_umount_volume,
|
||||
mock_validate_volume
|
||||
):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = quobyte.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
quobyte_volume = '192.168.1.1/volume-00001'
|
||||
export_mnt_base = os.path.join(mnt_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
file_path = os.path.join(export_mnt_base, self.name)
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': self.name}}
|
||||
|
||||
libvirt_driver.connect_volume(connection_info, self.disk_info)
|
||||
|
||||
conf = libvirt_driver.get_config(connection_info, self.disk_info)
|
||||
tree = conf.format_dom()
|
||||
self._assertFileTypeEquals(tree, file_path)
|
||||
libvirt_driver.disconnect_volume(connection_info, "vde")
|
||||
|
||||
expected_commands = [
|
||||
('findmnt', '--target', export_mnt_base,
|
||||
'--source', "quobyte@" + quobyte_volume),
|
||||
('findmnt', '--target', export_mnt_base,
|
||||
'--source', "quobyte@" + quobyte_volume),
|
||||
]
|
||||
self.assertEqual(expected_commands, self.executes)
|
||||
|
||||
mock_umount_volume.assert_called_once_with(export_mnt_base)
|
||||
mock_validate_volume.assert_called_once_with(export_mnt_base)
|
||||
|
||||
@mock.patch.object(quobyte, 'validate_volume')
|
||||
@mock.patch.object(quobyte, 'mount_volume')
|
||||
@mock.patch.object(libvirt_utils, 'is_mounted', return_value=False)
|
||||
def test_libvirt_quobyte_driver_qcow2(self, mock_is_mounted,
|
||||
mock_mount_volume,
|
||||
mock_validate_volume
|
||||
):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
libvirt_driver = quobyte.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
name = 'volume-00001'
|
||||
image_format = 'qcow2'
|
||||
quobyte_volume = '192.168.1.1/volume-00001'
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': name,
|
||||
'format': image_format}}
|
||||
|
||||
export_mnt_base = os.path.join(mnt_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
|
||||
libvirt_driver.connect_volume(connection_info, self.disk_info)
|
||||
conf = libvirt_driver.get_config(connection_info, self.disk_info)
|
||||
tree = conf.format_dom()
|
||||
self.assertEqual(tree.get('type'), 'file')
|
||||
self.assertEqual(tree.find('./driver').get('type'), 'qcow2')
|
||||
|
||||
(mock_mount_volume.
|
||||
assert_called_once_with('192.168.1.1/volume-00001',
|
||||
export_mnt_base,
|
||||
mock.ANY))
|
||||
mock_validate_volume.assert_called_with(export_mnt_base)
|
||||
|
||||
libvirt_driver.disconnect_volume(connection_info, "vde")
|
||||
|
||||
def test_libvirt_quobyte_driver_mount_non_quobyte_volume(self):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = quobyte.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': self.name}}
|
||||
|
||||
def exe_side_effect(*cmd, **kwargs):
|
||||
if cmd == mock.ANY:
|
||||
raise exception.NovaException()
|
||||
|
||||
with mock.patch.object(quobyte,
|
||||
'validate_volume') as mock_execute:
|
||||
mock_execute.side_effect = exe_side_effect
|
||||
self.assertRaises(exception.NovaException,
|
||||
libvirt_driver.connect_volume,
|
||||
connection_info,
|
||||
self.disk_info)
|
||||
|
||||
def test_libvirt_quobyte_driver_normalize_url_with_protocol(self):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = quobyte.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
self.assertEqual(libvirt_driver._normalize_url(export_string),
|
||||
"192.168.1.1/volume-00001")
|
||||
|
||||
def test_libvirt_quobyte_driver_normalize_url_without_protocol(self):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = quobyte.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = '192.168.1.1/volume-00001'
|
||||
self.assertEqual(libvirt_driver._normalize_url(export_string),
|
||||
"192.168.1.1/volume-00001")
|
||||
|
|
|
@ -29,7 +29,6 @@ from nova.tests.unit.virt.libvirt import fakelibvirt
|
|||
from nova import utils
|
||||
from nova.virt.libvirt import host
|
||||
from nova.virt.libvirt import utils as libvirt_utils
|
||||
from nova.virt.libvirt.volume import quobyte
|
||||
from nova.virt.libvirt.volume import volume
|
||||
|
||||
CONF = cfg.CONF
|
||||
|
@ -59,10 +58,11 @@ class FakeSecret(object):
|
|||
return 0
|
||||
|
||||
|
||||
class LibvirtVolumeTestCase(test.NoDBTestCase):
|
||||
class LibvirtVolumeBaseTestCase(test.NoDBTestCase):
|
||||
"""Contains common setup and helper methods for libvirt volume tests."""
|
||||
|
||||
def setUp(self):
|
||||
super(LibvirtVolumeTestCase, self).setUp()
|
||||
super(LibvirtVolumeBaseTestCase, self).setUp()
|
||||
self.executes = []
|
||||
|
||||
def fake_execute(*cmd, **kwargs):
|
||||
|
@ -98,6 +98,13 @@ class LibvirtVolumeTestCase(test.NoDBTestCase):
|
|||
self.uuid = '875a8070-d0b9-4949-8b31-104d125c9a64'
|
||||
self.user = 'foo'
|
||||
|
||||
def _assertFileTypeEquals(self, tree, file_path):
|
||||
self.assertEqual(tree.get('type'), 'file')
|
||||
self.assertEqual(tree.find('./source').get('file'), file_path)
|
||||
|
||||
|
||||
class LibvirtVolumeTestCase(LibvirtVolumeBaseTestCase):
|
||||
|
||||
def _assertNetworkAndProtocolEquals(self, tree):
|
||||
self.assertEqual(tree.get('type'), 'network')
|
||||
self.assertEqual(tree.find('./source').get('protocol'), 'rbd')
|
||||
|
@ -110,10 +117,6 @@ class LibvirtVolumeTestCase(test.NoDBTestCase):
|
|||
iscsi_name = '%s/%s' % (self.iqn, self.vol['id'])
|
||||
self.assertEqual(tree.find('./source').get('name'), iscsi_name)
|
||||
|
||||
def _assertFileTypeEquals(self, tree, file_path):
|
||||
self.assertEqual(tree.get('type'), 'file')
|
||||
self.assertEqual(tree.find('./source').get('file'), file_path)
|
||||
|
||||
def _assertDiskInfoEquals(self, tree, disk_info):
|
||||
self.assertEqual(tree.get('device'), disk_info['type'])
|
||||
self.assertEqual(tree.find('./target').get('bus'),
|
||||
|
@ -933,177 +936,3 @@ Setting up iSCSI targets: unused
|
|||
tree = conf.format_dom()
|
||||
self.assertEqual('file', tree.get('type'))
|
||||
self.assertEqual('fake_serial', tree.find('./serial').text)
|
||||
|
||||
@mock.patch.object(quobyte, 'validate_volume')
|
||||
@mock.patch.object(quobyte, 'mount_volume')
|
||||
@mock.patch.object(libvirt_utils, 'is_mounted', return_value=False)
|
||||
def test_libvirt_quobyte_driver_mount(self,
|
||||
mock_is_mounted,
|
||||
mock_mount_volume,
|
||||
mock_validate_volume
|
||||
):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = volume.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
quobyte_volume = '192.168.1.1/volume-00001'
|
||||
export_mnt_base = os.path.join(mnt_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
file_path = os.path.join(export_mnt_base, self.name)
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': self.name}}
|
||||
libvirt_driver.connect_volume(connection_info, self.disk_info)
|
||||
|
||||
conf = libvirt_driver.get_config(connection_info, self.disk_info)
|
||||
tree = conf.format_dom()
|
||||
|
||||
self._assertFileTypeEquals(tree, file_path)
|
||||
|
||||
mock_mount_volume.assert_called_once_with(quobyte_volume,
|
||||
export_mnt_base,
|
||||
mock.ANY)
|
||||
mock_validate_volume.assert_called_with(export_mnt_base)
|
||||
|
||||
@mock.patch.object(quobyte, 'validate_volume')
|
||||
@mock.patch.object(quobyte, 'umount_volume')
|
||||
@mock.patch.object(libvirt_utils, 'is_mounted', return_value=True)
|
||||
def test_libvirt_quobyte_driver_umount(self, mock_is_mounted,
|
||||
mock_umount_volume,
|
||||
mock_validate_volume):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = volume.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
quobyte_volume = '192.168.1.1/volume-00001'
|
||||
export_mnt_base = os.path.join(mnt_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
file_path = os.path.join(export_mnt_base, self.name)
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': self.name}}
|
||||
libvirt_driver.connect_volume(connection_info, self.disk_info)
|
||||
|
||||
conf = libvirt_driver.get_config(connection_info, self.disk_info)
|
||||
tree = conf.format_dom()
|
||||
self._assertFileTypeEquals(tree, file_path)
|
||||
|
||||
libvirt_driver.disconnect_volume(connection_info, "vde")
|
||||
|
||||
mock_validate_volume.assert_called_once_with(export_mnt_base)
|
||||
mock_umount_volume.assert_called_once_with(export_mnt_base)
|
||||
|
||||
@mock.patch.object(quobyte, 'validate_volume')
|
||||
@mock.patch.object(quobyte, 'umount_volume')
|
||||
def test_libvirt_quobyte_driver_already_mounted(self,
|
||||
mock_umount_volume,
|
||||
mock_validate_volume
|
||||
):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = volume.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
quobyte_volume = '192.168.1.1/volume-00001'
|
||||
export_mnt_base = os.path.join(mnt_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
file_path = os.path.join(export_mnt_base, self.name)
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': self.name}}
|
||||
|
||||
libvirt_driver.connect_volume(connection_info, self.disk_info)
|
||||
|
||||
conf = libvirt_driver.get_config(connection_info, self.disk_info)
|
||||
tree = conf.format_dom()
|
||||
self._assertFileTypeEquals(tree, file_path)
|
||||
libvirt_driver.disconnect_volume(connection_info, "vde")
|
||||
|
||||
expected_commands = [
|
||||
('findmnt', '--target', export_mnt_base,
|
||||
'--source', "quobyte@" + quobyte_volume),
|
||||
('findmnt', '--target', export_mnt_base,
|
||||
'--source', "quobyte@" + quobyte_volume),
|
||||
]
|
||||
self.assertEqual(expected_commands, self.executes)
|
||||
|
||||
mock_umount_volume.assert_called_once_with(export_mnt_base)
|
||||
mock_validate_volume.assert_called_once_with(export_mnt_base)
|
||||
|
||||
@mock.patch.object(quobyte, 'validate_volume')
|
||||
@mock.patch.object(quobyte, 'mount_volume')
|
||||
@mock.patch.object(libvirt_utils, 'is_mounted', return_value=False)
|
||||
def test_libvirt_quobyte_driver_qcow2(self, mock_is_mounted,
|
||||
mock_mount_volume,
|
||||
mock_validate_volume
|
||||
):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
libvirt_driver = volume.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
name = 'volume-00001'
|
||||
image_format = 'qcow2'
|
||||
quobyte_volume = '192.168.1.1/volume-00001'
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': name,
|
||||
'format': image_format}}
|
||||
|
||||
export_mnt_base = os.path.join(mnt_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
|
||||
libvirt_driver.connect_volume(connection_info, self.disk_info)
|
||||
conf = libvirt_driver.get_config(connection_info, self.disk_info)
|
||||
tree = conf.format_dom()
|
||||
self.assertEqual(tree.get('type'), 'file')
|
||||
self.assertEqual(tree.find('./driver').get('type'), 'qcow2')
|
||||
|
||||
(mock_mount_volume.
|
||||
assert_called_once_with('192.168.1.1/volume-00001',
|
||||
export_mnt_base,
|
||||
mock.ANY))
|
||||
mock_validate_volume.assert_called_with(export_mnt_base)
|
||||
|
||||
libvirt_driver.disconnect_volume(connection_info, "vde")
|
||||
|
||||
def test_libvirt_quobyte_driver_mount_non_quobyte_volume(self):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = volume.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
|
||||
connection_info = {'data': {'export': export_string,
|
||||
'name': self.name}}
|
||||
|
||||
def exe_side_effect(*cmd, **kwargs):
|
||||
if cmd == mock.ANY:
|
||||
raise exception.NovaException()
|
||||
|
||||
with mock.patch.object(quobyte,
|
||||
'validate_volume') as mock_execute:
|
||||
mock_execute.side_effect = exe_side_effect
|
||||
self.assertRaises(exception.NovaException,
|
||||
libvirt_driver.connect_volume,
|
||||
connection_info,
|
||||
self.disk_info)
|
||||
|
||||
def test_libvirt_quobyte_driver_normalize_url_with_protocol(self):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = volume.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = 'quobyte://192.168.1.1/volume-00001'
|
||||
self.assertEqual(libvirt_driver._normalize_url(export_string),
|
||||
"192.168.1.1/volume-00001")
|
||||
|
||||
def test_libvirt_quobyte_driver_normalize_url_without_protocol(self):
|
||||
mnt_base = '/mnt'
|
||||
self.flags(quobyte_mount_point_base=mnt_base, group='libvirt')
|
||||
|
||||
libvirt_driver = volume.LibvirtQuobyteVolumeDriver(self.fake_conn)
|
||||
export_string = '192.168.1.1/volume-00001'
|
||||
self.assertEqual(libvirt_driver._normalize_url(export_string),
|
||||
"192.168.1.1/volume-00001")
|
||||
|
|
|
@ -286,7 +286,7 @@ libvirt_volume_drivers = [
|
|||
'nova.virt.libvirt.volume.volume.LibvirtFibreChannelVolumeDriver',
|
||||
'scality=nova.virt.libvirt.volume.volume.LibvirtScalityVolumeDriver',
|
||||
'gpfs=nova.virt.libvirt.volume.volume.LibvirtGPFSVolumeDriver',
|
||||
'quobyte=nova.virt.libvirt.volume.volume.LibvirtQuobyteVolumeDriver',
|
||||
'quobyte=nova.virt.libvirt.volume.quobyte.LibvirtQuobyteVolumeDriver',
|
||||
]
|
||||
|
||||
|
||||
|
|
|
@ -13,9 +13,11 @@
|
|||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
import errno
|
||||
import os
|
||||
|
||||
from oslo_concurrency import processutils
|
||||
from oslo_config import cfg
|
||||
from oslo_log import log as logging
|
||||
from oslo_utils import fileutils
|
||||
|
||||
|
@ -23,11 +25,25 @@ from nova import exception as nova_exception
|
|||
from nova.i18n import _
|
||||
from nova.i18n import _LE
|
||||
from nova.i18n import _LI
|
||||
from nova import paths
|
||||
from nova import utils
|
||||
|
||||
from nova.virt.libvirt import utils as libvirt_utils
|
||||
from nova.virt.libvirt.volume import volume as libvirt_volume
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
volume_opts = [
|
||||
cfg.StrOpt('quobyte_mount_point_base',
|
||||
default=paths.state_path_def('mnt'),
|
||||
help='Directory where the Quobyte volume is mounted on the '
|
||||
'compute node'),
|
||||
cfg.StrOpt('quobyte_client_cfg',
|
||||
help='Path to a Quobyte Client configuration file.'),
|
||||
]
|
||||
|
||||
CONF = cfg.CONF
|
||||
CONF.register_opts(volume_opts, 'libvirt')
|
||||
|
||||
SOURCE_PROTOCOL = 'quobyte'
|
||||
SOURCE_TYPE = 'file'
|
||||
DRIVER_CACHE = 'none'
|
||||
|
@ -78,3 +94,82 @@ def validate_volume(mnt_base):
|
|||
msg = (_LE("Volume is not writable. Please broaden the file"
|
||||
" permissions. Mount: %s") % mnt_base)
|
||||
raise nova_exception.NovaException(msg)
|
||||
|
||||
|
||||
class LibvirtQuobyteVolumeDriver(libvirt_volume.LibvirtBaseVolumeDriver):
|
||||
"""Class implements libvirt part of volume driver for Quobyte."""
|
||||
|
||||
def __init__(self, connection):
|
||||
"""Create back-end to Quobyte."""
|
||||
super(LibvirtQuobyteVolumeDriver,
|
||||
self).__init__(connection, is_block_dev=False)
|
||||
|
||||
def get_config(self, connection_info, disk_info):
|
||||
conf = super(LibvirtQuobyteVolumeDriver,
|
||||
self).get_config(connection_info, disk_info)
|
||||
data = connection_info['data']
|
||||
conf.source_protocol = SOURCE_PROTOCOL
|
||||
conf.source_type = SOURCE_TYPE
|
||||
conf.driver_cache = DRIVER_CACHE
|
||||
conf.driver_io = DRIVER_IO
|
||||
conf.driver_format = data.get('format', 'raw')
|
||||
|
||||
quobyte_volume = self._normalize_url(data['export'])
|
||||
path = os.path.join(self._get_mount_point_for_share(quobyte_volume),
|
||||
data['name'])
|
||||
conf.source_path = path
|
||||
|
||||
return conf
|
||||
|
||||
@utils.synchronized('connect_volume')
|
||||
def connect_volume(self, connection_info, disk_info):
|
||||
"""Connect the volume."""
|
||||
data = connection_info['data']
|
||||
quobyte_volume = self._normalize_url(data['export'])
|
||||
mount_path = self._get_mount_point_for_share(quobyte_volume)
|
||||
mounted = libvirt_utils.is_mounted(mount_path,
|
||||
SOURCE_PROTOCOL
|
||||
+ '@' + quobyte_volume)
|
||||
if mounted:
|
||||
try:
|
||||
os.stat(mount_path)
|
||||
except OSError as exc:
|
||||
if exc.errno == errno.ENOTCONN:
|
||||
mounted = False
|
||||
LOG.info(_LI('Fixing previous mount %s which was not'
|
||||
' unmounted correctly.'), mount_path)
|
||||
umount_volume(mount_path)
|
||||
|
||||
if not mounted:
|
||||
mount_volume(quobyte_volume,
|
||||
mount_path,
|
||||
CONF.libvirt.quobyte_client_cfg)
|
||||
|
||||
validate_volume(mount_path)
|
||||
|
||||
@utils.synchronized('connect_volume')
|
||||
def disconnect_volume(self, connection_info, disk_dev):
|
||||
"""Disconnect the volume."""
|
||||
|
||||
quobyte_volume = self._normalize_url(connection_info['data']['export'])
|
||||
mount_path = self._get_mount_point_for_share(quobyte_volume)
|
||||
|
||||
if libvirt_utils.is_mounted(mount_path, 'quobyte@' + quobyte_volume):
|
||||
umount_volume(mount_path)
|
||||
else:
|
||||
LOG.info(_LI("Trying to disconnected unmounted volume at %s"),
|
||||
mount_path)
|
||||
|
||||
def _normalize_url(self, export):
|
||||
protocol = SOURCE_PROTOCOL + "://"
|
||||
if export.startswith(protocol):
|
||||
export = export[len(protocol):]
|
||||
return export
|
||||
|
||||
def _get_mount_point_for_share(self, quobyte_volume):
|
||||
"""Return mount point for Quobyte volume.
|
||||
|
||||
:param quobyte_volume: Example: storage-host/openstack-volumes
|
||||
"""
|
||||
return os.path.join(CONF.libvirt.quobyte_mount_point_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
|
|
|
@ -16,7 +16,6 @@
|
|||
|
||||
"""Volume drivers for libvirt."""
|
||||
|
||||
import errno
|
||||
import os
|
||||
import re
|
||||
|
||||
|
@ -31,13 +30,11 @@ import six.moves.urllib.parse as urlparse
|
|||
from nova import exception
|
||||
from nova.i18n import _
|
||||
from nova.i18n import _LE
|
||||
from nova.i18n import _LI
|
||||
from nova.i18n import _LW
|
||||
from nova import paths
|
||||
from nova import utils
|
||||
from nova.virt.libvirt import config as vconfig
|
||||
from nova.virt.libvirt import utils as libvirt_utils
|
||||
from nova.virt.libvirt.volume import quobyte
|
||||
from nova.virt.libvirt.volume import remotefs
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
@ -92,12 +89,6 @@ volume_opts = [
|
|||
default=[],
|
||||
help='Protocols listed here will be accessed directly '
|
||||
'from QEMU. Currently supported protocols: [gluster]'),
|
||||
cfg.StrOpt('quobyte_mount_point_base',
|
||||
default=paths.state_path_def('mnt'),
|
||||
help='Directory where the Quobyte volume is mounted on the '
|
||||
'compute node'),
|
||||
cfg.StrOpt('quobyte_client_cfg',
|
||||
help='Path to a Quobyte Client configuration file.'),
|
||||
cfg.StrOpt('iscsi_iface',
|
||||
deprecated_name='iscsi_transport',
|
||||
help='The iSCSI transport iface to use to connect to target in '
|
||||
|
@ -787,82 +778,3 @@ class LibvirtGPFSVolumeDriver(LibvirtBaseVolumeDriver):
|
|||
conf.source_type = "file"
|
||||
conf.source_path = connection_info['data']['device_path']
|
||||
return conf
|
||||
|
||||
|
||||
class LibvirtQuobyteVolumeDriver(LibvirtBaseVolumeDriver):
|
||||
"""Class implements libvirt part of volume driver for Quobyte."""
|
||||
|
||||
def __init__(self, connection):
|
||||
"""Create back-end to Quobyte."""
|
||||
super(LibvirtQuobyteVolumeDriver,
|
||||
self).__init__(connection, is_block_dev=False)
|
||||
|
||||
def get_config(self, connection_info, disk_info):
|
||||
conf = super(LibvirtQuobyteVolumeDriver,
|
||||
self).get_config(connection_info, disk_info)
|
||||
data = connection_info['data']
|
||||
conf.source_protocol = quobyte.SOURCE_PROTOCOL
|
||||
conf.source_type = quobyte.SOURCE_TYPE
|
||||
conf.driver_cache = quobyte.DRIVER_CACHE
|
||||
conf.driver_io = quobyte.DRIVER_IO
|
||||
conf.driver_format = data.get('format', 'raw')
|
||||
|
||||
quobyte_volume = self._normalize_url(data['export'])
|
||||
path = os.path.join(self._get_mount_point_for_share(quobyte_volume),
|
||||
data['name'])
|
||||
conf.source_path = path
|
||||
|
||||
return conf
|
||||
|
||||
@utils.synchronized('connect_volume')
|
||||
def connect_volume(self, connection_info, disk_info):
|
||||
"""Connect the volume."""
|
||||
data = connection_info['data']
|
||||
quobyte_volume = self._normalize_url(data['export'])
|
||||
mount_path = self._get_mount_point_for_share(quobyte_volume)
|
||||
mounted = libvirt_utils.is_mounted(mount_path,
|
||||
quobyte.SOURCE_PROTOCOL
|
||||
+ '@' + quobyte_volume)
|
||||
if mounted:
|
||||
try:
|
||||
os.stat(mount_path)
|
||||
except OSError as exc:
|
||||
if exc.errno == errno.ENOTCONN:
|
||||
mounted = False
|
||||
LOG.info(_LI('Fixing previous mount %s which was not'
|
||||
' unmounted correctly.'), mount_path)
|
||||
quobyte.umount_volume(mount_path)
|
||||
|
||||
if not mounted:
|
||||
quobyte.mount_volume(quobyte_volume,
|
||||
mount_path,
|
||||
CONF.libvirt.quobyte_client_cfg)
|
||||
|
||||
quobyte.validate_volume(mount_path)
|
||||
|
||||
@utils.synchronized('connect_volume')
|
||||
def disconnect_volume(self, connection_info, disk_dev):
|
||||
"""Disconnect the volume."""
|
||||
|
||||
quobyte_volume = self._normalize_url(connection_info['data']['export'])
|
||||
mount_path = self._get_mount_point_for_share(quobyte_volume)
|
||||
|
||||
if libvirt_utils.is_mounted(mount_path, 'quobyte@' + quobyte_volume):
|
||||
quobyte.umount_volume(mount_path)
|
||||
else:
|
||||
LOG.info(_LI("Trying to disconnected unmounted volume at %s"),
|
||||
mount_path)
|
||||
|
||||
def _normalize_url(self, export):
|
||||
protocol = quobyte.SOURCE_PROTOCOL + "://"
|
||||
if export.startswith(protocol):
|
||||
export = export[len(protocol):]
|
||||
return export
|
||||
|
||||
def _get_mount_point_for_share(self, quobyte_volume):
|
||||
"""Return mount point for Quobyte volume.
|
||||
|
||||
:param quobyte_volume: Example: storage-host/openstack-volumes
|
||||
"""
|
||||
return os.path.join(CONF.libvirt.quobyte_mount_point_base,
|
||||
utils.get_hash_str(quobyte_volume))
|
||||
|
|
Loading…
Reference in New Issue