raven_gpus / index.html
Ashima's picture
Update index.html
3d055ad verified
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0"/>
<title>GPU Monitor</title>
<style>
body {
font-family: monospace;
background: #1e1e1e;
color: #cfcfcf;
padding: 2rem;
}
h1, h2 {
color: #4CAF50;
}
.container {
display: grid;
grid-template-columns: 1fr 1fr;
gap: 20px;
}
@media (max-width: 768px) {
.container {
grid-template-columns: 1fr;
}
}
.card {
background: #2d2d2d;
padding: 1rem;
border-radius: 10px;
margin-bottom: 20px;
}
pre {
overflow-x: auto;
white-space: pre-wrap;
word-wrap: break-word;
}
#refresh {
background-color: #4CAF50;
color: white;
border: none;
padding: 10px 20px;
margin-bottom: 20px;
font-size: 16px;
border-radius: 5px;
cursor: pointer;
}
#refresh:hover {
background-color: #45a049;
}
table {
width: 100%;
border-collapse: collapse;
}
th, td {
text-align: left;
padding: 8px;
border-bottom: 1px solid #444;
}
th {
background-color: #333;
color: #4CAF50;
}
.user-row {
background-color: #2a2a2a;
}
.user-row:nth-child(even) {
background-color: #303030;
}
</style>
</head>
<body>
<h1>πŸš€ Remote GPU Status</h1>
<button id="refresh">πŸ”„ Refresh</button>
<div class="container">
<div class="card">
<h2>πŸ–₯️ GPU Information</h2>
<pre id="gpu-info">Loading GPU information...</pre>
</div>
<div class="card">
<h2>⏱️ User GPU Hours - not super accurate, check activity timeline to track your process</h2>
<div id="user-hours">Loading user hours...</div>
</div>
</div>
<div class="card">
<h2>πŸ“Š Activity Timeline</h2>
<pre id="activity-timeline">Loading activity timeline...</pre>
</div>
<script>
const fetchGpuInfo = async () => {
try {
const res = await fetch("gpustat_output.txt");
if (!res.ok) throw new Error("Failed to fetch GPU info.");
const text = await res.text();
document.getElementById("gpu-info").textContent = text;
} catch (e) {
document.getElementById("gpu-info").textContent = "Error loading GPU info.";
}
};
const fetchUserData = async () => {
try {
const res = await fetch("gpu_usage_db.json");
if (!res.ok) throw new Error("Failed to fetch user data.");
const data = await res.json();
displayUserHours(data.user_gpu_hours);
displayActivityTimeline(data.samples);
} catch (e) {
document.getElementById("user-hours").textContent = "Error loading user data.";
document.getElementById("activity-timeline").textContent = "Error loading timeline data.";
}
};
const displayUserHours = (userHours) => {
const container = document.getElementById("user-hours");
// Clear previous content
container.innerHTML = "";
if (Object.keys(userHours).length === 0) {
container.textContent = "No user data available.";
return;
}
// Create table
const table = document.createElement("table");
// Create header
const thead = document.createElement("thead");
const headerRow = document.createElement("tr");
["User", "GPU ID", "Hours Used"].forEach(text => {
const th = document.createElement("th");
th.textContent = text;
headerRow.appendChild(th);
});
thead.appendChild(headerRow);
table.appendChild(thead);
// Create body
const tbody = document.createElement("tbody");
Object.entries(userHours).forEach(([key, hours]) => {
const [user, gpuId] = key.split(":");
const row = document.createElement("tr");
row.className = "user-row";
const userCell = document.createElement("td");
userCell.textContent = user;
const gpuCell = document.createElement("td");
gpuCell.textContent = gpuId;
const hoursCell = document.createElement("td");
hoursCell.textContent = hours.toFixed(2);
row.appendChild(userCell);
row.appendChild(gpuCell);
row.appendChild(hoursCell);
tbody.appendChild(row);
});
table.appendChild(tbody);
container.appendChild(table);
};
const displayActivityTimeline = (samples) => {
const container = document.getElementById("activity-timeline");
if (!samples || samples.length === 0) {
container.textContent = "No activity data available.";
return;
}
// Format the data for display
const formattedData = samples.map(sample => {
const date = new Date(sample.timestamp);
const timeString = date.toLocaleTimeString();
const users = sample.users.join(", ");
return `${timeString}: Active users - ${users}`;
}).join("\n");
container.textContent = formattedData;
};
// Refresh function that updates all data
const refreshAll = () => {
fetchGpuInfo();
fetchUserData();
};
// Add event listener
document.getElementById("refresh").addEventListener("click", refreshAll);
// Initial load
refreshAll();
</script>
</body>
</html>