(function () { "use strict"; if (document.body.dataset.view !== "agent_management") return; const ids = [ "agentManagementLoading", "agentManagementError", "agentManagementErrorText", "agentManagementRetry", "agentManagementContent", "agentManagementRefresh", "agentCount", "agentZoneCount", "agentWaitingEnrollmentCount", "agentRows", "agentEmpty", "agentZoneRows", "agentZoneEmpty", "agentEnrollmentRows", "agentEnrollmentEmpty", "agentCreateForm", "agentSite", "agentZone", "agentDisplayName", "agentPlatform", "agentCreateSubmit", "agentCreateStatus", "agentEnrollmentResult", "agentEnrollmentToken", "agentEnrollmentExpires", "agentEnrollmentDownload", "agentEnrollmentCopy", "agentEnrollmentDismiss", "agentEnrollmentCopyStatus" ]; const el = {}; ids.forEach(function (id) { el[id] = document.getElementById(id); }); let registry = { agents: [], sites: [], zones: [] }; let enrollments = []; function text(value, fallback) { if (value === null || value === undefined || value === "") { return fallback || "Unavailable"; } return String(value); } function dateTime(value) { if (!value) return "Never"; const parsed = new Date(value); if (Number.isNaN(parsed.valueOf())) return "Unavailable"; return parsed.toLocaleString(); } function words(value) { return text(value, "Unknown") .replaceAll("_", " ") .replace(/\b\w/g, function (letter) { return letter.toUpperCase(); }); } function cell(value, className) { const node = document.createElement("td"); if (className) node.className = className; node.textContent = value; return node; } function setState(name) { el.agentManagementLoading.hidden = name !== "loading"; el.agentManagementError.hidden = name !== "error"; el.agentManagementContent.hidden = name !== "ready"; } async function api(path, options) { const response = await fetch(path, Object.assign({ credentials: "same-origin", cache: "no-store", headers: { "Accept": "application/json" } }, options || {})); const payload = await response.json().catch(function () { return {}; }); if (!response.ok) { const detail = payload && payload.detail ? String(payload.detail) : "Request failed with status " + response.status + "."; throw new Error(detail); } return payload; } function renderAgents() { el.agentRows.replaceChildren(); registry.agents.forEach(function (agent) { const row = document.createElement("tr"); const identity = document.createElement("td"); const name = document.createElement("strong"); const id = document.createElement("span"); name.textContent = text(agent.display_name, "Unnamed Agent"); id.className = "secondary"; id.textContent = agent.agent_id; identity.append(name, id); const location = [ text(agent.site_name, "Unknown site"), text(agent.agent_zone_name, "No Agent Zone") ].join(" / "); const host = [ text(agent.hostname, "Unknown host"), text(agent.ip_address, "No IP") ].join(" / "); row.append( identity, cell(location), cell(host), cell(text(agent.version, "Unknown")), cell(dateTime(agent.last_checkin_at)), cell(words(agent.credential_state)), cell(words(agent.routing_state)) ); el.agentRows.appendChild(row); }); el.agentEmpty.hidden = registry.agents.length !== 0; } function renderZones() { el.agentZoneRows.replaceChildren(); registry.zones.forEach(function (zone) { const row = document.createElement("tr"); const networks = Array.isArray(zone.networks) && zone.networks.length ? zone.networks.join(", ") : "No networks recorded"; row.append( cell(zone.site_name), cell(zone.name), cell(networks), cell(text(zone.assigned_agent_id, "Unassigned")), cell(zone.is_enabled ? "Enabled" : "Disabled") ); el.agentZoneRows.appendChild(row); }); el.agentZoneEmpty.hidden = registry.zones.length !== 0; } function renderEnrollments() { el.agentEnrollmentRows.replaceChildren(); enrollments.forEach(function (enrollment) { const row = document.createElement("tr"); row.append( cell(enrollment.display_name), cell( enrollment.site_name + " / " + enrollment.agent_zone_name ), cell(words(enrollment.status)), cell(dateTime(enrollment.created_at)), cell(dateTime(enrollment.expires_at)), cell(text(enrollment.enrolled_agent_id, "Not enrolled")) ); el.agentEnrollmentRows.appendChild(row); }); el.agentEnrollmentEmpty.hidden = enrollments.length !== 0; } function populateSites() { if (!el.agentSite) return; const selected = el.agentSite.value; el.agentSite.replaceChildren(); const placeholder = document.createElement("option"); placeholder.value = ""; placeholder.textContent = "Choose a site"; el.agentSite.appendChild(placeholder); registry.sites.forEach(function (site) { const option = document.createElement("option"); option.value = site.id; option.textContent = site.name; el.agentSite.appendChild(option); }); if ([...el.agentSite.options].some(function (option) { return option.value === selected; })) { el.agentSite.value = selected; } populateZones(); } function populateZones() { if (!el.agentZone || !el.agentSite) return; const siteId = el.agentSite.value; const selected = el.agentZone.value; el.agentZone.replaceChildren(); const placeholder = document.createElement("option"); placeholder.value = ""; if (!siteId) { placeholder.textContent = "Choose a site first"; el.agentZone.disabled = true; el.agentZone.appendChild(placeholder); return; } placeholder.textContent = "Choose an Agent Zone"; el.agentZone.appendChild(placeholder); const available = registry.zones.filter(function (zone) { return ( zone.site_id === siteId && zone.is_enabled === true && !zone.assigned_agent_id ); }); available.forEach(function (zone) { const option = document.createElement("option"); option.value = zone.id; option.textContent = zone.name; el.agentZone.appendChild(option); }); el.agentZone.disabled = available.length === 0; if ([...el.agentZone.options].some(function (option) { return option.value === selected; })) { el.agentZone.value = selected; } } function renderSummary() { el.agentCount.textContent = String(registry.agents.length); el.agentZoneCount.textContent = String(registry.zones.length); const waiting = enrollments.filter(function (item) { return item.status === "waiting"; }).length; el.agentWaitingEnrollmentCount.textContent = String(waiting); } function render() { renderSummary(); renderAgents(); renderZones(); renderEnrollments(); populateSites(); } async function refreshData(showLoading) { if (showLoading !== false) setState("loading"); try { const results = await Promise.all([ api("/api/agents"), api("/api/agent-enrollments") ]); registry = results[0] && results[0].data ? results[0].data : { agents: [], sites: [], zones: [] }; enrollments = results[1] && Array.isArray(results[1].data) ? results[1].data : []; render(); setState("ready"); } catch (error) { el.agentManagementErrorText.textContent = error.message || "Agent information could not be loaded."; setState("error"); } } async function createEnrollment(event) { event.preventDefault(); if (!el.agentCreateForm) return; el.agentCreateSubmit.disabled = true; el.agentCreateStatus.textContent = "Creating enrollment..."; try { const payload = await api("/api/agent-enrollments", { method: "POST", headers: { "Accept": "application/json", "Content-Type": "application/json" }, body: JSON.stringify({ site_id: el.agentSite.value, agent_zone_id: el.agentZone.value, display_name: el.agentDisplayName.value.trim() }) }); const enrollment = payload.data; el.agentEnrollmentToken.textContent = enrollment.enrollment_token; el.agentEnrollmentExpires.textContent = "Expires " + dateTime(enrollment.expires_at); el.agentEnrollmentCopyStatus.textContent = ""; el.agentEnrollmentResult.hidden = false; el.agentCreateStatus.textContent = "Enrollment created."; el.agentDisplayName.value = ""; await refreshData(false); } catch (error) { el.agentCreateStatus.textContent = error.message || "Enrollment could not be created."; } finally { el.agentCreateSubmit.disabled = false; } } async function downloadWindowsPackage() { const token = el.agentEnrollmentToken.textContent; if (!token) { el.agentEnrollmentCopyStatus.textContent = "No enrollment token is available to download."; return; } el.agentEnrollmentDownload.disabled = true; el.agentEnrollmentCopyStatus.textContent = "Building Windows Agent package..."; try { const response = await fetch( "/api/agent-enrollments/windows-package", { method: "POST", credentials: "same-origin", cache: "no-store", headers: { "Accept": "application/zip", "Content-Type": "application/json" }, body: JSON.stringify({ token: token }) } ); if (!response.ok) { const payload = await response.json().catch(function () { return {}; }); throw new Error( payload && payload.detail ? String(payload.detail) : "Package request failed with status " + response.status + "." ); } const blob = await response.blob(); const downloadUrl = window.URL.createObjectURL(blob); const link = document.createElement("a"); link.href = downloadUrl; link.download = "MinerOpsAgent-Windows.zip"; document.body.appendChild(link); link.click(); link.remove(); window.URL.revokeObjectURL(downloadUrl); dismissToken(); el.agentCreateStatus.textContent = "Windows Agent package downloaded. " + "The on-screen token has been cleared."; } catch (error) { el.agentEnrollmentCopyStatus.textContent = error.message || "Windows package could not be downloaded."; } finally { el.agentEnrollmentDownload.disabled = false; } } async function copyToken() { const token = el.agentEnrollmentToken.textContent; if (!token) return; try { await navigator.clipboard.writeText(token); el.agentEnrollmentCopyStatus.textContent = "Enrollment token copied."; } catch (error) { el.agentEnrollmentCopyStatus.textContent = "Copy was unavailable. Select and copy the token manually."; } } function dismissToken() { el.agentEnrollmentToken.textContent = ""; el.agentEnrollmentExpires.textContent = ""; el.agentEnrollmentCopyStatus.textContent = ""; el.agentEnrollmentResult.hidden = true; } el.agentManagementRetry.addEventListener("click", function () { refreshData(true); }); if (el.agentManagementRefresh) { el.agentManagementRefresh.addEventListener("click", function () { refreshData(true); }); } if (el.agentSite) { el.agentSite.addEventListener("change", populateZones); } if (el.agentCreateForm) { el.agentCreateForm.addEventListener("submit", createEnrollment); } if (el.agentEnrollmentDownload) { el.agentEnrollmentDownload.addEventListener( "click", downloadWindowsPackage ); } if (el.agentEnrollmentCopy) { el.agentEnrollmentCopy.addEventListener("click", copyToken); } if (el.agentEnrollmentDismiss) { el.agentEnrollmentDismiss.addEventListener( "click", dismissToken ); } refreshData(true); }());