Step 1: Open your browser of choice

Step 2: navigate to http://vfox-dt.thefurrycollective.ca/counties-auto.html (or wheverever this folder is located)

Step 3: Open Developer Tools or Inspect, or whatever the technical debugging part of the browser is called.

Step 4:  To do a TEST for WAYNE COUNTY, put this code in:


// Simulate a "Watch" alert for Wayne County
const countyId = "Wayne";              // must match your SVG id
const fakeClass = "alert-watch";       // yellow fill

// Find the county element in the SVG
const el = getCountyElement(countyId);

// Apply the alert class if not manually overridden
if (el && !manualOverrides[countyId]) {
  applyAlertClass(el, fakeClass);
}

// Also update the summary box manually
const summaryEl = document.getElementById("noaa-alert-summary");
if (summaryEl) {
  summaryEl.innerHTML = `<span class="${fakeClass}">${countyId.toUpperCase()}: TEST WATCH</span>`;
}


If you want to have it also change the LED:

// Wayne County: Watch (yellow)
const countyId = "Wayne";
const fakeClass = "alert-watch";
const el = getCountyElement(countyId);
if (el && !manualOverrides[countyId]) applyAlertClass(el, fakeClass);

// Update NOAA summary
const summaryEl = document.getElementById("noaa-alert-summary");
if (summaryEl) {
  summaryEl.innerHTML = `<span class="${fakeClass}">${countyId.toUpperCase()}: TEST WATCH</span>`;
}

// Turn NOAA LED red
showNOAALed(true);





Step 5: To do a MULTI-COUNTY MULTI-ALERT, such as a WARNING for ESSEX COUNTY and ADVISORY for CHATHAM-KENT, put this code in:

// Simulate multiple alerts at once

// Wayne County: Watch (yellow)
{
  const countyId = "Wayne";
  const fakeClass = "alert-watch";
  const el = getCountyElement(countyId);
  if (el && !manualOverrides[countyId]) applyAlertClass(el, fakeClass);

  const summaryEl = document.getElementById("noaa-alert-summary");
  if (summaryEl) {
    summaryEl.innerHTML += `<span class="${fakeClass}">${countyId.toUpperCase()}: TEST WATCH</span><br>`;
  }
}

// Essex County + Pelee Island: Warning (red)
{
  const countyId = "Windsor-Essex-Pelee"; // group id in your SVG
  const fakeClass = "alert-warning";
  const el = getCountyElement(countyId);
  if (el && !manualOverrides[countyId]) applyAlertClass(el, fakeClass);

  const summaryEl = document.getElementById("ec-alert-summary");
  if (summaryEl) {
    summaryEl.innerHTML += `<span class="${fakeClass}">${countyId.toUpperCase()}: TEST WARNING</span><br>`;
  }
}

// Chatham-Kent + Moraviantown: Advisory (blue)
{
  const countyId = "Chatham-Kent-Moraviantown";
  const fakeClass = "alert-advisory";
  const el = getCountyElement(countyId);
  if (el && !manualOverrides[countyId]) applyAlertClass(el, fakeClass);

  const summaryEl = document.getElementById("ec-alert-summary");
  if (summaryEl) {
    summaryEl.innerHTML += `<span class="${fakeClass}">${countyId.toUpperCase()}: TEST ADVISORY</span><br>`;
  }
}

If you want it to also change the LED:

// Wayne County: Watch
{
  const countyId = "Wayne";
  const fakeClass = "alert-watch";
  const el = getCountyElement(countyId);
  if (el && !manualOverrides[countyId]) applyAlertClass(el, fakeClass);

  const summaryEl = document.getElementById("noaa-alert-summary");
  if (summaryEl) {
    summaryEl.innerHTML += `<span class="${fakeClass}">${countyId.toUpperCase()}: TEST WATCH</span><br>`;
  }
  showNOAALed(true); // LED red
}

// Essex County: Warning
{
  const countyId = "Windsor-Essex-Pelee";
  const fakeClass = "alert-warning";
  const el = getCountyElement(countyId);
  if (el && !manualOverrides[countyId]) applyAlertClass(el, fakeClass);

  const summaryEl = document.getElementById("ec-alert-summary");
  if (summaryEl) {
    summaryEl.innerHTML += `<span class="${fakeClass}">${countyId.toUpperCase()}: TEST WARNING</span><br>`;
  }
  showECLed(true); // LED red
}

