# verify trash dir is clean
self._wait_for_trash_empty()
+ def test_subvolume_create_idempotence_resize(self):
+ # create subvolume
+ subvolume = self._generate_random_subvolume_name()
+ self._fs_cmd("subvolume", "create", self.volname, subvolume)
+
+ # try creating w/ same subvolume name with size -- should set quota
+ self._fs_cmd("subvolume", "create", self.volname, subvolume, "1000000000")
+
+ # get subvolume metadata
+ subvol_info = json.loads(self._get_subvolume_info(self.volname, subvolume))
+ self.assertEqual(subvol_info["bytes_quota"], 1000000000)
+
+ # remove subvolume
+ self._fs_cmd("subvolume", "rm", self.volname, subvolume)
+
+ # verify trash dir is clean
+ self._wait_for_trash_empty()
+
def test_subvolume_create_with_invalid_data_pool_layout(self):
subvolume = self._generate_random_subvolume_name()
data_pool = "invalid_pool"
else:
self.metadata_mgr = MetadataManager(self.fs, self.config_path, 0o640)
- def _set_attrs(self, path, size, isolate_namespace, pool, uid, gid):
+ def set_attrs(self, path, size, isolate_namespace, pool, uid, gid):
# set size
if size is not None:
try:
# layout remains unset and will undesirably change with ancestor's
# pool layout changes.
xattr_key = 'ceph.dir.layout.pool'
- xattr_val = get_ancestor_xattr(self.fs, path, "ceph.dir.layout.pool")
+ xattr_val = None
+ try:
+ self.fs.getxattr(path, 'ceph.dir.layout.pool').decode('utf-8')
+ except cephfs.NoData as e:
+ xattr_val = get_ancestor_xattr(self.fs, os.path.split(path)[0], "ceph.dir.layout.pool")
if xattr_key and xattr_val:
try:
self.fs.setxattr(path, xattr_key, xattr_val.encode('utf-8'), 0)
try:
# create directory and set attributes
self.fs.mkdirs(subvol_path, mode)
- self._set_attrs(subvol_path, size, isolate_nspace, pool, uid, gid)
+ self.set_attrs(subvol_path, size, isolate_nspace, pool, uid, gid)
# persist subvolume metadata
qpath = subvol_path.decode('utf-8')
try:
# create directory and set attributes
self.fs.mkdirs(subvol_path, source_subvolume.mode)
- self._set_attrs(subvol_path, None, None, pool, source_subvolume.uid, source_subvolume.gid)
+ self.set_attrs(subvol_path, None, None, pool, source_subvolume.uid, source_subvolume.gid)
# persist subvolume metadata and clone source
qpath = subvol_path.decode('utf-8')
volname = kwargs['vol_name']
subvolname = kwargs['sub_name']
groupname = kwargs['group_name']
+ size = kwargs['size']
+ pool = kwargs['pool_layout']
+ uid = kwargs['uid']
+ gid = kwargs['gid']
try:
with open_volume(self, volname) as fs_handle:
with open_group(fs_handle, self.volspec, groupname) as group:
try:
- with open_subvol(fs_handle, self.volspec, group, subvolname):
- # idempotent creation -- valid.
- pass
+ with open_subvol(fs_handle, self.volspec, group, subvolname) as subvolume:
+ # idempotent creation -- valid. Attributes set is supported.
+ uid = uid if uid else subvolume.uid
+ gid = gid if gid else subvolume.gid
+ subvolume.set_attrs(subvolume.path, size, False, pool, uid, gid)
except VolumeException as ve:
if ve.errno == -errno.ENOENT:
self._create_subvolume(fs_handle, volname, group, subvolname, **kwargs)