Update AppImage

This commit is contained in:
MacRimi
2025-10-13 15:06:03 +02:00
parent 61e3dae708
commit 9186a44860
4 changed files with 61 additions and 16 deletions

View File

@@ -66,6 +66,19 @@ interface ProxmoxStorageData {
error?: string error?: string
} }
const formatStorage = (sizeInGB: number): string => {
if (sizeInGB < 1) {
// Less than 1 GB, show in MB
return `${(sizeInGB * 1024).toFixed(1)} MB`
} else if (sizeInGB < 1024) {
// Less than 1024 GB, show in GB
return `${sizeInGB.toFixed(1)} GB`
} else {
// 1024 GB or more, show in TB
return `${(sizeInGB / 1024).toFixed(1)} TB`
}
}
export function StorageOverview() { export function StorageOverview() {
const [storageData, setStorageData] = useState<StorageData | null>(null) const [storageData, setStorageData] = useState<StorageData | null>(null)
const [proxmoxStorage, setProxmoxStorage] = useState<ProxmoxStorageData | null>(null) const [proxmoxStorage, setProxmoxStorage] = useState<ProxmoxStorageData | null>(null)
@@ -257,7 +270,7 @@ export function StorageOverview() {
<Database className="h-4 w-4 text-muted-foreground" /> <Database className="h-4 w-4 text-muted-foreground" />
</CardHeader> </CardHeader>
<CardContent> <CardContent>
<div className="text-2xl font-bold">{totalProxmoxUsed.toFixed(1)} GB</div> <div className="text-2xl font-bold">{formatStorage(totalProxmoxUsed)}</div>
<p className="text-xs text-muted-foreground mt-1">{usagePercent}% used</p> <p className="text-xs text-muted-foreground mt-1">{usagePercent}% used</p>
</CardContent> </CardContent>
</Card> </Card>

View File

@@ -383,6 +383,19 @@ export function SystemOverview() {
return (bytes / 1024 ** 3).toFixed(2) return (bytes / 1024 ** 3).toFixed(2)
} }
const formatStorage = (sizeInGB: number): string => {
if (sizeInGB < 1) {
// Less than 1 GB, show in MB
return `${(sizeInGB * 1024).toFixed(1)} MB`
} else if (sizeInGB < 1024) {
// Less than 1024 GB, show in GB
return `${sizeInGB.toFixed(1)} GB`
} else {
// 1024 GB or more, show in TB
return `${(sizeInGB / 1024).toFixed(1)} TB`
}
}
const tempStatus = getTemperatureStatus(systemData.temperature) const tempStatus = getTemperatureStatus(systemData.temperature)
const localStorage = proxmoxStorageData?.storage.find( const localStorage = proxmoxStorageData?.storage.find(
@@ -623,15 +636,15 @@ export function SystemOverview() {
<div className="pt-2 border-t border-border space-y-2"> <div className="pt-2 border-t border-border space-y-2">
<div className="flex justify-between items-center"> <div className="flex justify-between items-center">
<span className="text-sm text-muted-foreground">Data Sent:</span> <span className="text-sm text-muted-foreground">Received:</span>
<span className="text-lg font-semibold text-foreground"> <span className="text-lg font-semibold text-green-500 flex items-center gap-1">
{(networkData.traffic.bytes_sent / 1024 ** 3).toFixed(2)} GB {formatStorage(networkData.traffic.bytes_recv / 1024 ** 3)}
</span> </span>
</div> </div>
<div className="flex justify-between items-center"> <div className="flex justify-between items-center">
<span className="text-sm text-muted-foreground">Data Received:</span> <span className="text-sm text-muted-foreground">Sent:</span>
<span className="text-lg font-semibold text-foreground"> <span className="text-lg font-semibold text-blue-500 flex items-center gap-1">
{(networkData.traffic.bytes_recv / 1024 ** 3).toFixed(2)} GB {formatStorage(networkData.traffic.bytes_sent / 1024 ** 3)}
</span> </span>
</div> </div>
</div> </div>

View File

@@ -114,6 +114,19 @@ const extractIPFromConfig = (config?: VMConfig): string => {
return "DHCP" return "DHCP"
} }
const formatStorage = (sizeInGB: number): string => {
if (sizeInGB < 1) {
// Less than 1 GB, show in MB
return `${(sizeInGB * 1024).toFixed(1)} MB`
} else if (sizeInGB < 1024) {
// Less than 1024 GB, show in GB
return `${sizeInGB.toFixed(1)} GB`
} else {
// 1024 GB or more, show in TB
return `${(sizeInGB / 1024).toFixed(1)} TB`
}
}
export function VirtualMachines() { export function VirtualMachines() {
const { const {
data: vmData, data: vmData,
@@ -419,7 +432,7 @@ export function VirtualMachines() {
</CardHeader> </CardHeader>
<CardContent> <CardContent>
<div className="text-2xl font-bold text-foreground"> <div className="text-2xl font-bold text-foreground">
{(safeVMData.reduce((sum, vm) => sum + (vm.maxdisk || 0), 0) / 1024 ** 3).toFixed(1)} GB {formatStorage(safeVMData.reduce((sum, vm) => sum + (vm.maxdisk || 0), 0) / 1024 ** 3)}
</div> </div>
<p className="text-xs text-muted-foreground mt-2">Allocated disk space</p> <p className="text-xs text-muted-foreground mt-2">Allocated disk space</p>
</CardContent> </CardContent>

View File

@@ -3672,8 +3672,7 @@ def api_backups():
# Get content of storage # Get content of storage
content_result = subprocess.run( content_result = subprocess.run(
['pvesh', 'get', f'/nodes/localhost/storage/{storage_id}/content', '--output-format', 'json'], ['pvesh', 'get', f'/nodes/localhost/storage/{storage_id}/content', '--output-format', 'json'],
capture_output=True, text=True, timeout=10 capture_output=True, text=True, timeout=10)
)
if content_result.returncode == 0: if content_result.returncode == 0:
contents = json.loads(content_result.stdout) contents = json.loads(content_result.stdout)
@@ -4097,8 +4096,7 @@ def api_vm_details(vmid):
# Get detailed config # Get detailed config
config_result = subprocess.run( config_result = subprocess.run(
['pvesh', 'get', f'/nodes/{node}/{vm_type}/{vmid}/config', '--output-format', 'json'], ['pvesh', 'get', f'/nodes/{node}/{vm_type}/{vmid}/config', '--output-format', 'json'],
capture_output=True, text=True, timeout=10 capture_output=True, text=True, timeout=10)
)
config = {} config = {}
if config_result.returncode == 0: if config_result.returncode == 0:
@@ -4143,8 +4141,7 @@ def api_vm_logs(vmid):
# Get real logs from the container/VM (last 1000 lines) # Get real logs from the container/VM (last 1000 lines)
log_result = subprocess.run( log_result = subprocess.run(
['pvesh', 'get', f'/nodes/{node}/{vm_type}/{vmid}/log', '--start', '0', '--limit', '1000'], ['pvesh', 'get', f'/nodes/{node}/{vm_type}/{vmid}/log', '--start', '0', '--limit', '1000'],
capture_output=True, text=True, timeout=10 capture_output=True, text=True, timeout=10)
)
logs = [] logs = []
if log_result.returncode == 0: if log_result.returncode == 0:
@@ -4198,8 +4195,7 @@ def api_vm_control(vmid):
# Execute action # Execute action
control_result = subprocess.run( control_result = subprocess.run(
['pvesh', 'create', f'/nodes/{node}/{vm_type}/{vmid}/status/{action}'], ['pvesh', 'create', f'/nodes/{node}/{vm_type}/{vmid}/status/{action}'],
capture_output=True, text=True, timeout=30 capture_output=True, text=True, timeout=30)
)
if control_result.returncode == 0: if control_result.returncode == 0:
return jsonify({ return jsonify({
@@ -4222,8 +4218,18 @@ def api_vm_control(vmid):
if __name__ == '__main__': if __name__ == '__main__':
# API endpoints available at: /api/system, /api/system-info, /api/storage, /api/proxmox-storage, /api/network, /api/vms, /api/logs, /api/health, /api/hardware # API endpoints available at: /api/system, /api/system-info, /api/storage, /api/proxmox-storage, /api/network, /api/vms, /api/logs, /api/health, /api/hardware
import sys
import logging import logging
# Silence werkzeug logger
log = logging.getLogger('werkzeug') log = logging.getLogger('werkzeug')
log.setLevel(logging.ERROR) log.setLevel(logging.ERROR)
# Silence Flask CLI banner (removes "Serving Flask app", "Debug mode", "WARNING" messages)
cli = sys.modules['flask.cli']
cli.show_server_banner = lambda *x: None
# Print only essential information
print("API endpoints available at: /api/system, /api/system-info, /api/storage, /api/proxmox-storage, /api/network, /api/vms, /api/logs, /api/health, /api/hardware")
app.run(host='0.0.0.0', port=8008, debug=False) app.run(host='0.0.0.0', port=8008, debug=False)