// Chatham-Kent: Advisory
{
  const countyId = "Chatham-Kent-Moraviantown";
  const fakeClass = "alert-advisory";
  const el = getCountyElement(countyId);
  if (el && !manualOverrides[countyId]) applyAlertClass(el, fakeClass);

  const summaryEl = document.getElementById("ec-alert-summary");
  if (summaryEl) {
    summaryEl.innerHTML += `<span class="${fakeClass}">${countyId.toUpperCase()}: TEST ADVISORY</span><br>`;
  }
  showECLed(true); // LED red
}


Step 5: To clear all alerts, type this in to the browser console:

// Reset all counties back to "alert-none"
document.querySelectorAll('.county').forEach(el => {
  // Remove any existing alert-* classes
  el.classList.remove(
    'alert-watch',
    'alert-warning',
    'alert-emergency',
    'alert-advisory',
    'alert-sws'
  );
  // Apply the neutral state
  el.classList.add('alert-none');
});

// Clear summaries
const noaaSummary = document.getElementById("noaa-alert-summary");
const ecSummary = document.getElementById("ec-alert-summary");
if (noaaSummary) noaaSummary.innerHTML = `<span class="alert-none">No active NOAA alerts for SE Michigan.</span>`;
if (ecSummary) ecSummary.innerHTML = `<span class="alert-none">No active EC alerts for SW Ontario.</span>`;

// Reset LEDs
document.getElementById("noaa-led")?.classList.remove("alert-active");
document.getElementById("ec-led")?.classList.remove("alert-active");


or try this:

resetAlerts(); // clears counties, summaries, timestamps, and LEDs back to neutral

Step 5:  How to test for a service outage (being unable to access NOAA.gov or weather.gc.ca):

Run these commands, seperately, into your browser console:
// Simulate NOAA fetch failure
showNOAALed(false);
const summaryEl = document.getElementById("noaa-alert-summary");
if (summaryEl) {
  summaryEl.innerHTML = `<span class="alert-none">Unable to fetch NOAA alerts (service error).</span>`;
}


// Simulate EC fetch failure
showECLed(false);
const summaryEl = document.getElementById("ec-alert-summary");
if (summaryEl) {
  summaryEl.innerHTML = `<span class="alert-none">Unable to fetch EC alerts (service error).</span>`;
}


to make the LEDs turn amber too....

// Simulate NOAA fetch failure
const led = document.getElementById("noaa-led");
if (led) {
  led.classList.remove("alert-active", "alert-none", "alert-outage"); // clear old states
  led.classList.add("alert-outage"); // amber state
}

const summaryEl = document.getElementById("noaa-alert-summary");
if (summaryEl) {
  summaryEl.innerHTML = `<span class="alert-none">Unable to fetch EC alerts (service error).</span>`;
}



// Simulate EC fetch failure
const led = document.getElementById("ec-led");
if (led) {
  led.classList.remove("alert-active", "alert-none", "alert-outage"); // clear old states
  led.classList.add("alert-outage"); // amber state
}

const summaryEl = document.getElementById("ec-alert-summary");
if (summaryEl) {
  summaryEl.innerHTML = `<span class="alert-none">Unable to fetch EC alerts (service error).</span>`;
}


or try these:

// NOAA outage
const noaaLed = document.getElementById("noaa-led");
if (noaaLed) {
  noaaLed.classList.remove("alert-active");
  noaaLed.classList.add("alert-outage"); // amber
}
const noaaSummary = document.getElementById("noaa-alert-summary");
if (noaaSummary) {
  noaaSummary.innerHTML = `<span class="alert-none">Unable to fetch NOAA alerts (service error).</span>`;
}

// EC outage
const ecLed = document.getElementById("ec-led");
if (ecLed) {
  ecLed.classList.remove("alert-active");
  ecLed.classList.add("alert-outage"); // amber
}
const ecSummary = document.getElementById("ec-alert-summary");
if (ecSummary) {
  ecSummary.innerHTML = `<span class="alert-none">Unable to fetch EC alerts (service error).</span>`;
}

Step 6: To refresh on command, just type this into console:
pollAlerts();




