Active discovery never produced cameras rows. Drop the scanner, systemd unit, ingest trigger, and docs/env knobs. Keep RTSP preview via ffmpeg.
90 lines
4 KiB
Python
90 lines
4 KiB
Python
"""HUD: layer-rail stats, shortcuts, terminator, zoom-gated cams, SWPC chip."""
|
|
|
|
from __future__ import annotations
|
|
|
|
from pathlib import Path
|
|
|
|
ROOT = Path(__file__).resolve().parent.parent
|
|
HTML = (ROOT / "app/static/index.html").read_text()
|
|
|
|
|
|
def _fn(name: str, nxt: str | None = None) -> str:
|
|
start = HTML.index(f"function {name}")
|
|
if nxt:
|
|
return HTML[start : HTML.index(f"function {nxt}", start + 1)]
|
|
return HTML[start : start + 4000]
|
|
|
|
|
|
def test_stats_poll_uses_api_then_falls_back():
|
|
assert "/api/stats" in HTML
|
|
assert "30000" in HTML.split("pollLayerStats")[1][:2500] or "STATS_POLL_MS" in HTML
|
|
poll = HTML.split("async function pollLayerStats")[1].split("async function ")[0]
|
|
assert "404" in poll
|
|
assert "catch" in poll
|
|
ids = HTML.split("STATS_COUNT_IDS")[1].split("};")[0]
|
|
assert "aircraft" in ids and "cameras" in ids and "fires" in ids and "vessels" in ids
|
|
# Overlay loaders still write array lengths when stats is down.
|
|
assert "setLayerCount('lp-fires-count'" in HTML or 'setLayerCount("lp-fires-count"' in HTML
|
|
assert "setLayerCount('lp-cams-count'" in HTML or 'setLayerCount("lp-cams-count"' in HTML
|
|
assert "setLayerCount('lp-ac-count'" in HTML or 'setLayerCount("lp-ac-count"' in HTML
|
|
assert "setLayerCount('lp-vessels-count'" in HTML or 'setLayerCount("lp-vessels-count"' in HTML
|
|
|
|
|
|
def test_keyboard_shortcuts_do_not_steal_osiris_fs():
|
|
keys = HTML.split("function initHudKeys")[1].split("function ")[0]
|
|
assert "Escape" in keys
|
|
assert "cheat-sheet" in keys or "toggleCheatSheet" in keys
|
|
assert "mapResetView" in keys
|
|
assert "toggleLayerPanel" in keys or "closeLayerPanel" in keys
|
|
# Do not bind Osiris's conflicting F/S (flights vs fullscreen / search).
|
|
assert "e.key === 'f'" not in keys.lower()
|
|
assert "e.key === 's'" not in keys.lower()
|
|
assert "case 'f'" not in keys.lower()
|
|
assert "case 's'" not in keys.lower()
|
|
assert 'id="cheat-sheet"' in HTML
|
|
assert "?" in keys or "Shift" in keys
|
|
|
|
|
|
def test_terminator_toggle_defaults_off():
|
|
assert 'id="lp-terminator-on"' in HTML
|
|
row = HTML.split('id="lp-terminator-on"')[0][-120:] + HTML.split('id="lp-terminator-on"')[1][:80]
|
|
assert "checked" not in row.split(">")[0]
|
|
assert "function toggleTerminator" in HTML
|
|
assert "subsolarPoint" in HTML or "terminator" in HTML.lower()
|
|
|
|
|
|
def test_camera_thumbs_gated_at_zoom_12():
|
|
assert "CAM_THUMB_MIN_ZOOM" in HTML
|
|
assert "CAM_THUMB_MIN_ZOOM = 12" in HTML
|
|
thumb = _fn("camThumb", "camPopupHtml")
|
|
assert "camThumbsAllowed" in thumb or "CAM_THUMB_MIN_ZOOM" in thumb
|
|
assert "zoom in for preview" in HTML or "zoom for preview" in HTML
|
|
assert "preview unavailable" in HTML
|
|
# RTSP still proxy through snapshot; never emit rtsp hrefs.
|
|
src = _fn("camSourceLink", "youtubeId")
|
|
assert "rtsp://" in src
|
|
assert "href=" not in src.split("rtsp://")[1].split("return")[0] or "Never emit" in src
|
|
assert 'href="${esc(url)}"' in src or "href=\"${esc(url)}\"" in src
|
|
assert src.index("rtsp://") < src.index("href=")
|
|
|
|
|
|
def test_swpc_chip_browser_direct_correct_urls():
|
|
assert 'id="swpc-chip"' in HTML
|
|
assert "services.swpc.noaa.gov/json/planetary_k_index_1m.json" in HTML
|
|
assert "services.swpc.noaa.gov/json/goes/primary/xray-flares-latest.json" in HTML
|
|
assert "services.swpc.noaa.gov/products/alerts.json" in HTML
|
|
assert "services.swpc.noaa.gov/json/alerts.json" not in HTML
|
|
sw = HTML.split("async function pollSwpc")[1].split("async function ")[0]
|
|
assert "hidden" in sw
|
|
assert "kp_index" in sw
|
|
assert "90000" in HTML or "SWPC_POLL_MS" in HTML
|
|
|
|
|
|
def test_new_chrome_does_not_cover_mobile_layers_zoom():
|
|
mobile = HTML.split("@media (max-width: 820px)")[1].split("@media (prefers-reduced-motion")[0]
|
|
assert "#layer-panel" in mobile
|
|
assert ".leaflet-top.leaflet-right .leaflet-control-zoom" in mobile
|
|
assert 'id="cheat-sheet"' in HTML
|
|
cheat = HTML.split(".cheat-sheet")[1][:500]
|
|
assert "z-index" in cheat
|
|
assert "calc(100% - 96px)" in cheat or "96px" in cheat
|