import errno
import os
+from oslo.config import cfg
+
import mox as mox_lib
from mox import IgnoreArg
from mox import IsA
mox = self._mox
drv = self._driver
+ df_total_size = 2620544
df_avail = 1490560
df_head = 'Filesystem 1K-blocks Used Available Use% Mounted on\n'
- df_data = 'nfs-host:/export 2620544 996864 %d 41%% /mnt' % df_avail
+ df_data = 'nfs-host:/export %d 996864 %d 41%% /mnt' % (df_total_size,
+ df_avail)
df_output = df_head + df_data
self.configuration.nfs_disk_util = 'df'
mox.ReplayAll()
- self.assertEquals(df_avail,
+ self.assertEquals((df_avail, df_total_size),
drv._get_available_capacity(self.TEST_NFS_EXPORT1))
mox.VerifyAll()
mox.ReplayAll()
- self.assertEquals(df_total_size - du_used,
+ self.assertEquals((df_total_size - du_used, df_total_size),
drv._get_available_capacity(self.TEST_NFS_EXPORT1))
mox.VerifyAll()
"""do_setup should throw error if shares config is not configured."""
drv = self._driver
- nfs.FLAGS.nfs_shares_config = self.TEST_SHARES_CONFIG_FILE
+ cfg.CONF.nfs_shares_config = self.TEST_SHARES_CONFIG_FILE
self.assertRaises(exception.NfsException,
drv.do_setup, IsA(context.RequestContext))
mox = self._mox
drv = self._driver
self.configuration.nfs_shares_config = self.TEST_SHARES_CONFIG_FILE
- nfs.FLAGS.nfs_shares_config = self.TEST_SHARES_CONFIG_FILE
+ cfg.CONF.nfs_shares_config = self.TEST_SHARES_CONFIG_FILE
mox.StubOutWithMock(os.path, 'exists')
os.path.exists(self.TEST_SHARES_CONFIG_FILE).AndReturn(True)
mox.StubOutWithMock(drv, '_get_available_capacity')
drv._get_available_capacity(self.TEST_NFS_EXPORT1).\
- AndReturn(2 * self.ONE_GB_IN_BYTES)
+ AndReturn((2 * self.ONE_GB_IN_BYTES, 5 * self.ONE_GB_IN_BYTES))
drv._get_available_capacity(self.TEST_NFS_EXPORT2).\
- AndReturn(3 * self.ONE_GB_IN_BYTES)
+ AndReturn((3 * self.ONE_GB_IN_BYTES, 10 * self.ONE_GB_IN_BYTES))
mox.ReplayAll()
mox.StubOutWithMock(drv, '_get_available_capacity')
drv._get_available_capacity(self.TEST_NFS_EXPORT1).\
- AndReturn(0)
+ AndReturn((0, 5 * self.ONE_GB_IN_BYTES))
drv._get_available_capacity(self.TEST_NFS_EXPORT2).\
- AndReturn(0)
+ AndReturn((0, 10 * self.ONE_GB_IN_BYTES))
mox.ReplayAll()
drv = self._driver
volume = self._simple_volume()
- setattr(nfs.FLAGS, 'nfs_sparsed_volumes', True)
+ setattr(cfg.CONF, 'nfs_sparsed_volumes', True)
mox.StubOutWithMock(drv, '_create_sparsed_file')
mox.StubOutWithMock(drv, '_set_rw_permissions_for_all')
mox.VerifyAll()
- delattr(nfs.FLAGS, 'nfs_sparsed_volumes')
+ delattr(cfg.CONF, 'nfs_sparsed_volumes')
def test_create_nonsparsed_volume(self):
mox = self._mox
self.configuration.nfs_sparsed_volumes = False
volume = self._simple_volume()
- setattr(nfs.FLAGS, 'nfs_sparsed_volumes', False)
+ setattr(cfg.CONF, 'nfs_sparsed_volumes', False)
mox.StubOutWithMock(drv, '_create_regular_file')
mox.StubOutWithMock(drv, '_set_rw_permissions_for_all')
mox.VerifyAll()
- delattr(nfs.FLAGS, 'nfs_sparsed_volumes')
+ delattr(cfg.CONF, 'nfs_sparsed_volumes')
def test_create_volume_should_ensure_nfs_mounted(self):
"""create_volume ensures shares provided in config are mounted."""
drv.delete_volume(volume)
mox.VerifyAll()
+
+ def test_get_volume_stats(self):
+ """get_volume_stats must fill the correct values"""
+ mox = self._mox
+ drv = self._driver
+
+ drv._mounted_shares = [self.TEST_NFS_EXPORT1, self.TEST_NFS_EXPORT2]
+
+ mox.StubOutWithMock(drv, '_ensure_shares_mounted')
+ mox.StubOutWithMock(drv, '_get_available_capacity')
+
+ drv._ensure_shares_mounted()
+
+ drv._get_available_capacity(self.TEST_NFS_EXPORT1).\
+ AndReturn((2 * self.ONE_GB_IN_BYTES, 10 * self.ONE_GB_IN_BYTES))
+ drv._get_available_capacity(self.TEST_NFS_EXPORT2).\
+ AndReturn((3 * self.ONE_GB_IN_BYTES, 20 * self.ONE_GB_IN_BYTES))
+
+ mox.ReplayAll()
+
+ drv.get_volume_stats()
+ self.assertEqual(drv._stats['total_capacity_gb'], 30.0)
+ self.assertEqual(drv._stats['free_capacity_gb'], 5.0)
+
+ mox.VerifyAll()
return {'provider_location': share}
- def get_volume_stats(self, refresh=False):
- """Get volume status.
-
- If 'refresh' is True, run update the stats first."""
- if refresh:
- self._update_volume_status()
-
- return self._stats
-
def _update_volume_status(self):
"""Retrieve status info from volume group."""
+ super(NetAppNFSDriver, self)._update_volume_status()
- LOG.debug(_("Updating volume status"))
- data = {}
backend_name = self.configuration.safe_get('volume_backend_name')
- data["volume_backend_name"] = backend_name or 'NetApp_NFS_7mode'
- data["vendor_name"] = 'NetApp'
- data["driver_version"] = '1.0'
- data["storage_protocol"] = 'NFS'
-
- data['total_capacity_gb'] = 'infinite'
- data['free_capacity_gb'] = 'infinite'
- data['reserved_percentage'] = 100
- data['QoS_support'] = False
- self._stats = data
+ self._stats["volume_backend_name"] = (backend_name or
+ 'NetApp_NFS_7mode')
+ self._stats["vendor_name"] = 'NetApp'
+ self._stats["driver_version"] = '1.0'
class NetAppCmodeNfsDriver (NetAppNFSDriver):
password=self.configuration.netapp_password)
return client
- def get_volume_stats(self, refresh=False):
- """Get volume status.
-
- If 'refresh' is True, run update the stats first."""
- if refresh:
- self._update_volume_status()
-
- return self._stats
-
def _update_volume_status(self):
"""Retrieve status info from volume group."""
+ super(NetAppCmodeNfsDriver, self)._update_volume_status()
- LOG.debug(_("Updating volume status"))
- data = {}
backend_name = self.configuration.safe_get('volume_backend_name')
- data["volume_backend_name"] = backend_name or 'NetApp_NFS_Cluster'
- data["vendor_name"] = 'NetApp'
- data["driver_version"] = '1.0'
- data["storage_protocol"] = 'NFS'
-
- data['total_capacity_gb'] = 'infinite'
- data['free_capacity_gb'] = 'infinite'
- data['reserved_percentage'] = 100
- data['QoS_support'] = False
- self._stats = data
+ self._stats["volume_backend_name"] = (backend_name or
+ 'NetApp_NFS_Cluster')
+ self._stats["vendor_name"] = 'NetApp'
+ self._stats["driver_version"] = '1.0'
class NetAppDirectNfsDriver (NetAppNFSDriver):
'destination-path': dest_path})
self._invoke_successfully(clone_create, vserver)
- def get_volume_stats(self, refresh=False):
- """Get volume status.
-
- If 'refresh' is True, run update the stats first."""
- if refresh:
- self._update_volume_status()
-
- return self._stats
-
def _update_volume_status(self):
"""Retrieve status info from volume group."""
+ super(NetAppDirectCmodeNfsDriver, self)._update_volume_status()
- LOG.debug(_("Updating volume status"))
- data = {}
backend_name = self.configuration.safe_get('volume_backend_name')
- data["volume_backend_name"] = (backend_name
- or 'NetApp_NFS_cluster_direct')
- data["vendor_name"] = 'NetApp'
- data["driver_version"] = '1.0'
- data["storage_protocol"] = 'NFS'
-
- data['total_capacity_gb'] = 'infinite'
- data['free_capacity_gb'] = 'infinite'
- data['reserved_percentage'] = 100
- data['QoS_support'] = False
- self._stats = data
+ self._stats["volume_backend_name"] = (backend_name or
+ 'NetApp_NFS_cluster_direct')
+ self._stats["vendor_name"] = 'NetApp'
+ self._stats["driver_version"] = '1.0'
class NetAppDirect7modeNfsDriver (NetAppDirectNfsDriver):
time.sleep(5)
retry = retry - 1
- def get_volume_stats(self, refresh=False):
- """Get volume status.
-
- If 'refresh' is True, run update the stats first."""
- if refresh:
- self._update_volume_status()
-
- return self._stats
-
def _update_volume_status(self):
"""Retrieve status info from volume group."""
+ super(NetAppDirect7modeNfsDriver, self)._update_volume_status()
- LOG.debug(_("Updating volume status"))
- data = {}
backend_name = self.configuration.safe_get('volume_backend_name')
- data["volume_backend_name"] = (backend_name
- or 'NetApp_NFS_7mode_direct')
- data["vendor_name"] = 'NetApp'
- data["driver_version"] = '1.0'
- data["storage_protocol"] = 'NFS'
-
- data['total_capacity_gb'] = 'infinite'
- data['free_capacity_gb'] = 'infinite'
- data['reserved_percentage'] = 100
- data['QoS_support'] = False
- self._stats = data
+ self._stats["volume_backend_name"] = (backend_name or
+ 'NetApp_NFS_7mode_direct')
+ self._stats["vendor_name"] = 'NetApp'
+ self._stats["driver_version"] = '1.0'
from oslo.config import cfg
from cinder import exception
-from cinder import flags
from cinder.openstack.common import log as logging
from cinder.volume import driver
'of the nfs man page for details'),
]
-FLAGS = flags.FLAGS
-FLAGS.register_opts(volume_opts)
-
class RemoteFsDriver(driver.VolumeDriver):
"""Common base for drivers that work like NFS."""
greatest_share = None
for nfs_share in self._mounted_shares:
- capacity = self._get_available_capacity(nfs_share)
+ capacity = self._get_available_capacity(nfs_share)[0]
if capacity > greatest_size:
greatest_share = nfs_share
greatest_size = capacity
available = 0
+ size = int(out.split()[1])
if self.configuration.nfs_disk_util == 'df':
available = int(out.split()[3])
else:
- size = int(out.split()[1])
out, _ = self._execute('du', '-sb', '--apparent-size',
'--exclude', '*snapshot*', mount_point,
run_as_root=True)
used = int(out.split()[0])
available = size - used
- return available
+ return available, size
def _mount_nfs(self, nfs_share, mount_path, ensure=False):
"""Mount NFS share to mount path"""
# Construct the NFS mount command.
nfs_cmd = ['mount', '-t', 'nfs']
- if FLAGS.nfs_mount_options is not None:
- nfs_cmd.extend(['-o', FLAGS.nfs_mount_options])
+ if cfg.CONF.nfs_mount_options is not None:
+ nfs_cmd.extend(['-o', cfg.CONF.nfs_mount_options])
nfs_cmd.extend([nfs_share, mount_path])
try:
LOG.warn(_("%s is already mounted"), nfs_share)
else:
raise
+
+ def get_volume_stats(self, refresh=False):
+ """Get volume status.
+
+ If 'refresh' is True, run update the stats first."""
+ if refresh or not self._stats:
+ self._update_volume_status()
+
+ return self._stats
+
+ def _update_volume_status(self):
+ """Retrieve status info from volume group."""
+
+ LOG.debug(_("Updating volume status"))
+ data = {}
+ backend_name = self.configuration.safe_get('volume_backend_name')
+ data["volume_backend_name"] = backend_name or 'Generic_NFS'
+ data["vendor_name"] = 'Open Source'
+ data["driver_version"] = '1.0'
+ data["storage_protocol"] = 'nfs'
+
+ self._ensure_shares_mounted()
+
+ global_capacity = 0
+ global_free = 0
+ for nfs_share in self._mounted_shares:
+ free, capacity = self._get_available_capacity(nfs_share)
+ global_capacity += capacity
+ global_free += free
+
+ data['total_capacity_gb'] = global_capacity / 1024.0 ** 3
+ data['free_capacity_gb'] = global_free / 1024.0 ** 3
+ data['reserved_percentage'] = 0
+ data['QoS_support'] = False
+ self._stats = data