Merge remote-tracking branch 'upstream/main' into fix/tracked-info-vertical-rate

This commit is contained in:
daikaginza committed 2026-10-16 08:39:10 +07:00
commit e9fb6c15c6
868 files changed
+136598 -6063

No files matched your search

+690 -34
View File
@@ -1,5 +1,634 @@
# Changelog
- Cyclone advisories no longer go dark while NHC publishes an advisory ahead
of its nominal time: advisory and position times up to 90 minutes ahead of
the server clock are accepted (previously 5 minutes), so the whole feed is
not rejected for about half an hour each advisory cycle.
- Flights age out vanished aircraft again. OpenSky's routine position-less rows
no longer mark every snapshot partial, which had kept vanished and landed
aircraft at full opacity for up to five minutes; those rows retain only their
own aircraft, and a likely-landed one still leaves on the landed limit.
- Add WSDOT highway cameras (Washington State) as a keyless CCTV source pack:
WSDOT's official Travel Center camera layer, with frames registered only on
WSDOT's own image host (partner-hosted cameras such as Oregon DOT and City of
Seattle are skipped). Cameras with a single cardinal `CompassDirection` get
a high-confidence heading; `B` (both directions), `O`, and unset directions
use the shared id-hash fallback at low confidence. By default the 250
cameras nearest Seattle and Spokane load; `CCTV_WSDOT_MAX_SOURCES` sets the
cap (8–1,200) and `CCTV_WSDOT_ENABLED=0` turns the pack off (bassem chagra,
#644).
- Refuse still-image cameras on the CCTV media relay. `/api/cctv/media` is the
live-feed route, but it also relayed any registered still camera through an
ordinary fetch that followed redirects to any host, passed through whatever
content type came back and had no cap on the body, bypassing every protection
`/api/cctv/frame` applies to the same URL. Only HLS, MP4, WebM and MJPEG
feeds are relayed now; a still camera, or an unknown id, gets a JSON 404
without an upstream request and is served only through `/api/cctv/frame`.
The client already loaded stills through `/frame`, so nothing it requests
changes.
- Add Lithuania's public Via Lietuva / Eismoinfo road cameras to CCTV, with published coordinates, on-demand snapshots, attribution and bounded catalog requests. No API key is required. The pack is opt-in (`CCTV_LITHUANIA_ENABLED=1`) because its camera endpoints are the eismoinfo.lt website backend, not a service listed in Via Lietuva's open-data statement, so the licence for the photos is unconfirmed.
- Add King County road cameras (Washington State) as a keyless CCTV source
pack: one public King County DOT ArcGIS layer, fetched with an explicit field
list so its staff-name columns are never requested, and frames pinned to the
county's own image host and upgraded to HTTPS. WSDOT-owned rows are skipped,
and city-owned cameras the county hosts credit their owner. The layer
publishes no facing, so headings use the shared id-hash fallback at low
confidence. It does publish each camera's hardware, which is served on
`/api/cctv/sources` as `model` and `manufacturer`. `CCTV_KINGCOUNTY_MAX_SOURCES`
sets the cap and `CCTV_KINGCOUNTY_ENABLED=0` turns the pack off
(bassem chagra, #645).
- Add City of Toronto RESCU traffic cameras as a keyless CCTV source pack: the
~336 municipal cameras the Ontario 511 pack does not carry — downtown
arterials plus the Gardiner, DVP, Allen and Lake Shore. The list is the
City's own open data feed; frames are built from the documented
`loc####.jpg` convention and a digits-only camera number, so the frame proxy
is pinned to the portal origin by construction. The dataset publishes no
camera facing — its `D1`-`D4` fields describe static 2016 comparison images,
not the live pan-tilt-zoom frame — so headings use the shared id-hash
fallback at low confidence and are corrected with the calibration gizmo.
Carries the required Open Government Licence – Toronto attribution. Disable
with `CCTV_TORONTO_ENABLED=0`.
- Stop one retired bikeshare feed from reporting the whole layer as failed.
City feeds are fetched independently, but failure was recorded in a single
flag that only a successful *activation* cleared — and an already-loaded city
never activates again. A dead feed re-entering camera range therefore latched
LOAD FAILED permanently over a map still drawing every other city's stations.
Failure is now tracked per city: a city that fails beside others still
drawing marks the layer DEGRADED, polls that all fail over previously drawn
points read STALE without advancing freshness, and LOAD FAILED is reported
only when nothing is left to draw. A city that recovers clears its own
failure, a failure is dropped once its city leaves range or the camera rises
above the activation altitude, and late results from superseded requests are
ignored.
Repointed the three feeds whose operators had moved: Reddy Bikeshare (Buffalo)
to Social Bicycles, Tugo (Tucson) and Trinity Metro (Fort Worth) to PBSC.
Dropped CoGo (Columbus) and Broward B-cycle (Fort Lauderdale), whose systems
have wound down — CoGo's feed reports no stations and last moved a bike in
March 2025. The three repointed feeds were verified live.
- Add Bike Share Toronto (1,069 stations) to the bikeshare registry. The system
publishes the same PBSC GBFS v2 feeds as the Austin, Honolulu and Chattanooga
entries, so it needs no new plumbing; a registry test now holds every city's
feed URLs against the proxy host and path allowlists, so a city the proxy
would refuse fails the suite instead of rendering an empty layer.
- GBFS v3 station names use English translations when available, then the first
usable translation or short name. Empty or malformed names no longer appear as
`[object Object]` or interrupt station loading; legacy string names remain
supported in the globe and bike-share tools. Thanks to
[Kristóf Kékesi](https://github.com/KristofKekesi) (#61).
- Overpass and military-installation disk caches no longer serve answers from a
previously configured `OVERPASS_UPSTREAMS` instance after it is repointed.
- A Radio Browser mirror answering 204, 205 or 304, or a status outside
200–599, no longer crashes the local dev/preview server. Null-body statuses
get an empty body; anything else that cannot become a response fails that
mirror so the next one is tried.
- Snow flakes sway within a fixed range instead of drifting sideways faster the
longer the app runs; the Wind setting still scales the sway.
- The right rail ignores panels that other CSS hides, such as during an event
view, so they no longer force one-panel-at-a-time layout or collapse visible
panels. Panels the rail collapses itself are still restored.
- Coordinate searches refuse empty latitude or longitude components instead of navigating to an unintended location.
- Bing Aerial and Bing Labels request HTTPS tiles on HTTP localhost through
their ion-backed providers, retaining ion and per-tile attribution without
widening the Content Security Policy.
- Add New York City traffic cameras from the NYC DOT Traffic Management Center
as an opt-in CCTV pack. NYC DOT requires a data-sharing agreement for the
camera feed, so the pack is off unless `CCTV_NYC_ENABLED=1` is set by an
operator who holds one; otherwise no request reaches NYC DOT. NYC DOT's
requested disclaimer is in the Data attribution popover. The camera list is one keyless JSON request to
`webcams.nyctmc.org/api/cameras`; frames are stills synthesized from each
camera UUID on that same host, so a catalog field cannot steer the proxy
off-host. Offline cameras are dropped. Once enabled, the 250 cameras nearest
the five borough cores load and `CCTV_NYC_MAX_SOURCES` changes the cap. The catalog-wide ceiling is
unchanged; extra cameras share it round-robin with the other packs.
- Street Level counts unique tiles before ranking so overlapping dateline halves
in polar views do not waste slots in the 16-tile overview budget.
- Directions no longer shows a truncation notice for a route with exactly 200
turns, and a roundabout at the 200th turn keeps its exit distance.
- Weather records keep missing conditions unknown and refuse summaries without a measured temperature.
- Tool string length validation counts Unicode characters correctly, including characters outside the basic multilingual plane.
- Director timeline seeks cross the dateline along the short longitude arc.
- Recent Imagery continues past malformed records in full catalog pages, respects the requested record limit, and reports results as truncated when that limit drops valid records.
- Regional articles retain unknown publication times when compact source dates do not identify a real calendar instant.
- Add Detroit (MoGo), Pittsburgh (POGOH), Aspen (WE-cycle) and Kona & Hilo
(HIBike) to the GBFS bikeshare registry, the layer's first stations in
Michigan.
- Treat explicitly current, complete empty vessel coverage as a successful update,
clearing obsolete contacts while retaining stale or incomplete snapshots.
- Custom Street Level provider switches survive share links and stored state
using URL-safe stable provider IDs and a shared boolean-switch codec; existing
Mapillary links keep their meaning. Explicit provider toggles reach durable
state without adopting unrelated live switch changes.
- Directions and Recent Imagery accept replaceable acquisition sources, including
route transport, imagery catalog, thumbnails, tile templates and attribution.
Explicitly removing either source leaves its layer unavailable; standalone
defaults preserve the existing providers.
- Catalog source availability no longer modifies layer objects; unavailable
tooltips use layer display names.
- Street Level with no providers uses the shared unavailable state and refuses
activation before initialization, while keeping its layer identity visible.
- Application source configuration accepts replacements and explicit removal.
Missing catalog feeds leave their layers unavailable without blocking startup
or making fallback requests; malformed supplied feeds remain configuration errors.
- Street Level providers are optional in application composition. Omitting a
Mapillary source no longer prevents startup; callers can inject a different
provider list or an empty list without changing layer identities or share links.
- Vector tile sources take their allowed tile origin from the configured
`tileJsonUrl`, so repointing only that URL at a mirror loads tiles from the
mirror or fails visibly instead of silently using OpenFreeMap. Thanks to
[daikaginza](https://github.com/daikaginza) (#935).
- MCP setup examples use the app's default port, `4173`. Thanks to
[Huanyi Xie](https://github.com/xiehuanyi) (#934) and
[shirunjies8-png](https://github.com/shirunjies8-png) (#959) for the same fix.
- Voice revisits numbered analyst records through current layer snapshots and
preserves resolved pin coordinates. Requested analyst lists and rankings can
speak returned items alongside the exact count and coverage caveats. Failed
actions settle the voice card without reviving cancelled turns. Coverage
benchmarks reject invalid calls before accepting semantic matches.
- Street Level is included in the voice layer manifest for visibility toggles;
imagery is not exposed as countable analyst records.
- Voice debug logs omit complete tool-result bodies and serialized function
outputs by default, including location queries and generated spoken replies.
`GEV_VOICE_LOG_CONTENT=1` retains them for explicit content debugging.
- Unqualified Alps searches use the bundled European range for navigation
and annotations instead of a same-named peak returned by a geocoder.
Coordinates, supplied presets and geographically qualified place names
keep their precedence; annotation proximity and containment guards remain.
- Contacts analyst follow-ups retain the snapshot's distance ranking rather
than switching to the camera. Requested radii and explicit scopes remain
authoritative, and a request for a list still requires an analyst query.
Analyst speech names stale or degraded feeds and withholds authoritative
counts when unavailable. The existing NOTES disclosure preserves complete,
deduplicated coverage and source caveats, including crowded results.
- The voice card shows analyst counts ("At least 250,000 aircraft …") with
their scope, feed window and caveats, and marks partial answers. Analyst
speech uses the same deterministic headline, preserves lower bounds and says
when an answer is partial. Follow-ups retain unanswered-layer coverage, and
keep the original scope label when they narrow a remembered result.
Contacts-window answers read one immutable panel snapshot, mark a 20,000-row
layer cap as a lower bound, and commit that displayed cohort only after
cancellation checks pass. Concurrent analyst calls from one model response
remain independent; a stopped or replaced user turn still cancels them.
- Voice answers are shorter and fill slow work instead of going silent. Slow
or multi-step requests may open with one short spoken plan; instant ones
just happen. Tool results carry a code-built `say` line and a `display`
card: sources and notes stay on screen, a caveat is spoken only when it
changes the answer, and "at least" and partial answers are always said. A card above the mic shows captions, the plan's steps and the
result. When a tool that reports steps (layers, place lookups, outlines,
nearest-aircraft) is still running after 1.5 s its current step is spoken
once; others say "still working" once after 8 s. A soft
tick plays in push-to-talk. Holding Space while the assistant talks cuts it
off. Each turn writes latency and speech figures to the debug log
(`node scripts/voice-turn-spans.mjs`). Captions of what you say are
counted in the voice cost meter; the debug log leaves out what was said
unless `GEV_VOICE_LOG_CONTENT=1`.
- Point and ask: hold Space with the cursor on an aircraft, ship or spot on
the map and say "what's that", "track that one" or "how many flights
around here". A reticle marks the point and the voice card shows what
"this" meant. In open mic it works when you have just moved the cursor
there. "The second one" picks from the last numbered list. Asking about
"the last one" resolves to the last of the five rows actually shown, and
referent-only tracking calls are accepted while empty targets are rejected.
Asking about
bare ground up close gives the assistant a small crop of the map around the
point. A slow render gets one bounded second frame request, while hidden,
stale, moved-camera, invalid and oversized captures still fail closed.
## [Unreleased]
- Add a keyless Air quality layer to the Weather group, with Environment and
Climate Change Canada's AQHI as the first registered provider. Readings carry
`{ provider, scale, value, band }` so another network can be added without
inventing a shared numeric meaning across indices that do not share one; the
row and readout both state that coverage is Canada only. The WEATHER card
shows the band legend and the highest readings currently in view. AQHI is
reported as an integer from 1 with an open-ended "10+", so readings round to
that published form rather than the decimal precision the API returns.
Readings older than six hours are dropped, and the layer reports `stale`
through `getStats()` (also when every observation was dropped) so feed
provenance cannot describe an aged feed as live. Voice can switch it on and
query readings by value, band, station and observation time.
- Bound six upstream body reads (FIRMS CSV, CelesTrak TLE groups, adsb.lol
`/v2/mil`, TomTom flow tiles, OpenSky `states/all` and adsbdb lookups) with
streaming size caps that cancel the body at the cap or the route's deadline;
the adsb.lol military poll gains a deadline of its own. An oversized OpenSky
snapshot is not retried, and an OpenSky 429 starts its cooldown before the
body is read.
- Keep later satellites when a TLE catalog entry is missing an orbital line.
The parser skips the incomplete set and resumes at the next complete named
set, instead of losing the rest of the group (#906).
- Satellite clouds keep Clouds only / Full as quick endpoints and add a continuous
cloud-filter slider: 0% is Full, 100% is the existing brightness key, and
intermediate values blend the keyed alpha. The slider commits on release to
avoid restaging imagery for every drag event. Filter percentages round-trip in
share links; legacy mode codes retain their old endpoint meanings. Background
panel refreshes preserve the pending drag value until release. Contributed by
[NotProniss](https://github.com/NotProniss) (#1084).
- Street Level: Panoramax is the fourth provider, keyless. Light its chip
(orange; off by default, one provider at a time): from orbit dots show
where the federated commons has pictures, and below about 60 km its
sequences draw as lines from `api.panoramax.xyz` vector tiles. A click on a
line opens that sequence's picture nearest the click without moving the
camera, flat or 360°, with cones along the sequence around it and ‹ › /
← → following the picture's own links. The 360° and since filters apply,
in the lines and in the lookup. The caption names each picture's author
and licence (CC BY-SA 4.0, Licence Ouverte 2.0…) and links to it in the
Panoramax viewer. HD originals load once, only when the viewer is wider
than the 2,048 px version (a panorama: expanded), and every download stops
when the photo changes; an image whose header declares more than 64 MP is
refused before it decodes. Share links carry it as
`0.m.0_0.r.google-0*kartaview-0*panoramax-1` (`0.m.0_0.r.panoramax-1` works
too). KartaView's photo viewer
is now shared (`photoViewer.js`, `panorama.js`); in it, for KartaView too,
Esc clears the selected drive before it collapses the panel. Lines are
simplified and drawn within a point budget (a tile's unsimplified lines
over Paris hung the tab), decoded in slices so the globe keeps moving,
and kept; the cones' tiles have their own connection, and the open
picture's tile draws its cones before its neighbours arrive.
- Flights and Military Flights highlight emergency transponder broadcasts in
fleet billboards, 3D models and Cockpit contacts. Colors update when a status
starts or clears. Emergency squawks outrank ADS-B priority statuses; GEV
reports minimum fuel and lifeguard without red tint. Cockpit names the code
or ADS-B status, and analyst/voice results retain broadcast provenance and
the latest known contact time. One omitted ADS-B status poll during a source
switch may retain the previous status if the squawk is unchanged; an explicit
clear takes effect immediately. Broadcasts are not confirmed incidents.
Contributed by [Leo Pechnicki](https://github.com/leopechnicki) (#856).
- Street Level: KartaView is the third provider, keyless. Light its chip
(purple; off by default, one provider at a time) and zoom in below about
6 km: the lines are the streets KartaView has photos of (z13–14 tiles from
`api.kartaview.org`). A click on a line opens the photo nearest the click
without moving the camera, flat or 360° (a small WebGL panorama: drag to
look, wheel to zoom), with cones along its drive and ‹ › / ← → to step
through it. The caption links to the full-size photo (KartaView's photo
pages fail for signed-out visitors), and the globe credits "© KartaView
contributors, CC BY-SA 4.0". Share links carry it in the provider
switches (`0.m.0_0.r.google-0*kartaview-1`). Archived photos (KartaView
answers 409) are skipped by the click and by ‹ ›. Shift+← →, ↑ ↓, + − and
pinch look around a 360° photo. The open photo's marker is a purple view
cone pointing along the drive (KartaView's own compass headings are often
0 or far off). The IMAGERY (ALL / 360° / FLAT) and SINCE filters apply to
KartaView as to Mapillary: its lines are filtered by KartaView's own
server (its filtered PNG tiles, as a mask over the JSON lines), and the
photo a click opens, and the cones, by each photo's projection and upload
date. KartaView's SINCE is the upload date (all its server can filter by);
a note under the slider says so while KartaView is lit (`sinceBasis:
'upload'` in the provider contract).
Mapillary's line coverage and sequence cones are now shared by both
(`lineCoverage.js`, `sequenceCones.js`).
- Street Level: Google Street View is the second provider. On the Google 3D
map (Google's terms keep it off other maps), light its chip (off by
default: every panorama is billed to the Google Maps key, which needs the
Maps JavaScript API) and click a street, or press OPEN STREET VIEW, to
open Google's own panorama in
the panel, with its arrows, the address and month in the caption, a link
to Google Maps and FOLLOW. Share links carry it in the provider switches
(`r.google-1`). One provider is lit at a time (lighting one switches the
other off), Mapillary by default since it is free. Street View's panoramas
are all 360°, so the IMAGERY and SINCE filters and the legend apply to
Mapillary only and hide while GOOGLE STREET VIEW is lit; its globe marker
is a Google-blue view cone.
- Add an experimental ChatGPT/Codex OAuth option for cloud voice in Provider
Settings. API-key voice remains the default. Local sign-in can start from
the auth button and reports completion, failure, timeout, or expired
credentials. OAuth credentials stay on the server; local routes require
loopback access and same-site requests. OAuth sessions retain usage data
and show unknown cost; caption transcriptions are counted rather than
priced into the API-key cap. The auth button keeps keyboard focus after a
mode change, and pending sign-in does not discard text in the key fields.
Thanks to [Shayan Khan](https://github.com/devv-shayan) for #621 and
[TheSmokeDev](https://github.com/TheSmokeDev) for the credential handling
from #653.
- **Docker install path.** `docker compose up` builds on CI's Node 24.14.0 image,
pinned by digest, and serves the app on `http://localhost:4173` with no local
Node install. The repo is bind-mounted and the container runs as the host user
(never root), so `.env`,
`.gev-cache`, and `.gev-logs` persist on the host exactly as they do under
`npm run dev` — Provider Settings included. The launcher
(`scripts/docker-start.mjs`) trusts the container's gateway address for that
panel, since that is where Docker delivers the host's own browser from; the
opt-in behind it, `GEV_KEY_SETUP_TRUSTED_PEERS`, takes exact addresses only
and is unset (so loopback-only, unchanged) under every other launcher.
Thanks to [jklaze](https://github.com/jklaze) for finding and diagnosing the
container-to-host 403, and to [14traits](https://github.com/14traits),
[PoBruno](https://github.com/PoBruno) and [milu70hub](https://github.com/milu70hub)
for testing on Apple silicon, Docker Engine on Linux, and NAS hosts.
- Stdio servers from one install share a panel key so a page read from one
process can make requests through another. Concurrent malformed-key repairs
now select one winner; unavailable storage or a busy repair retains the
logged per-process fallback. Thanks to [Jibran Tahir](https://github.com/jibraaan)
for #958, [MarvinNL046](https://github.com/MarvinNL046) for the report and
proposed diagnosis in #927, and [kvnloo](https://github.com/kvnloo) for identifying
the repair race. Windows/Claude Desktop Cowork confirmation remains outstanding.
- Street Level: a street-level imagery layer modelled on the iD editor's photo
overlay, with Mapillary as its first provider (free client token, CC BY-SA 4.0
imagery). One right-rail panel holds a chip per provider, shared 360°/flat and
captured-since filters, and an embedded viewer with EXPAND, FIT/FILL and
FOLLOW (Google 3D only). Coverage lines and image cones are drawn from orbit
down to a single street; on Google 3D they sit on the bare earth, refined
against the rendered mesh near the camera, so trees and buildings hide them.
Share links carry the provider switches, the filters and the panel's collapsed
state. A server proxy caches Mapillary coverage tiles (24 h, 1 GiB on disk),
refuses cross-site requests, rate-limits per IP and backs off when Mapillary
rejects the token or rate-limits.
- The CCTV and Street Level panels are portable: drag the header to float the
panel, resize it from any edge or corner, and double-click the header to dock
it again. The position persists across reloads.
- Add Norway's city bikes to the Bike Share layer: Oslo, Bergen and
Trondheim Bysykkel (Urban Sharing), Kolumbus Bysykkel in Stavanger and
Farte Bysykkel in Skien/Porsgrunn (Entur Mobility), and Bysykkel
Lillestrøm (JCDecaux), about 760 stations in all. Every feed is keyless
GBFS. `gbfs.urbansharing.com`, `api.entur.io` and `api.cyclocity.fr` join
the proxy allowlist; the last two are kept to their GBFS paths. The proxy
now sends `Client-Identifier: gods-eye-view` on every request and
`ET-Client-Name: gods-eye-view-bikeshare` to Entur, as the operators ask,
and accepts Entur's extensionless feed paths. Attributed under NLOD and
Licence Ouverte. `get_bike_share` covers the six systems too.
- Add Norway's road cameras from Statens vegvesen as a CCTV pack. The camera
list is one keyless GeoJSON request to the agency's OGC API view of its
DATEX 3.1 CCTV table, so no DATEX account is needed. Every working camera
loads (~850; faulty ones are dropped) under one "Norway" category, and the
~135 working cameras that publish HLS play as live video through the existing in-memory
relay with the still as fallback. Frames and manifests are pinned to each
camera's own path on the agency hosts. `CCTV_VEGVESEN_ENABLED=0` disables
the pack, `CCTV_VEGVESEN_MAX_SOURCES` caps it (keeping cameras nearest the
largest cities) and `CCTV_VEGVESEN_VIDEO=0` keeps stills only. Attributed
under NLOD 2.0.
- Add Catalonia (Servei Català de Trànsit) as a keyless CCTV source pack: ~130
cameras from a WFS/GML feed that aggregates SCT's own highway cameras with
hotlinked Barcelona and Terrassa municipal cameras, each partner named as a
credit beside the shared provider. Ambient-card refresh paced to 3 minutes,
matching the empirically observed upstream cadence. `CCTV_CATALONIA_MAX_SOURCES`
sets the cap and `CCTV_CATALONIA_ENABLED=0` turns the pack off. The catalog
is fetched over https with redirects refused and a 1 MiB body cap, and frame
links carrying userinfo or an explicit port, or outside the publisher's frame
directory, are rejected even on an allowlisted host. Camera ids come from
each frame's SCT camera file or image path rather than the feed's
restart-dependent feature id, and rows the feed repeats collapse to one.
- Import your own GeoJSON, KML, KMZ and GPX files from DISPLAY or by dropping
them onto the app. Show, hide, fly to or remove each file for the session.
GeoJSON/GPX draw on the ground; KML retains its styles and explicit heights.
Large repeated-style exports use shared local pins, while recorded track
vertices and segment gaps stay intact. Imports respect newer camera gestures,
leave the shared clock alone, and report malformed or oversized files.
File bytes stay on the device; rendered overlays may appear in shared map
screenshots. Thanks to [Chase Mills](https://github.com/kapturner) (#925).
- GNSS Integrity (Events, voice-addressable, share token `3`) draws navigation
accuracy scores from a keyless regional adsb.lol sample; aircraft-level analyst
queries are unavailable for these aggregate cells. Cells do not intercept
map clicks. Pan/zoom refreshes automatically; feed failures retain the display
and explain the next retry. Aircraft-reported quality includes MLAT-positioned
contacts after GPS loss, excludes TIS-B/MLAT-derived quality, and locates GPS-loss
evidence at the last good GNSS position when available. Scores discount one
bad aircraft per cell and retain 30 minutes of visited-view evidence; they
do not confirm jamming. See [method and limits](DATA_SOURCES.md#gnss-integrity).
Contributed by [Leo Pechnicki](https://github.com/leopechnicki) (#855).
- Live HLS cameras play on a page opened over plain HTTP from another machine
(`HOST=0.0.0.0`). The client lease id came from `crypto.randomUUID`, which
browsers only expose in secure contexts, so starting a live feed threw
before playback. The id now falls back to a v4 UUID built from
`crypto.getRandomValues`, which the server's lease check accepts.
- Move Google geocoding behind the local server. Forward and reverse lookups now
go through `/api/google/geocode` and `/api/google/reverse-geocode` with the
server key, joining Places and Street View. Google's Geocoding web service
refuses referrer-restricted keys, so the previous browser call left
`SECURITY.md`'s advice and working search mutually exclusive: the bundled
browser key had to be unrestricted for search to work at all. That key now
needs only the Map Tiles API and the Maps JavaScript API (Street View). Keyless sessions and the Photon/Nominatim
fallback order are unchanged.
## [0.2.1] — 2026-10-02 — God's Eye View through Your Agent (with security fixes and other features)
- Ship each bundled data pack once. The region, marine, admin-boundary,
county, military-name and neighborhood packs were emitted twice by the
production build, as the JSON the browser fetches and as an unused
JavaScript copy; `dist/` drops from 54 MB to 42 MB. Under Node the loader
reads the JSON file directly (reporting that Node 24.14 or newer is needed
on a runtime too old to do so), and a test keeps app code from importing a
pack as a module.
- Apply the Host check before the app's own routes. Vite installs its Host
check after the middleware that plugins add, so the provider and `/api`
routes used to answer any Host, including a DNS-rebinding name, in every
mode. A first-running middleware now applies the same allowed hosts on the
dev and preview servers.
- Refuse cross-site browser requests to the cost-bearing and log endpoints
(`/api/realtime/token`, `/api/openai/hud-summary`,
`/api/google/nearby-places`, `/api/google/text-search`,
`/api/realtime/debug-log`): a foreign or opaque
Origin, a cross-site `Sec-Fetch-Site`, or proxy forwarding headers get 403,
while loopback tools and LAN use keep working. The dev and preview servers
send one shared Content-Security-Policy (James Sumpter, #242).
- The voice debug log records the server's own time: a record can no longer
supply its `loggedAt`. The dev and preview servers also send
`X-Content-Type-Options: nosniff` (findings by Sunil, #710).
- Keep the Host-header check when binding to all interfaces. `HOST=0.0.0.0`
used to accept any Host; the dev and preview servers now accept IP
addresses, `localhost` and the LAN hostnames listed in `GEV_ALLOWED_HOSTS`
(suffix and wildcard entries are ignored), which also keeps DNS-rebinding
names out in LAN mode. The `.local` suffix is no longer accepted by default;
list such a name explicitly (Puspo Aditya, #97, fixes #21).
- Throttle the cost-bearing proxies by default instead of on request. The
OpenAI endpoints (`/api/realtime/token`, `/api/openai/hud-summary`) now allow
30 requests per minute per client IP and the Google Places endpoints
(`/api/google/nearby-places`, `/api/google/text-search`) 120 — the caps the
Pinokio build already ships, so the packaged app is unaffected and only an
unconfigured server changes, from unlimited to what the product already runs
with. `GEV_RATELIMIT_OPENAI_PER_MIN` and `GEV_RATELIMIT_GOOGLE_PER_MIN` still
override the caps, and exactly `0` disables them; a value that cannot be read
as a number now falls back to the default rather than to unlimited, so a typo
cannot silently disarm the guard (daikaginza, #683).
- Tighten the local MCP server and embed mode. The panel's `panel_request`
needs the key in its MCP server's panel page, and refuses Provider
Settings, credential and model endpoints, `/mcp` and development server
routes in any letter case, encoding or dot suffix; panels on one server share six
requests in flight, and further requests wait their turn. `/mcp` applies Provider Settings' proxy and sharing checks,
requires a Host on the port it reached and an Origin from that host, and
times out request bodies after 30 seconds; stdio honors
`notifications/cancelled`. Embed mode is no longer framable unless
`GEV_EMBED_FRAME_ANCESTORS` allows the framing page, and view answers go
only to the origin that sent the view. SECURITY.md describes the MCP surface
and the panel's browser keys.
- Cockpit now enters on the existing matching map style while keeping one fixed,
duplicate-free carousel over `Normal / CRT / NVG / FLIR / Anime / Noir / Snow`.
Normal remains a real unfiltered option; Cockpit-only choices still restore
the captured map style through both Exit Cockpit and Reset.
- Cyber's compact right-rail and Cockpit utility buttons now center their glyphs
vertically and share the same inset and edge alignment.
- Keep Cyber Voice help/error popups and Location/Visual Presets pins clear of
their decorative frames. Leave space above attribution for its full logo row.
- Add an intentionally future-facing, opt-in panel surface contract for new
panels to inherit compatible Normal, Cyber and Cockpit styling. Its first
production adopter will land separately after this change.
- Restore the user's previous visual preset when they explicitly switch from
Cyber to another HUD layout, without overriding scene or shared-link state.
- Move the aligned Cyber side-panel rails upward on desktop so the left stack
clears the lower coordinate card; keep Cockpit's independent visor layout.
## [0.2.0] — 2026-10-02 — God's Eye View through Your Agent
- Show God's Eye View inside AI conversations. Answers that can be shown
include a view (camera, layers, style, map, marks, something to follow),
and `show_in_gods_eye_view` displays it as the live globe in clients that
support MCP Apps, such as Claude Desktop and the Codex and ChatGPT desktop
apps, and as a link everywhere else. The panel loads the app's panel build
(`npm run build:panel`) and its data through the MCP server, so a local
server needs no HTTPS or tunnel. `?embed=1` shows the globe alone for pages
that frame the app.
- Add tools for language-model clients and a local MCP server, served over
stdio by `npm run mcp` and over HTTP at `/mcp` on the development and preview
servers for local requests only. `npm run mcp`
serves earthquake, active-fire, launch, aircraft, ship, satellite, camera, radio,
place, routing, bike-share, transit, traffic, weather, cyclone, fire-perimeter,
terrain, installation and map-feature queries, plus a situation brief, over
stdio to clients such as Claude Code, reading
from a running app. Tools are defined
once in `gods-eye-view/tools`, reuse the layers' source factories, and are
exposed through the protocol adapter in `gods-eye-view/tools/mcp`. The
catalog also covers weather maps, wind, recent imagery, submarine cables,
license plate reader cameras, datacenters and dams, the Bhote Koshi flood,
military awareness and links that open the app over an area with layers on.
Voice offers the same queries next to its app actions.
- Public Overpass instances are no longer used by default. Street Traffic
roads come from TomTom flow tiles, OpenFreeMap vector tiles, or both, chosen
on the layer row (TomTom / OSM / Hybrid) or with `?trafficRoads=`. With a
TomTom key the default is Hybrid: TomTom roads with live flow, plus
OpenFreeMap roads TomTom does not cover, simulated. Without a key every
choice draws OpenFreeMap roads. TomTom mode shows only roads with flow; OSM
mode matches TomTom flow onto OpenFreeMap roads for congestion colors,
speeds and closures, and unmatched roads stay simulated. Road failures name
OpenFreeMap and retain HTTP status or timeout reasons separately from TomTom.
Flow coverage counts
rendered dots on roads with flow; mapped military areas come from OpenFreeMap and
follow settled camera changes with cached tiles and retained site entities.
Superseded requests preserve the next view’s pending load.
Tile and API transports can be injected independently; the optional Overpass
ALPR adapter remains available.
OSM-derived layers share one attribution entry and a persistent inline map credit,
including routing, Warendorf cameras, datacenters, dams and the Nepal locator.
Military areas use bundled Overture/OSM names; wide views show bounded,
decluttered named points that follow camera motion while Contacts holds a subject,
using the shared world-overlay host for wide-point and polygon titles. Polygons appear while names load; cancelled views
cannot publish late names, and stalled name downloads can retry. Merged groups
keep their identity and parent name when a pan hides the largest member. Late
names reconcile ids across zooms while retaining selection and marker ownership. Wide
named points remain visible until matching close polygons take over. Installation
titles share datacenter/dam card arbitration and keep incumbents while panning.
Selecting an installation replaces its label with one card; deselection restores it.
Selected footprints receive a translucent fill draped on the active map surface.
ALPR cameras come from an hourly OpenStreetMap extract (US and Canada). Features
without a replacement say they are unavailable; area and footprint
annotations check once whether an Overpass instance is configured and skip
the query when none is. Area annotations outline countries, states and provinces
(Natural Earth, including UK constituent countries) and US counties (US Census Bureau) from bundled data, with no
lookup. County names are disambiguated across countries by aliases, qualifiers
and geography. `OVERPASS_UPSTREAMS` sets an
Overpass instance you run or pay for. The cockpit regional brief resolves
regions from bundled Natural Earth data instead of Nominatim. Traffic starts on enable and paints
locally grounded roads incrementally, shares concurrent tile requests and
reuses validated heights across pans. Camera moves and arriving tiles retain
existing traffic dots on their roads; budget changes fade in/out incrementally,
height refinements ease vertically, and live flow changes color and speed in
place. The traffic footprint follows the reticle square at oblique angles, with
cached detailed near tiles and coarse distant roads. Failed detail tiles retain
coarse roads and retry at most three times. Road-pass deadlines also cancel
queued tile paints and terrain callbacks;
off-screen height corrections cannot hold loading open, and visible corrections
stay pixel-limited at canvas and camera-plane boundaries. Completed road snapshots replace
streamed previews without duplicating roads. Unresolved previews no longer delay or suppress detailed street roads.
Road admission excludes private, parking, walking and unknown traffic categories;
OpenStreetMap service ways and tunnels no longer receive surface vehicles.
Detail tiles load alongside previews, arrival bypasses the movement debounce,
and geographically validated rendered depth avoids repeated mesh redraws.
Traffic releases surface-frame listeners on disable/destroy and reuses unchanged
surface identities without frame-by-frame allocations.
Grounded dots respect building occlusion instead of drawing through roofs,
and the traffic status chip reports completion without a delayed text animation.
Short road chunks and local surface elevation keep the budget on visible
streets in elevated cities. Congestion and closures respect travel
direction. ALPR distinguishes unsupported coverage from empty results and
asks for zoom-in before exceeding its tile budget. Installation footprints
retain visible fragments without joining separate parcels across zooms or
across quantization gaps between different mapped identities. Keyless
terrain tiles retry HTTP 429 and transient gateway failures with bounded,
shared backoff. Operator-configured Overpass area and footprint queries
retain relation member geometry so their outlines remain available.
Contacts filters mapped installations to a true 100 km surface radius around
the current tracked subject,
including in Cockpit, instead of "?" or nothing. Search arrivals frame against the resolved
ground and lift the eye above the rendered surface, so Camp Mabry and Denver
no longer land underground (Milan Khanal, #118). Arrival corrections yield to
new camera owners and are cancelled on layer/app teardown. ALPR floor preparation
and marker placement share terrain requests, cancelled when the layer is disabled.
Map-source changes reposition every ALPR marker without replacing entities. ALPR loads
whole-city views from z9-z12 tiles, drops native ground wedges and clamping,
keeps frame time with ALPR on within a few percent of ALPR off, seats nearby
badges on the rendered surface and says when no loaded camera is on screen.
- CCTV cameras whose bearing is a guess now say so. Packs mark bearings derived
from a hash of the camera id as `headingConfidence: 'low'`, but nothing read the
flag, so roughly 70% of a default catalog rendered like surveyed facings. The HUD
@@ -111,8 +740,34 @@
(`src/ui/imagerySplit.js`, `src/maps/imageryComparison.js`), and
`MapSourceController.subscribe()` reports every settled map switch.
## Unreleased — voice reaches every layer; honest analyst answers
- Voice can switch on every shipped data layer (the two scene-driven
Bhote Koshi layers stay scene-only), including transit, Recent
Imagery, wind, the weather layers, cyclones and mapped installations, and
understands their spoken names ("buses", "hurricanes", "military bases").
One voice manifest (`src/voice/layerManifest.js`) generates the tool enums
and aliases, and a unit test fails when a new layer has no entry.
- `analyst_query` counts up to 250,000 loaded records per layer instead of the
first 2,000, and says when a layer went past that (`complete: false`). It
also answers over bikeshare stations, transit vehicles, rocket launches,
cyclones, ALPR cameras, mapped installations, local ADS-B aircraft and fire perimeters; fire
records carry their sensor (VIIRS or MODIS).
- Unknown fields, operators, units, value types, scope kinds and invalid
centres are refused with the allowed values instead of answering zero or widening to anywhere. A
layer that is off, still loading or unavailable is reported as such, not
as a count of zero; a partly answerable query is marked `partial`.
Distance sorts honour `sortDir`, a written unit such as `altitudeM(ft)`
converts, and large rankings no longer sort the whole set.
- Results carry `lat`/`lon` for each item and a `display` object with the
scope, the feed window (earthquakes and fires cover the last 24 h) and any
caveat for the screen. The model is asked to answer in one short phrase.
- The weather and Recent Imagery panels can be opened by voice.
## Unreleased — local receiver feeds
### Local receiver feeds
- The Local ADS-B layer also reads local 1090 MHz and 978 MHz UAT decoder
feeds: the `aircraft.json` that dump1090-fa, readsb, tar1090 or skyaware978
serves. Configure them server-side with `LOCAL_RECEIVER_FEEDS`
@@ -140,7 +795,7 @@
- Records carry `band` (`1090`/`978`) and `source` (`webusb`/`feed`).
- See `docs/LOCAL-RECEIVERS.md`.
## Unreleased — local RTL-SDR and Local ADS-B
### Local RTL-SDR and Local ADS-B
- Add a Local RTL-SDR card to the Radio panel. It connects a USB RTL-SDR in
desktop Chrome or Edge through WebUSB and receives broadcast FM (tune, seek,
@@ -165,7 +820,7 @@
- Add `@jtarrio/webrtlsdr` and `@jtarrio/signals` (Apache-2.0); see
`THIRD_PARTY_NOTICES.md`.
## Unreleased — weather review
### Weather review
- On 3D Tiles, draw a 4096×2048 detail window around the view on each
observed-weather shell except global infrared, sampled by the shell's own
@@ -253,6 +908,7 @@
Add feed provenance to analyst/view answers and HUD context while retaining existing response fields and runner ownership (Matt Van Horn, #347).
Analyst records for loaded satellites, datacenters and dams, with explicit bounded count/rank coverage (Matt Van Horn, #351).
- New Fire Perimeters layer (Events group): live NIFC WFIGS interagency
wildfire incident perimeters as ground-clamped polygons with a
containment-colored fire line, refreshed every 5 minutes from the public
@@ -431,26 +1087,26 @@ Analyst records for loaded satellites, datacenters and dams, with explicit bound
- Split application scene, controls, catalog, tools and HTML into reusable components; configure application request services and sources without changing global fetch. Preserve standalone markup and voice behavior. Explicit annotation navigation may resolve a distant named target.
## Satellite pass prediction
### Satellite pass prediction
- Bisect pass rise/set to ~0.2 s and fit peak elevation with a parabola.
- Mark passes visible from Earth-shadow and civil-twilight checks.
- Add `getNextSatellitePass(noradId, options)` for any loaded catalog satellite.
- `next_iss_pass` retains the next geometric pass and adds visibility metadata. `next_satellite_pass` adds bounded loaded-catalog name/NORAD lookup and optional visible-only filtering (Rehaan Delmotra, #451; maintainer adaptation).
## Voice component boundaries
### Voice component boundaries
- Separate voice controls, Realtime connection requests and the action runner.
- Allow compatible endpoints and server-selected models through construction options.
- Cancel pending token/SDP requests on Stop or teardown and reject expired secrets.
## Configurable geospatial services
### Configurable geospatial services
- Compose geocoding, place context and routes through independent providers.
- Allow compatible endpoint configuration without changing voice tools or annotation behavior.
- Isolate configured source caches and reject results after cancellation.
## ALPR camera locations
### ALPR camera locations
- Port Manjunath's (@manjunath22466) cyan camera badges, coral selection brackets,
gradient direction wedges and animated tactical labels into the reusable ALPR
@@ -470,32 +1126,32 @@ Analyst records for loaded satellites, datacenters and dams, with explicit bound
- Separate the request adapter, camera model, presentation, and instance lifecycle.
Source cancellation also guards late response bodies and rejects invalid query bounds.
## Release disabled infrastructure rendering
### Release disabled infrastructure rendering
- Remove built Data Center, Dam and Submarine Cable entities when their layers
are disabled, avoiding retained visualizer work and entity memory.
- Keep parsed datasets cached for re-enable; rebuild entities without refetching.
## Camera layer components
### Camera layer components
- Separate camera source requests, placement, frames, projection, cards and calibration.
- Own visibility listeners and pending initialization within each layer lifetime.
- Preserve existing camera catalogs, URL families, geometry and playback behavior.
## Traffic and bikeshare components
### Traffic and bikeshare components
- Separate traffic loading, animation, styling and lifecycle into factory-owned components.
- Give each flow source its own bounded decode cache and cancellation checks.
- Separate bikeshare registry, station requests, rendering, selection and proximity handling.
## Installation and context components
### Installation and context components
- Separate mapped-site requests, records, placement, selection and viewport lifecycle.
- Separate proximity queries, subject tracking, navigation/history, panel and direction rendering.
- Retain source and ground-floor ownership in standalone composition; reject malformed
installation snapshots and ignore failures from cancelled requests.
## Satellite and mission layer components
### Satellite and mission layer components
- Separate catalog loading, orbit calculations, display, tracking and interaction
into instance-owned satellite components.
@@ -503,20 +1159,20 @@ Analyst records for loaded satellites, datacenters and dams, with explicit bound
operations, retaining existing layer controls and satellite coordination.
- Cancel late mission source work and reject malformed launch snapshots.
## Fire layer components
### Fire layer components
- Split fire source loading, state, rendering, cards, selection and viewport work
into reusable components with application-owned scene services.
- Cancel late refreshes, retain good data after malformed responses, and preserve
selection identity without repeating a user-selection notification on refresh.
## Earthquake components
### Earthquake components
- Separate earthquake snapshot loading, record validation, and display ownership.
- Cancel pending earthquake refreshes on disable or destruction, retaining the
last good snapshot after malformed or failed refreshes.
## September 8, 2026
### September 8, 2026
Earthquake refreshes validate the complete feed and construct replacement entities before clearing the previous snapshot. Malformed rows and duplicate rendered IDs retain the last good entities, overlays, count and timestamp and report a malformed response; unknown magnitude is excluded from M2.5+ rendering.
@@ -527,7 +1183,7 @@ Launch payloads with missing records now say PAYLOAD DATA UNAVAILABLE. Missing n
This changelog records public product changes. For the authoritative description
of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md).
## [Unreleased]
### Other changes
- Add ECMWF IFS model selection to Wind (#464, thanks @beneduzi), with model-scoped forecast-step caches, cancellation of replaced requests, and separate issue/valid timestamps.
@@ -547,7 +1203,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
- Separate submarine cable sources and rendering components, and export bundled geography lookup modules.
### Added
#### Added
- DISPLAY ▸ Draw: draw on the world by hand. Pick Area, Line or Pin, click the
vertices, double-click or press Enter to finish, label and colour it; Backspace
@@ -557,7 +1213,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
together. While you are drawing, the draw tool owns the pointer and no layer
selects what you click through (#235 — thanks @cora-fresh-labs).
### Fixed
#### Fixed
- Keep traffic-road bounds crossing the antimeridian monotonic and inside the
longitude range accepted by the Overpass request path, preserving the small
@@ -624,7 +1280,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
toggle. Camera departure cancels pending work, arrival checks the final view,
and superseded requests cannot keep a newer view loading.
### Added
#### Added
- Add MODIS NRT (Terra+Aqua, ~1 km) active fires to the FIRMS layer, sharing the
existing `FIRMS_MAP_KEY` and 30-minute cache.
@@ -752,9 +1408,9 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
- Extract shared surface keyboard handling for the welcome launcher and Provider
Settings, preserving Tab/Escape behavior and releasing the listener on teardown.
### Added
#### Added
### Security
#### Security
- The CCTV media route no longer forwards a client `Range` header to the upstream
camera host as it arrived. A single `bytes=` range is canonicalized and
@@ -785,7 +1441,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
- Cancel the active location lookup when its controls are disposed.
### Fixed
#### Fixed
- `DATA_SOURCES.md` states what the project does with camera frame content: a
successful upstream response is relayed as the provider served it, nothing in
@@ -864,7 +1520,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
fetching, AIS records/tracks and shared request helpers; preserve existing
routes, local setup, fallback behavior and rendering.
### Added
#### Added
- **Directions layer** — keyless A→B directions without a geocoder or a
microphone (thanks @spcpza). The row's chips arm a globe click for A and B
@@ -892,7 +1548,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
voice routes since launch, previously uncredited), with the OpenStreetMap
credit and the "fix the map" link the service's usage policy asks for.
### Changed
#### Changed
- The interface asks Google Fonts for only the icon glyphs it draws, instead of
the whole variable icon font, and no longer requests a second icon family that
@@ -907,7 +1563,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
- Rename standalone browser startup to `src/standalone/` and add a Node-only
`gods-eye-view/build/vite` export with checked package ownership.
### Development
#### Development
- The CCTV launcher and preview-server tests resolve their temporary fixture
root through `fs.realpath`, so they pass on macOS, where the system temp
@@ -941,7 +1597,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
infrastructure modules and their consumer tests. Package boundary checks keep
those exports separate from app startup and local Node services.
### Fixed
#### Fixed
- Reduce terrain-height timeouts when Re:Earth slows down. Batches are
sized against measured response latency on both browser and server to reduce
@@ -1032,7 +1688,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
and upstream error bodies; response statuses and cache fallback remain intact.
Includes the security fixes contributed by Tom-Neverwinter in PR #171.
### Fixed
#### Fixed
- Map Source keyboard opening retries focus until the selected tile is visible.
Leaving the disclosure, pointer interaction, or closing the tray cancels the
@@ -1074,7 +1730,7 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
that had since recovered. A miss is now cached only when every source
consulted actually returned a verdict.
### Added
#### Added
- Keyless place search. The LOCATION search box and the `fly_to_location` voice
tool now resolve place names through Photon (komoot, over OpenStreetMap) when
@@ -1094,6 +1750,13 @@ of current runtime behavior, see [`docs/CURRENT-STATE.md`](docs/CURRENT-STATE.md
to Puppeteer 25.10.0 and Sharp 0.35.4. Cesium remains on 1.138.0.
Browser QA awaits the new asynchronous executable-path lookup.
### Live CCTV video
- Live HLS video shares one decoder between the camera panel and projection,
with a DelDOT HTTPS source pack. Credit: Daniel Slay (@Danielslay86), PR #489.
- Maintainer adjustments bound sessions and downloads, remove disk/subprocess
remuxing, reject redirects, and clean up playback on switching or disabling.
## [0.1.1] — 2026-09-01 — Installation and live-data fixes
### Changed
@@ -1330,10 +1993,3 @@ represent previously published GitHub Releases.
## [0.1.0] — 2026-02-09
- Initial project version.
### Live CCTV integration candidate
- Live HLS video shares one decoder between the camera panel and projection,
with a DelDOT HTTPS source pack. Credit: Daniel Slay (@Danielslay86), PR #489.
- Maintainer adjustments bound sessions and downloads, remove disk/subprocess
remuxing, reject redirects, and clean up playback on switching or disabling.