Step 7: Since we've updated a lot of code, we can run multi-alerts better, and it auto-detects where the timestamps are, to not touch them. just insert this into your browser's console:


// Mock NOAA + EC alerts (no timestamps included)
const summaryLines = [
  "WAYNE COUNTY: Severe Thunderstorm Warning",
  "WAYNE COUNTY: Tornado Watch",
  "OAKLAND COUNTY: Flood Advisory",
  "WINDSOR-ESSEX-PELEE: Tornado Watch",
  "CHATHAM-KENT-MORAVIANTOWN: Severe Thunderstorm Warning",
  "LAMBTON COUNTY: Flood Advisory"
];

// regroup alerts by county
const alertsByCounty = {};
summaryLines.forEach(line => {
  const parts = line.split(": ");
  if (parts.length < 2) return;
  const [county, type] = parts;
  if (!alertsByCounty[county]) alertsByCounty[county] = [];
  alertsByCounty[county].push(type);
});

// build summary with bullets + color coding
let summaryHTML = "";
for (const county in alertsByCounty) {
  summaryHTML += `${county}:<ul class="alert-list">`;
  for (const type of alertsByCounty[county]) {
    let cssClass = "alert-sws";
    if (/Warning/i.test(type)) cssClass = "alert-warning";
    else if (/Watch/i.test(type)) cssClass = "alert-watch";
    else if (/Advisory/i.test(type)) cssClass = "alert-advisory";
    else if (/Emergency/i.test(type)) cssClass = "alert-emergency";

    summaryHTML += `<li><span class="${cssClass}">${type}</span></li>`;
  }
  summaryHTML += "</ul>";
}

// inject into NOAA summary element
const noaaSummaryEl = document.getElementById("noaa-alert-summary");
if (noaaSummaryEl) {
  // preserve any existing timestamp node
  const timestampNode = noaaSummaryEl.querySelector(".timestamp");
  noaaSummaryEl.innerHTML = summaryHTML;
  if (timestampNode) {
    noaaSummaryEl.appendChild(timestampNode);
  }
}

// inject into EC summary element
const ecSummaryEl = document.getElementById("ec-alert-summary");
if (ecSummaryEl) {
  // preserve any existing timestamp node
  const timestampNode = ecSummaryEl.querySelector(".timestamp");
  ecSummaryEl.innerHTML = summaryHTML;
  if (timestampNode) {
    ecSummaryEl.appendChild(timestampNode);
  }
}





Step 8: to seperate NOAA and EC alerts from each other, and to avoid duplication, try this in browser console:

// Mock NOAA alerts
const noaaSummaryLines = [
  "WAYNE COUNTY: Severe Thunderstorm Warning (until 5:00 PM ET)",
  "WAYNE COUNTY: Tornado Watch (until 7:30 PM ET)",
  "OAKLAND COUNTY: Flood Advisory (until 9:00 PM ET)"
];

// Mock EC alerts
const ecSummaryLines = [
  "WINDSOR-ESSEX-PELEE: Tornado Watch (until 8:00 PM ET)",
  "CHATHAM-KENT-MORAVIANTOWN: Severe Thunderstorm Warning (until 5:30 PM ET)",
  "LAMBTON COUNTY: Flood Advisory (until 11:00 PM ET)"
];

function buildSummaryHTML(summaryLines) {
  const alertsByCounty = {};
  summaryLines.forEach(line => {
    const parts = line.split(": ");
    if (parts.length < 2) return;
    const [county, type] = parts;
    if (!alertsByCounty[county]) alertsByCounty[county] = [];
    alertsByCounty[county].push(type);
  });

  let summaryHTML = "";
  for (const county in alertsByCounty) {
    summaryHTML += `${county}:<ul class="alert-list">`;
    for (const type of alertsByCounty[county]) {
      let cssClass = "alert-sws";
      if (/Warning/i.test(type)) cssClass = "alert-warning";
      else if (/Watch/i.test(type)) cssClass = "alert-watch";
      else if (/Advisory/i.test(type)) cssClass = "alert-advisory";
      else if (/Emergency/i.test(type)) cssClass = "alert-emergency";

      summaryHTML += `<li><span class="${cssClass}">${type}</span></li>`;
    }
    summaryHTML += "</ul>";
  }
  return summaryHTML;
}

