Skip to content

Commit

Permalink
Expose raidz expand
Browse files Browse the repository at this point in the history
  • Loading branch information
themylogin committed Apr 22, 2024
1 parent 50cec42 commit 91e5960
Showing 1 changed file with 105 additions and 0 deletions.
105 changes: 105 additions & 0 deletions libzfs.pyx
Original file line number Diff line number Diff line change
Expand Up @@ -475,6 +475,11 @@ class ZFSVdevStatsException(ZFSException):
super(ZFSVdevStatsException, self).__init__(code, 'Failed to fetch ZFS Vdev Stats')


class ZFSPoolRaidzExpandStatsException(ZFSException):
def __init__(self, code):
super(ZFSPoolScanStatsException, self).__init__(code, 'Failed to retrieve ZFS pool scan stats')


class ZFSPoolScanStatsException(ZFSException):
def __init__(self, code):
super(ZFSPoolScanStatsException, self).__init__(code, 'Failed to retrieve ZFS pool scan stats')
Expand Down Expand Up @@ -2552,6 +2557,102 @@ cdef class ZFSVdev(object):
return result


cdef class ZPoolRaidzExpand(object):
cdef readonly ZFS root
cdef readonly ZFSPool pool
cdef zfs.pool_raidz_expand_stat_t *stats

def __init__(self, ZFS root, ZFSPool pool):
self.root = root
self.pool = pool
self.stats = NULL
cdef NVList config
cdef NVList nvroot = pool.get_raw_config().get_raw(zfs.ZPOOL_CONFIG_VDEV_TREE)
cdef int ret
cdef uint_t total
if zfs.ZPOOL_CONFIG_SCAN_STATS not in nvroot:
return

ret = nvroot.nvlist_lookup_uint64_array(
<nvpair.nvlist_t*>nvroot.handle, zfs.ZPOOL_CONFIG_RAIDZ_EXPAND_STATS, <uint64_t **>&self.stats, &total
)
if ret != 0:
raise ZPoolRaidzExpandStatsException(ret)

property state:
def __get__(self):
if self.stats != NULL:
return ScanState(self.stats.pres_state)

property expanding_vdev:
def __get__(self):
if self.stats != NULL:
return self.stats.pres_expanding_vdev

property start_time:
def __get__(self):
if self.stats != NULL:
return datetime.utcfromtimestamp(self.stats.pres_start_time)

property end_time:
def __get__(self):
if self.stats != NULL and self.state != ScanState.SCANNING:
return datetime.utcfromtimestamp(self.stats.pres_end_time)

property bytes_to_reflow:
def __get__(self):
if self.stats != NULL:
return self.stats.pres_to_reflow

property bytes_reflowed:
def __get__(self):
if self.stats != NULL:
return self.stats.pres_reflowed

property waiting_for_resilver:
def __get__(self):
if self.stats != NULL:
return self.stats.pres_waiting_for_resilver

property total_secs_left:
def __get__(self):
if self.state != ScanState.SCANNING:
return

copied = self.bytes_reflowed or 1
total = self.bytes_to_reflow
fraction_done = <float>copied / <float>total

elapsed = time.time() - self.stats.pres_start_time
elapsed = elapsed or 1
rate = <float>copied / <float>elapsed
rate = rate or 1
return int((total - copied) / rate)

property percentage:
def __get__(self):
if self.stats == NULL:
return

copied = self.bytes_reflowed or 1
total = self.bytes_to_reflow

return (<float>copied / <float>total) * 100

def asdict(self):
return {
'state': self.state.name if self.stats != NULL else None,
'expanding_vdev': self.expanding_vdev,
'start_time': self.start_time,
'end_time': self.end_time,
'bytes_to_reflow': self.bytes_to_reflow,
'bytes_reflowed': self.bytes_reflowed,
'waiting_for_resilver': self.waiting_for_resilver,
'total_secs_left': self.total_secs_left,
'percentage': self.percentage,
}


cdef class ZPoolScrub(object):
cdef readonly ZFS root
cdef readonly ZFSPool pool
Expand Down Expand Up @@ -3057,6 +3158,10 @@ cdef class ZFSPool(object):
def __get__(self):
return ZPoolScrub(self.root, self)

property expand:
def __get__(self):
return ZPoolRaidzExpand(self.root, self)

IF HAVE_LZC_WAIT:
def wait(self, operation_type):
if operation_type not in ZpoolWaitActivity.__members__:
Expand Down

0 comments on commit 91e5960

Please sign in to comment.