diff --git a/js/status/device-roles.js b/js/status/device-roles.js
index 1e51f2d..9a3e0b9 100644
--- a/js/status/device-roles.js
+++ b/js/status/device-roles.js
@@ -9,14 +9,12 @@ async function deviceRolesChart() {
ctx.fillText('Loading data...', canvas.width / 2, canvas.height / 2);
try {
- const response = await fetch('https://map.sthlm-mesh.se/api/v1/nodes/');
- const data = await response.json();
-
+ await fetchNodes();
const predefinedLabels = ['CLIENT', 'CLIENT_MUTE', 'CLIENT_HIDDEN', 'ROUTER_LATE', 'ROUTER', 'ROUTER_CLIENT'];
// Count role occurrences
const roleCounts = {};
- data.nodes.forEach(node => {
+ nodes.forEach(node => {
const role = node.role_name || "UNKNOWN";
roleCounts[role] = (roleCounts[role] || 0) + 1;
});
diff --git a/js/status/nodes-seen.js b/js/status/nodes-seen.js
index b7f8a70..d10cda9 100644
--- a/js/status/nodes-seen.js
+++ b/js/status/nodes-seen.js
@@ -1,21 +1,16 @@
+function countNodesSince(daysAgo) {
+ const now = new Date();
+ const threshold = new Date(now);
+ threshold.setDate(threshold.getDate() - daysAgo);
+ return nodes.filter(node => new Date(node.updated_at) >= threshold).length;
+}
async function nodesSeen() {
- const response = await fetch('https://map.sthlm-mesh.se/api/v1/nodes/');
- const data = await response.json();
- const nodes = data.nodes;
- const now = new Date();
-
-
- const countNodesSince = (daysAgo) => {
- const threshold = new Date(now);
- threshold.setDate(threshold.getDate() - daysAgo);
- return nodes.filter(node => new Date(node.updated_at) >= threshold).length;
- };
+ await fetchNodes();
document.getElementById("count-30").textContent = countNodesSince(30);
document.getElementById("count-7").textContent = countNodesSince(7);
document.getElementById("count-1").textContent = countNodesSince(1);
-
}
-nodesSeen();
\ No newline at end of file
+nodesSeen();
diff --git a/js/status/portnum-distribution-chart.js b/js/status/portnum-distribution-chart.js
index 0114d91..9ea2463 100644
--- a/js/status/portnum-distribution-chart.js
+++ b/js/status/portnum-distribution-chart.js
@@ -1,20 +1,14 @@
-let allNodes = [];
let highlightedIndex = -1;
let chartInstance;
-async function fetchNodes() {
- const res = await fetch('https://map.sthlm-mesh.se/api/v1/nodes/');
- const data = await res.json();
-
- const threshold = new Date();
- threshold.setDate(threshold.getDate() - 1);
- allNodes = data.nodes.filter(node => new Date(node.updated_at) >= threshold);
-}
-
function filterSuggestions(query) {
const lowerQuery = query.toLowerCase();
- return allNodes?.filter(node => node.long_name?.toLowerCase().includes(lowerQuery)) || [];
+ const threshold = new Date();
+ threshold.setDate(threshold.getDate() - 1);
+ return nodes
+ .filter(node => new Date(node.updated_at) >= threshold)
+ .filter(node => node.long_name?.toLowerCase().includes(lowerQuery)) || [];
}
function showSuggestions(matches) {
@@ -178,4 +172,4 @@ async function portnumDistributionChart(nodeId = null) {
}
}
-fetchNodes().then(() => portnumDistributionChart());
+portnumDistributionChart();
diff --git a/js/status/shared.js b/js/status/shared.js
new file mode 100644
index 0000000..fbedde4
--- /dev/null
+++ b/js/status/shared.js
@@ -0,0 +1,21 @@
+let nodes = [];
+let fetchPromise = null;
+
+async function fetchNodes() {
+ if (nodes.length > 0) return;
+
+ if (!fetchPromise) {
+ fetchPromise = fetch('https://map.sthlm-mesh.se/api/v1/nodes/')
+ .then(res => res.json())
+ .then(data => {
+ nodes = data.nodes;
+ fetchPromise = null; // reset after successful fetch
+ })
+ .catch(err => {
+ fetchPromise = null; // reset on failure
+ throw err;
+ });
+ }
+
+ await fetchPromise;
+}
diff --git a/sitemap.xml b/sitemap.xml
index cb9314d..ba20cf2 100644
--- a/sitemap.xml
+++ b/sitemap.xml
@@ -1 +1 @@
-
Fördelningen av olika pakettyper i nätverket under de senaste dygnet. Diagrammet visar hur nätverket används, inklusive meddelanden, positionstelemetri och andra systempaket. Sökrutan till höger kan användas för att visa antalet paket av respektive typ för en given nod.
Antalet enheter av respektive hårdvarutyp som synts i meshet de senaste 30 dagarna.
Graferna baseras på data från map.sthlm-mesh.se, där data samlas in från ett par noder i Stockholmsområdet. Data hämtas från API’t, som vi dessutom har utökat med fler funktioner för att möjliggöra mer analys. Visualisering sker genom biblioteket chartjs.org.