// inject into NOAA summary element
const noaaSummaryEl = document.getElementById("noaa-alert-summary");
if (noaaSummaryEl) {
  const timestampNode = noaaSummaryEl.querySelector(".timestamp");
  noaaSummaryEl.innerHTML = buildSummaryHTML(noaaSummaryLines);
  if (timestampNode) noaaSummaryEl.appendChild(timestampNode);
}

// inject into EC summary element
const ecSummaryEl = document.getElementById("ec-alert-summary");
if (ecSummaryEl) {
  const timestampNode = ecSummaryEl.querySelector(".timestamp");
  ecSummaryEl.innerHTML = buildSummaryHTML(ecSummaryLines);
  if (timestampNode) ecSummaryEl.appendChild(timestampNode);
}

// Simulate LEDs turning red (alert active)
showNOAALed(true);
showECLed(true);



to test if there is an outage:

// Simulate NOAA outage
const noaaLed = document.getElementById("noaa-led");
noaaLed.classList.remove("alert-active"); // clear red
noaaLed.classList.add("alert-outage");    // amber outage

// Simulate EC outage
const ecLed = document.getElementById("ec-led");
ecLed.classList.remove("alert-active");   // clear red
ecLed.classList.add("alert-outage");      // amber outage





Since i've added a test mode, you can even simulate another alert by calling another alert from the same state and modifying the UGC for the counties:


You want to intercept the fetch inside fetchUSAlerts() and return your own fake data. Here’s how to do it safely in the console:

⭐ Step 1 - Save the original fetch by running:

window.originalFetch = window.fetch;

⭐ Step 2 - Override fetch for NOAA alerts

window.fetch = async (url) => {
  if (url.includes("api.weather.gov/alerts/active")) {
    return new Response(JSON.stringify({
      features: [
        {
          properties: {
            event: "Winter Weather Advisory",
            expires: new Date(Date.now() + 36 * 3600 * 1000).toISOString(),
            geocode: { UGC: ["MIZ068", "MIZ063", "MIZ069"] },
            "@id": "urn:oid:fake-test-alert-12345"
          }
        }
      ]
    }), { status: 200 });
  }

  return window.originalFetch(url);
};

⭐ Step 3- Run your dashboard fetch

fetchUSAlerts();

Your dashboard will now:

- skip the real NOAA API

- use your injected alert

- run through the full real pipeline

- update summary

- apply auto‑painting

- update timestamp

⭐ Step 4 - Restore original fetch when done:

window.fetch = window.originalFetch;



For Environment Canada, it's similar but simpler and easier and faster:

⭐ Step 1 — Override EC fetch (same as before)

window.originalFetch = window.fetch;

window.fetch = async (url) => {
  if (url.includes("onrm")) {
    return new Response(`
      <feed xmlns="http://www.w3.org/2005/Atom"
            xmlns:cap="urn:oasis:names:tc:emergency:cap:1.2">
        <entry>
          <title>Snow Squall Warning for Niagara Region</title>
          <summary>Heavy snow expected. CHATHAM TEST TOKEN.</summary>
          <link href="https://weather.gc.ca/warnings/report_e.html?onrm19"/>
          <cap:areaDesc>ON019</cap:areaDesc>
        </entry>
      </feed>
    `, { status: 200 });
  }

  return window.originalFetch(url);
};


The magic is here:

CHATHAM TEST TOKEN

Your detection logic sees “Chatham” and goes:

- “Oh! This alert belongs to Chatham‑Kent‑Moraviantown”

- Lights up the CK county box

- Adds it to summaryLines

- Applies the correct CSS class

- Updates timestamp

- Turns on the EC LED

All without touching your code.

⭐ Step 2 — Replace EC feeds with Niagara

ecFeeds.length = 0;
ecFeeds.push("https://cors-proxy.thefurrycollective.ca/ec/onrm19_e.xml");

⭐ Step 3 — Run the EC fetch

fetchECAlertsRSS();
You will now see:

- EC LED ON

- Chatham‑Kent box lit up

- Summary shows Niagara alert

- Timestamp updates

- No recursion

- No stack overflow

- No file edits

⭐ Step 4 — Restore normal behavior

window.fetch = window.originalFetch;

Reloading the page also resets everything.