- `;
-
- const infoBtnEl = tile.querySelector(".tile-info-btn");
+ var infoBtnEl = tile.querySelector(".tile-info-btn");
if (infoBtnEl) {
- infoBtnEl.addEventListener("click", (e) => {
+ infoBtnEl.addEventListener("click", function(e) {
e.stopPropagation();
openCredsModal(svc.unit, svc.name);
});
}
-
return tile;
}
-// ── Render: live update (no DOM rebuild) ──────────────────────────
+// ── Render: live update ───────────────────────────────────────────
function updateTiles(services) {
_servicesCache = services;
-
- for (const svc of services) {
- const id = CSS.escape(tileId(svc));
- const tile = $tilesArea.querySelector(`.service-tile[data-tile-id="${id}"]`);
+ for (var i = 0; i < services.length; i++) {
+ var svc = services[i];
+ if (svc.type === "support") continue;
+ var id = CSS.escape(tileId(svc));
+ var tile = $tilesArea.querySelector('.service-tile[data-tile-id="' + id + '"]');
if (!tile) continue;
-
- if (svc.type === "support") continue; // Support tile doesn't have a systemd status
-
- const sc = statusClass(svc.status);
- const st = statusText(svc.status, svc.enabled);
-
- const dot = tile.querySelector(".status-dot");
- const text = tile.querySelector(".status-text");
-
- if (dot) { dot.className = `status-dot ${sc}`; }
- if (text) { text.textContent = st; }
+ var sc = statusClass(svc.status);
+ var st = statusText(svc.status, svc.enabled);
+ var dot = tile.querySelector(".status-dot");
+ var text = tile.querySelector(".status-text");
+ if (dot) dot.className = "status-dot " + sc;
+ if (text) text.textContent = st;
}
}
// ── Service polling ───────────────────────────────────────────────
-let _firstLoad = true;
+var _firstLoad = true;
async function refreshServices() {
try {
- const services = await apiFetch("/api/services");
- if (_firstLoad) {
- buildTiles(services, _categoryLabels);
- _firstLoad = false;
- } else {
- updateTiles(services);
- }
- } catch (err) {
- console.warn("Failed to fetch services:", err);
- }
+ var services = await apiFetch("/api/services");
+ if (_firstLoad) { buildTiles(services, _categoryLabels); _firstLoad = false; }
+ else { updateTiles(services); }
+ } catch (err) { console.warn("Failed to fetch services:", err); }
}
// ── Network IPs ───────────────────────────────────────────────────
async function loadNetwork() {
try {
- const data = await apiFetch("/api/network");
+ var data = await apiFetch("/api/network");
if ($internalIp) $internalIp.textContent = data.internal_ip || "—";
if ($externalIp) $externalIp.textContent = data.external_ip || "—";
_cachedExternalIp = data.external_ip || "unavailable";
@@ -287,14 +225,10 @@ async function loadNetwork() {
async function checkUpdates() {
try {
- const data = await apiFetch("/api/updates/check");
- const hasUpdates = !!data.available;
- if ($updateBadge) {
- $updateBadge.classList.toggle("visible", hasUpdates);
- }
- if ($updateBtn) {
- $updateBtn.classList.toggle("has-updates", hasUpdates);
- }
+ var data = await apiFetch("/api/updates/check");
+ var hasUpdates = !!data.available;
+ if ($updateBadge) $updateBadge.classList.toggle("visible", hasUpdates);
+ if ($updateBtn) $updateBtn.classList.toggle("has-updates", hasUpdates);
} catch (_) {}
}
@@ -302,72 +236,45 @@ async function checkUpdates() {
async function openCredsModal(unit, name) {
if (!$credsModal) return;
-
if ($credsTitle) $credsTitle.textContent = name + " — Connection Info";
- if ($credsBody) $credsBody.innerHTML = '
Loading…
';
-
+ if ($credsBody) $credsBody.innerHTML = '
Loading…
';
$credsModal.classList.add("open");
-
try {
- const data = await apiFetch(`/api/credentials/${encodeURIComponent(unit)}`);
-
+ var data = await apiFetch("/api/credentials/" + encodeURIComponent(unit));
if (!data.credentials || data.credentials.length === 0) {
$credsBody.innerHTML = '
No connection info available yet.
';
return;
}
-
- let html = "";
- for (const cred of data.credentials) {
- const id = "cred-" + Math.random().toString(36).substring(2, 8);
- const displayValue = linkify(cred.value);
-
- let qrBlock = "";
+ var html = "";
+ for (var i = 0; i < data.credentials.length; i++) {
+ var cred = data.credentials[i];
+ var id = "cred-" + Math.random().toString(36).substring(2, 8);
+ var displayValue = linkify(cred.value);
+ var qrBlock = "";
if (cred.qrcode) {
- qrBlock = `
-
';
}
@@ -391,117 +293,34 @@ async function openSupportModal() {
function renderSupportInactive() {
stopSupportTimer();
- const ip = _cachedExternalIp || "loading…";
- $supportBody.innerHTML = `
-
-
🛟
-
Need help from Sovran Systems?
-
- This will temporarily give Sovran Systems secure SSH access to your machine
- so we can diagnose and fix issues for you.
-
-
-
-
- Your External IP
- ${escHtml(ip)}
-
-
- Give this IP to your Sovran Systems technician when asked.
-
-
-
-
-
What happens when you click Enable:
-
-
A Sovran Systems SSH key is added to this machine
-
You give us your External IP shown above
-
We connect and help you remotely
-
When done, you click End Support Session to remove the key
-
-
-
-
-
- You can end the session at any time. The access key will be completely removed.
-
-
- `;
-
+ var ip = _cachedExternalIp || "loading…";
+ $supportBody.innerHTML = '
🛟
Need help from Sovran Systems?
This will temporarily give Sovran Systems secure SSH access to your machine so we can diagnose and fix issues for you.
Your External IP' + escHtml(ip) + '
Give this IP to your Sovran Systems technician when asked.
What happens when you click Enable:
A Sovran Systems SSH key is added to this machine
You give us your External IP shown above
We connect and help you remotely
When done, you click End Support Session to remove the key
You can end the session at any time. The access key will be completely removed.
';
document.getElementById("btn-support-enable").addEventListener("click", enableSupport);
}
function renderSupportActive() {
- const ip = _cachedExternalIp || "loading…";
- $supportBody.innerHTML = `
-
-
🔓
-
Support Access is Active
-
- Sovran Systems can currently connect to your machine via SSH.
-
-
-
-
- Your External IP
- ${escHtml(ip)}
-
-
- Session Duration
- —
-
-
-
-
- When your support session is complete, click the button below to
- immediately remove the access key.
-
-
-
-
- `;
-
+ var ip = _cachedExternalIp || "loading…";
+ $supportBody.innerHTML = '
🔓
Support Access is Active
Sovran Systems can currently connect to your machine via SSH.
Your External IP' + escHtml(ip) + '
Session Duration—
When your support session is complete, click the button below to immediately remove the access key.
';
document.getElementById("btn-support-disable").addEventListener("click", disableSupport);
startSupportTimer();
}
function renderSupportRemoved(verified) {
stopSupportTimer();
- const icon = verified ? "✅" : "⚠️";
- const msg = verified
- ? "The Sovran Systems SSH key has been completely removed from your machine. We no longer have any access."
- : "The key removal was requested but could not be fully verified. Please reboot your machine to be sure.";
-
- $supportBody.innerHTML = `
-
-
${icon}
-
Support Session Ended
-
${escHtml(msg)}
-
-
- SSH Key Status:
-
- ${verified ? "✓ Removed — No access" : "⚠ Verify by rebooting"}
-
-
-
-
-
- `;
-
+ var icon = verified ? "✅" : "⚠️";
+ var msg = verified ? "The Sovran Systems SSH key has been completely removed from your machine. We no longer have any access." : "The key removal was requested but could not be fully verified. Please reboot your machine to be sure.";
+ var vclass = verified ? "verified-gone" : "verify-warning";
+ var vlabel = verified ? "✓ Removed — No access" : "⚠ Verify by rebooting";
+ $supportBody.innerHTML = '