Commit Graph

62 Commits

Author SHA1 Message Date
itsrubberduck
5de5f6c834 feat(atis): serve the resolved ATIS from /api/airports/:icao/atis
Composes the three live sources into one AtisReport: VATSIM ATIS stations,
the METAR, and the OpenAIP runway ends the frequency endpoint was already
fetching and discarding.

The upstream fetches move into server/utils/airportSources.ts with a TTL cache
matched to each source (VATSIM 20s, METAR 5min, OpenAIP 6h). Without it, adding
this endpoint would have meant pulling the multi-megabyte VATSIM datafeed twice
per session start; the frequency endpoint now shares the same cached copy.

Verified against live data: EDDF (no VATSIM ATIS) synthesises information I with
runway 25C from wind 260/14, while EDDC and EDDM take letter and runway from
their live VATSIM broadcasts.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-26 19:37:16 +02:00
itsrubberduck
a53442b1d1 fix(tts): back to fast Piper controllers, classroom voice setting
Kokoro-82M generates several times slower than Piper — since the controller
pool moved onto it, every ATC reply arrived seconds late. Controllers return
to distinct Piper speakers with the standard US voice (ryan) as the product
default, so replies are fast again and the default sounds like before.

The classroom gets an instructor-voice setting: standard US voice by default,
'random per module' (stable instructor per module), or one of ten named
US/GB voices.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-19 12:36:19 +02:00
itsrubberduck
8c9bb2f988 feat(tts): curated Kokoro+Piper radio voices, classroom instructor from pool
Controllers now speak with the four Kokoro speakers (bm_george, bf_emma,
am_michael, af_heart — heard most, best quality), pilots with six distinct
Piper speakers (alan, alba, joe, amy, bryce, kristin); ATIS moves to the
dedicated ljspeech broadcast voice. The classroom instructor draws a stable
controller-pool voice per module when the user hasn't configured one, and the
TTS cache key follows the effective voice.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-19 11:50:30 +02:00
itsrubberduck
70260cac1e feat(tts): dedicated ATIS broadcast voice on Speaches
The ATIS tag now resolves to en_GB-alba-medium — outside both voice pools —
instead of sharing 'verse' with the user's own readback voice.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-19 11:22:44 +02:00
itsrubberduck
2a8875a7f3 feat(tts): map logical pool voices to distinct Piper speakers on Speaches
Until now the Speaches branch sent every request to the single env-configured
model (de_DE-thorsten — a German voice for English radio), so the voice pool
had no audible effect. A server-side registry now resolves the logical voice
ids to disjoint controller/pilot Piper speakers; unknown ids keep the env
fallback and the cache key follows the resolved pair.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-19 10:45:49 +02:00
itsrubberduck
3c284716bb fix(websim): authenticate bridge connection in dev 2026-07-16 19:05:59 +02:00
itsrubberduck
4799b2b89f feat(websim): browser A320 cockpit to test /live-atc without MSFS (WIP)
Flight model (ground/air physics, SELECTED/NAV/APPR/AUTOLAND autopilot with
STAR sequencing and ILS capture), bridge client that feeds the existing
/api/bridge/* endpoints so /live-atc can't tell it apart from a real bridge,
and the cockpit UI (PFD reuse, FCU, radio panel, Leaflet ND, three.js
exterior, spawn presets at EDDF/EDDS). Design doc:
docs/plans/2026-07-16-websim-design.md.

Also adds a local-dev-only auto-login (/dev-login, server/api/dev/login.post.ts)
that bypasses the invite-only login and MongoDB entirely via a fixed in-memory
user, so require-auth pages are reachable for local testing even when the dev
DB is unreachable. Hard-disabled outside development.

Status: unit tests green (yarn test) and typecheck clean (yarn typecheck).
Browser walkthrough of the actual cockpit (flying a preset, confirming
telemetry reaches /live-atc) is not yet done — picking up from a fresh dev
server + /dev-login?redirect=/flightlab/websim confirmed the spawn screen
renders past auth, but full instrument/map/exterior verification is still
outstanding.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-07-16 18:49:31 +02:00
itsrubberduck
ab04411bc5 feat(sim-control): wire frequency-sim-control command channel end-to-end
Implements the open items from docs/plans/2026-07-14-frequency-sim-control-design.md
§4/§"Offen für die Implementierungsphase": a per-bridge-token in-memory command
queue piggybacked on the existing telemetry channel, plus the client-side gate
and TTS confirmations.

- server/utils/simControlQueue.ts: TTL-based queue keyed by bridge token
  (enqueue → drainPending → resolve → drainResultsForClient).
- server/api/bridge/data.post.ts: response gains a `commands` field the
  bridge drains on its next telemetry POST.
- server/api/bridge/command.post.ts (new): client enqueues a parsed command,
  re-validated server-side via isValidSimControlCommand.
- server/api/bridge/command-result.post.ts (new): bridge reports ok/failed.
- server/api/bridge/live.get.ts: response gains `commandResults` so the
  client can announce outcomes.
- shared/utils/simControl.ts: wire types, isValidSimControlCommand, and
  simControlRejectionSpeech/simControlResultSpeech TTS phrasing.
- useLiveAtcSession.ts: parseSimControl() gated on bridgeConnected, wired in
  right after the local special cases and before the frequency check —
  matched commands never reach radioBackend.transmit().
- useSimBridgeSync.ts / live-atc.vue: bridgeToken threaded through, command
  results forwarded from the telemetry poll to TTS.

43 new tests (shared parser/validation/speech + server queue lifecycle/TTL).

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-07-15 09:31:17 +02:00
itsrubberduck
9b245a3f07 fix(onboarding): also ask OS for X-Plane, not just 'other'
X-Plane runs on Windows/Mac/Linux same as any non-MSFS sim, so it
should trigger the OS follow-up too.
2026-07-09 17:26:11 +02:00
itsrubberduck
dc2a8760cf feat(onboarding): add sanitization and callsign computation helpers 2026-07-09 16:25:29 +02:00
leubeem
9802c438a5 feat(pm): LLM routing endpoint, usage capture, and admin review view
Backend counterpart to the Python engine's semantic router.

- POST /api/decision/route: service-secret-guarded endpoint the Python
  backend calls on regex-miss. Calls gpt-5-mini (ROUTER_LLM_MODEL),
  validates the chosen id against the candidate set, and writes both a
  UsageEvent (central cost ledger) and a routing-review record — including
  timeouts, with timeoutMs + actual latencyMs — so the budget can be tuned
- LlmRoutingDecision model + GET /api/admin/llm-routing (paginated,
  status-filtered, per-status counts)
- admin "LLM Routing" tab: transcript vs expected phrase, candidate chips
  with the chosen one highlighted, latency/budget chip, model reason
- serviceAuth util (mirrors CRON_SECRET pattern)
- .env.example: ROUTER_LLM_MODEL, SERVICE_SECRET

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-29 10:27:57 +02:00
itsrubberduck
d9e9be2b54 hotkey support 2026-06-20 03:17:53 +02:00
leubeem
0b7345ced7 feat(server): per-user AI usage tracking, cost alerting, and endpoint hardening
Usage tracking:
- new UsageEvent collection records every STT/TTS/LLM call per user with
  provider, model, volume (audio seconds, characters, tokens) and an
  estimated USD cost; self-hosted providers (Speaches/Piper) and cache
  hits record at $0
- pricing table for whisper-1, tts-1, gpt-5-nano & co. in server/utils/usage.ts
- weekly KPI mail gains an "AI-Nutzung & Kosten" section: weekly and
  rolling 30-day cost, per-kind breakdown, top 5 users by cost
- quota alert mail when rolling 30-day cost exceeds USAGE_ALERT_USD
  (default $5), at most once per calendar month (UsageAlertDelivery)

Hardening:
- /api/atc/say now requires an authenticated session (middleware
  exemption removed); useFlightLabAudio sends the bearer token
- /api/service/tools/latency requires auth (was a public LLM endpoint)
- per-user rate limits: PTT 20/min, say 60/min, latency 5/min
- cron endpoints (waitlist-drip, weekly-kpi-report) require a shared
  secret via ?secret= or x-cron-secret (CRON_SECRET, falls back to
  KPI_CRON_SECRET); allowed with a warning while unset so existing
  deployments keep working
- PTT records the actual transcribed audio duration for billing accuracy

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-10 23:17:03 +02:00
leubeem
76ab765069 Cleanup old unused code and add id sessionId to /api/atc/ptt 2026-05-20 14:13:26 +02:00
itsrubberduck
4a01593612 fix typescript errors and update dependencies 2026-02-17 18:13:04 +01:00
itsrubberduck
25e4f77ca3 add server log 2026-02-17 15:31:32 +01:00
itsrubberduck
562ad236a2 use 6 digit codes for bridge 2026-02-16 15:47:12 +01:00
itsrubberduck
ae0f0b0f86 Unify bridge auth header and add live telemetry panel 2026-02-15 16:04:07 +01:00
itsrubberduck
52734e8d8b feat(flightlab): sidebar, progress bars, skip speech, SimBridge telemetry & auth
- Add collapsible sidebar with phase stepper (jump between phases)
- Add SimBridge conditions panel in sidebar (live values, progress bars, targets)
- Add global progress bar (top edge, glowing) + phase-local TTS progress bar
- Add skip button to skip TTS speech while ATC is speaking
- Add skipSpeech() to audio composable (stops current Pizzicato sound)
- Wire up bridge data.post.ts with user auth (JWT) + example payload
- Add server-side telemetry store with pub/sub for Bridge→WS relay
- Extend WS handler with subscribe-telemetry message + userId tracking
- Extend sync composable with subscribeTelemetry() + onTelemetry() callback
- Add require-auth middleware to all flightlab pages
- Fix instructor station ECONNREFUSED via import.meta.client guard
- Add animations: phase transitions, button lists, fade-scale, check-pop, pulse

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-14 10:14:33 +01:00
itsrubberduck
cabdc8db6d fix pm 2026-02-13 08:50:02 +01:00
Remi
291c18ed03 Normalize taxi routes for clearer speech 2025-10-18 21:29:56 +02:00
Remi
3dbf7c2bc6 Add reply-to support for admin notifications 2025-10-18 16:33:06 +02:00
Remi
d0f3d07200 feat: surface pilot intent from llm decisions 2025-10-16 21:07:21 +02:00
Remi
649cae11bc feat: integrate llm-backed routing with fallback 2025-10-16 19:55:13 +02:00
Remi
18f25998f5 Allow configuring OpenAI base URL 2025-10-16 11:15:31 +02:00
itsrubberduck
651a41106f merge 2025-10-12 15:42:18 +02:00
Remi
fc7d5f59e2 Add waitlist invitation sending from admin 2025-10-07 12:34:02 +02:00
Remi
79c2cd4870 Simplify decision routing to avoid unnecessary LLM calls 2025-09-25 23:47:05 +02:00
Remi
fd2ac100ce Align regex auto selection trace with LLM decisions 2025-09-25 23:35:23 +02:00
Remi
60d7d2d89e Refactor route decision selection 2025-09-25 23:00:31 +02:00
Remi
b756bf2ea6 Point bridge download to GitHub 2025-09-24 00:01:00 +02:00
Remi
7f2585c211 Improve flow activation handling and expose active nodes 2025-09-23 23:12:02 +02:00
Remi
fbec5c4830 Add session timeline logging and admin sessions view 2025-09-21 23:08:10 +02:00
Remi
6c9f467b94 Enable flow-aware decision routing 2025-09-21 21:16:33 +02:00
Remi
e31b2d9289 Extend access token lifetime 2025-09-20 20:53:06 +02:00
itsrubberduck
137bc84276 stash 2025-09-20 16:36:35 +02:00
itsrubberduck
409f9d5c20 merge 2025-09-20 09:50:20 +02:00
Remi
440aef2f62 Fix remaining German comment 2025-09-20 09:46:34 +02:00
Remi
341a39e7d8 refactor: share llm decision types 2025-09-20 09:27:45 +02:00
Remi
df68719374 refactor: centralize radio speech normalization 2025-09-19 09:20:04 +02:00
Remi
43f2f42238 Add waitlist admin view and log OpenAI decision traces 2025-09-18 23:30:56 +02:00
Remi
b6785e9f05 Fix admin notifications formatting 2025-09-18 19:54:04 +02:00
Remi
74da40cc87 Add readback correction states and improve validation 2025-09-18 19:54:04 +02:00
Remi
8020a4a285 Refine ATC decision routing and ATIS handling 2025-09-18 19:41:32 +02:00
itsrubberduck
8ea2ae28d2 log llm call body 2025-09-18 18:21:01 +02:00
Remi
03b86ae637 Add ATIS quick actions and airport frequency data 2025-09-18 18:16:40 +02:00
itsrubberduck
abd158700c add other flights 2025-09-18 18:08:28 +02:00
Remi
3dcc6479a8 Finalize admin tools and transmission fault flow 2025-09-18 14:03:26 +02:00
Remi
7a44d67844 Harden runtime config and input validation 2025-09-18 14:03:25 +02:00
Remi
e355d0ba18 Align public messaging and add news banners 2025-09-17 19:22:56 +02:00