orphan disk update

This commit is contained in:
David Schroeder
2026-09-22 22:22:07 -05:00
parent cce22283d5
commit 3ecc338466
4 changed files with 50 additions and 9 deletions
+11 -6
View File
@@ -10,7 +10,7 @@ import subprocess
import sys
VOLUME = re.compile(r"(?<![\w.-])([\w.-]+:[^\s,;\"']+)")
FIELDS = ['node', 'storage', 'volume', 'size_bytes', 'status', 'detail']
FIELDS = ['node', 'storage', 'volume', 'size_bytes', 'status', 'detail', 'size_is_approximate']
def api(path, *options):
@@ -147,7 +147,12 @@ def scan(root=Path('/etc/pve/nodes'), get=api):
for volume in disks:
result = classify(volume, name, shared, refs, bool(errors))
if result:
rows.append(dict(zip(FIELDS, [label, sid, volume['volid'], volume.get('size'), *result])))
size = volume.get('size')
approximate = False
if format_size(size) == 'Unknown':
size = volume.get('approximate-size')
approximate = format_size(size) != 'Unknown'
rows.append(dict(zip(FIELDS, [label, sid, volume['volid'], size, *result, approximate])))
# Detect migrations/config changes during this non-atomic inventory.
_, after_errors, after = references(root, nodes, guests)
if after != before or after_errors:
@@ -157,7 +162,7 @@ def scan(root=Path('/etc/pve/nodes'), get=api):
return rows, warnings, coverage
def format_size(size_bytes):
def format_size(size_bytes, approximate=False):
try:
size = float(size_bytes)
except (TypeError, ValueError):
@@ -166,7 +171,7 @@ def format_size(size_bytes):
return 'Unknown'
for unit in ('B', 'KiB', 'MiB', 'GiB', 'TiB', 'PiB'):
if size < 1024 or unit == 'PiB':
return f'{size:.2f} {unit}'
return f"{'~' if approximate else ''}{size:.2f} {unit}"
size /= 1024
@@ -183,7 +188,7 @@ def render(rows, warnings, coverage):
if group != (row['node'], row['storage']):
group = (row['node'], row['storage'])
print(f'\n{group[0]} / {group[1]}')
size = format_size(row['size_bytes'])
size = format_size(row['size_bytes'], row.get('size_is_approximate', False))
print(f" {row['volume']} Disk size: {size} {row['status']}\n {row['detail']}")
print(f'\n{len(rows)} volume(s) reported.')
if not rows:
@@ -196,7 +201,7 @@ def export_csv(path, rows, warnings):
writer = csv.DictWriter(handle, fieldnames=FIELDS + ['disk_size', 'coverage_warnings'])
writer.writeheader()
for row in rows:
writer.writerow(dict(row, disk_size=format_size(row['size_bytes']),
writer.writerow(dict(row, disk_size=format_size(row['size_bytes'], row.get('size_is_approximate', False)),
coverage_warnings='; '.join(warnings)))
if warnings and not rows:
writer.writerow({'status': 'Incomplete scan', 'coverage_warnings': '; '.join(warnings)})