'localhost',
'user' => 'CHANGE_ME_DB_USER',
'pass' => 'CHANGE_ME_DB_PASSWORD',
'name' => 'panel'
];
$TABLE_PREFIX = 'gsp_';
$AUTO_REFRESH_SECONDS = 30; // set 0 to disable auto-refresh
/***************************************/
$mysqli = @new mysqli($db['host'], $db['user'], $db['pass'], $db['name']);
if ($mysqli->connect_errno) {
http_response_code(500);
echo "
DB connect failed: " . htmlspecialchars($mysqli->connect_error) . "
";
exit;
}
$mysqli->set_charset("utf8mb4");
function q($mysqli, $sql, $params=[]) {
$stmt = $mysqli->prepare($sql);
if(!$stmt){ throw new Exception($mysqli->error); }
if(!empty($params)) {
// infer types (all strings for simplicity)
$types = str_repeat('s', count($params));
$stmt->bind_param($types, ...$params);
}
$stmt->execute();
$res = $stmt->get_result();
$rows = $res ? $res->fetch_all(MYSQLI_ASSOC) : [];
$stmt->close();
return $rows;
}
function fmt_bytes($b) {
if ($b===null) return '—';
$u = ['B','KB','MB','GB','TB','PB']; $i=0;
while ($b>=1024 && $i=80) return 'bar danger';
if ($p>=60) return 'bar warn';
return 'bar ok';
}
function pct($v) { return $v===null ? '—' : sprintf('%.1f%%', $v); }
function num0($v) { return $v===null ? '—' : number_format($v,0); }
$machine = isset($_GET['machine']) ? trim($_GET['machine']) : '';
$windows = ['1h'=>1, '24h'=>24, '7d'=>168];
?>
GSP Stats Dashboard
0): ?>
';
foreach ($rows as $r) {
// Get latest machine sample for this machine to show current status
$latest_sample = q($mysqli, "SELECT cpu_pct, mem_used_pct, disk_used_pct, load1 FROM {$TABLE_PREFIX}machine_samples WHERE machine_id=? ORDER BY ts DESC LIMIT 1", [$r['machine_id']]);
$sample = $latest_sample ? $latest_sample[0] : null;
echo '
';
echo '
'.htmlspecialchars($r['hostname']).'
'.htmlspecialchars($r['machine_id']).'';
echo '
Last sample: '.htmlspecialchars($r['last_ts'] ?: '—').'
';
// Show current resource usage if available
if ($sample) {
echo '
';
echo '
CPU
'.pct($sample['cpu_pct']).'
';
echo '
MEM
'.pct($sample['mem_used_pct']).'
';
echo '
DISK
'.pct($sample['disk_used_pct']).'
';
if ($sample['load1'] !== null) {
echo '
LOAD
'.number_format((float)$sample['load1'], 1).'
';
}
echo '
';
}
echo '
';
echo '
';
}
echo '
';
echo ''; exit;
}
// LAST sample
$last = q($mysqli, "SELECT * FROM {$TABLE_PREFIX}machine_samples WHERE machine_id=? ORDER BY ts DESC LIMIT 1", [$machine]);
$last = $last ? $last[0] : null;
// Windows
$agg = [];
foreach($windows as $label=>$hours){
$aggM = q($mysqli, "SELECT
COUNT(*) n,
AVG(cpu_pct) cpu_avg,
AVG(mem_used_pct) mem_avg,
AVG(disk_used_pct) disk_avg
FROM {$TABLE_PREFIX}machine_samples
WHERE machine_id=? AND ts >= (NOW() - INTERVAL {$hours} HOUR)", [$machine]);
$netRows = q($mysqli, "SELECT ts, rx_bytes, tx_bytes, iface_speed_mbps
FROM {$TABLE_PREFIX}machine_samples
WHERE machine_id=? AND ts >= (NOW() - INTERVAL {$hours} HOUR)
ORDER BY ts ASC", [$machine]);
$net = ['avg_rx_Bps'=>null,'avg_tx_Bps'=>null,'avg_total_Bps'=>null,'avg_util_pct'=>null];
if (count($netRows)>=2) {
$first = $netRows[0]; $lastn = $netRows[count($netRows)-1];
$secs = max(1, strtotime($lastn['ts']) - strtotime($first['ts']));
$rx_bps = ((int)$lastn['rx_bytes'] - (int)$first['rx_bytes']) / $secs;
$tx_bps = ((int)$lastn['tx_bytes'] - (int)$first['tx_bytes']) / $secs;
$speed_mbps = $lastn['iface_speed_mbps'] ? (int)$lastn['iface_speed_mbps'] : null;
$util_pct = null;
if ($speed_mbps && $speed_mbps>0) {
$capacity_Bps = ($speed_mbps * 1000000) / 8.0;
$util_pct = (($rx_bps + $tx_bps) / $capacity_Bps) * 100.0;
}
$net = ['avg_rx_Bps'=>$rx_bps,'avg_tx_Bps'=>$tx_bps,'avg_total_Bps'=>$rx_bps+$tx_bps,'avg_util_pct'=>$util_pct];
}
$aggS = q($mysqli, "SELECT server_name,
AVG(cpu_pct) cpu_avg,
AVG(mem_pct) mem_avg,
MAX(folder_size_bytes) folder_size_bytes
FROM {$TABLE_PREFIX}process_samples
WHERE machine_id=? AND ts >= (NOW() - INTERVAL {$hours} HOUR)
GROUP BY server_name
ORDER BY server_name ASC", [$machine]);
$agg[$label] = ['machine'=>$aggM[0], 'net'=>$net, 'servers'=>$aggS];
}
} catch (Throwable $e) {
echo 'Error: '.htmlspecialchars($e->getMessage()).'