subvolume = loaded_subvolumes.get_subvolume_object_max(fs, vol_spec, group, subvolname)
subvolume.create_clone(pool, source_volume, source_subvolume, snapname)
-def remove_subvol(fs, vol_spec, group, subvolname):
+def remove_subvol(fs, vol_spec, group, subvolname, force=False):
"""
remove a subvolume.
:param vol_spec: volume specification
:param group: group object for the subvolume
:param subvolname: subvolume name
+ :param force: force remove subvolumes
:return: None
"""
- with open_subvol(fs, vol_spec, group, subvolname) as subvolume:
+ nc_flag = True if not force else False
+ with open_subvol(fs, vol_spec, group, subvolname, need_complete=nc_flag) as subvolume:
if subvolume.list_snapshots():
raise VolumeException(-errno.ENOTEMPTY, "subvolume '{0}' has snapshots".format(subvolname))
subvolume.remove()
try:
with open_volume(self, volname) as fs_handle:
with open_group(fs_handle, self.volspec, groupname) as group:
- remove_subvol(fs_handle, self.volspec, group, subvolname)
+ remove_subvol(fs_handle, self.volspec, group, subvolname, force)
# kick the purge threads for async removal -- note that this
# assumes that the subvolume is moved to trash can.
# TODO: make purge queue as singleton so that trash can kicks
# the purge threads on dump.
self.purge_queue.queue_job(volname)
except VolumeException as ve:
- if not (ve.errno == -errno.ENOENT and force):
+ if ve.errno == -errno.EAGAIN:
+ ve = VolumeException(ve.errno, ve.error_str + " (use --force to override)")
+ ret = self.volume_exception_to_retval(ve)
+ elif not (ve.errno == -errno.ENOENT and force):
ret = self.volume_exception_to_retval(ve)
return ret