Files
ARIA-AGENT/CHANGELOG.md
T

357 lines
24 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# ARIA — Changelog
Alle Änderungen am Projekt. Format: [Keep a Changelog](https://keepachangelog.com/de/1.1.0/)
> **Hinweis:** Dieser Changelog hatte eine große Lücke — er endete bei `0.0.0.5`
> (2026-03), das Projekt lief aber bis `0.2.0.2` (2026-07) weiter (u. a. OAuth,
> Voice-Streaming, Speaker-ID, Datei-Manager). Ab dem Projekte-/Multi-Threading-
> Epos (2026-07) wird wieder gepflegt; die dazwischenliegenden Versionen
> `0.0.0.6``0.1.9.6` sind nicht rückwirkend nacherfasst.
---
## [0.2.0.6] — 2026-07-11
### Hinzugefügt
**Diagnostic + App — Projekte verstecken**
- Neues `hidden`-Flag pro Projekt (bleibt voll nutzbar, nur aus Listen ausgeblendet — unabhängig von `status`/`archived`); `PATCH /projects/{id} {hidden}`
- Diagnostic: 👁-Auge pro Projekt-Bubble (🙈 verstecken / 👁 dauerhaft sichtbar), Header-Toggle „Versteckte anzeigen (N)" blendet sie temporär gedimmt + „versteckt"-Badge ein — zum Ansehen/Auswählen ohne permanentes Enttarnen
- App (`ProjectsBrowser`): versteckte standardmäßig ausgeblendet (Mama sieht sie nicht), Auge pro Zeile + Toggle spiegeln das Diagnostic-Verhalten; geteilter `hidden`-Status übers Brain
**Diagnostic — Token-Ersparnis durch lokales LLM**
- `metrics.jsonl` trägt jetzt `source` (claude | local | fast-path); lokale Calls nutzen echte `usage`-Tokens vom Adapter, Fast-Path = 0 Prompt-Tokens (`by_source`-Aggregation, rückwärts-kompatibel)
- Neue Card „Lokales LLM & Claude-Ersparnis": pro Fenster (1h/5h/24h/30d) gesparte Claude-Calls (local + fast-path) + lokale Token-Last (eigene HW, kein Quota)
**Spotify-Skill — von ARIA selbst geschärft**
- Geräte-Transfer startet die Wiedergabe direkt mit (`play=true`) statt nur zu übertragen, inkl. Verifikation (`is_playing`-Check + expliziter Play-Fallback), Fuzzy-Gerätenamen und sauberen Exit-Codes; neue semantische Actions `play_on_device`/`search_and_play`/`playlist_play`/`queue_add`
### Behoben
- **Spotify-Resume (App):** nach einem Voice-Befehl blieb Spotify auf dem Handy pausiert. Statt des auf manchen Geräten (OnePlus) flakigen Audio-Focus-Nudge jetzt ein echter `KEYCODE_MEDIA_PLAY`-KeyEvent an die aktive MediaSession — gegated: nur wenn vor dem Dialog Musik lief (`isMusicActive`). Deterministisch, geräteunabhängig
- **TTS-Zahlen:** freistehende Ganzzahlen werden jetzt tag-unabhängig ausgeschrieben („23°C" → „dreiundzwanzig Grad Celsius", „100%" → „einhundert Prozent"). Regression, seit das lokale LLM (bewusst ohne `<voice>`-Tag) leichte Turns übernahm; neuer vollständiger Zahl→Wort-Konverter (0…999999) am Ende von `clean_text_for_tts`, lange Ziffernfolgen (IDs) bleiben Ziffern
- **„ARIA denkt" hängt:** Indikator + Abbrechen blieben stehen, obwohl der Turn laut Diagnostic fertig war. Die App räumt den kontext-scoped Indikator jetzt beim Eintreffen der Antwort selbst; die Bridge sendet zusätzlich ein `idle` für die Request-`projectId`, falls der Turn umgeroutet wurde (thinking ging mit Request-, idle mit Turn-`projectId`)
- **Lokale Tool-Fehler:** Action-Skills, die bei Exit 0 einen Fehlschlag nur im stdout-Text melden (Spotify: „Fehler beim Übertragen", „Gerät nicht gefunden"), eskalieren jetzt generisch an Claude statt vom lokalen LLM vorgelesen zu werden (Info-Tools wie web_search ausgenommen)
---
## [0.2.0.4 0.2.0.5] — 2026-07-11 — Plan B: Lokales LLM („Gemini-Feeling")
Ein kleines, schnelles Modell (**Qwen3 8B** via llama.cpp/llama-swap auf der Gamebox-GPU) übernimmt einfache Turns in **<1 s**; alles Schwere/Technische/Werkzeug-artige reicht ein Router automatisch an **Claude** weiter. Ziel: schnelle Antworten ohne die Claude-Max-Subscription aufzugeben.
### Hinzugefügt
**Lokales LLM (Brain + Bridge + Adapter)**
- Router (B1a): Heuristik + `<<ESCALATE>>`-Selbstabbruch entscheidet pro Turn lokal vs. Claude; schlanker System-Prompt mit demselben `IDENTITY_ANCHOR` wie Claude (Rolle hält), nur letzte 8 Turns (Speed)
- Lokale Tool-Fast-Lane (B1b): kuratierte Tools — `web_search` (self-hosted **SearXNG**, local-only), `memory_search`, `trigger_timer`, Spotify; Eskalation bei Tool-Fehler statt Raten
- Consumer-Kette gespiegelt zu FLUX: Brain → Bridge `/internal/local-llm` → RVS → `llm-adapter` → llama.cpp; `enable_thinking:false` (Qwen wickelte sonst die ganze Antwort in `<think>`)
- **B0.5:** llama-swap (Hot-Swap der Modelle on-demand) + Modellauswahl-Dropdown + Live-Lade-Status (loading/ready + Download-Hinweis) in Diagnostic
- **SearXNG** als 6. Container auf der ARIA-VM (keyless Meta-Suche, JSON-API)
**Quell-Badge (local / claude / fast-path)**
- Diagnostic: immer an den ARIA-Bubbles
- App: optionaler Schalter in den Einstellungen, pro Gerät gemerkt, default aus („ich will's, meine Mama nicht")
**TTS — System-Flag `speak` (ja/nein) pro Antwort**
- Die Quelle entscheidet übers Vorlesen (Fast-Path/Steuerbefehl = stumm, ARIA-Antwort = vorlesen), robust statt des fragilen leeren `<voice></voice>`-Hacks der beim Skill-Rebuild verloren ging
### Behoben / Geändert
- **Identität (Hauptchat):** Proxy nutzt jetzt `--system-prompt` (voller Replace) statt `--append-system-prompt` — die Claude-Code-Basis-Identität leakt nicht mehr in den Hauptchat (ARIA antwortete dort als „Claude Code" bzw. deutete die Persona als Injection). Dazu `IDENTITY_SEED` (synthetischer Grounding-Turn) + Gift-Wächter (Identity-Breaks werden nie in die History persistiert, Retry+Fallback) + Cleanup-Script gegen bereits vergiftete Turns
- **Datenschutz (kritisch):** harte Diskretions-Regel im `IDENTITY_ANCHOR` — ARIA kennt intime/private Details, gibt sie aber **NIE ungefragt** preis (nicht in Vorstellungen, „was weißt du über mich", Zusammenfassungen, Triggern); nur auf konkrete Nachfrage, knapp. Bereits ausgeplauderte Turns bereinigt. Lokales Tier eskaliert Personen-/Beziehungs-/Gedächtnisfragen an Claude (kennt das Gedächtnis + antwortet diskret)
- **Lokale Antwort nicht in `<voice>`** wickeln (Qwen imitierte den Tag aus dem Kontext → Anzeige war leer); **generische** Tool-Fehler-Eskalation statt per-Skill-Router-Hardcode (Router muss nicht wissen, welche Skills „schwer" sind)
---
## [0.2.0.3] — 2026-07-10
### Hinzugefügt
**Proxy — ARIA-Persona über echten System-Prompt-Kanal**
- Persona + Tool-Use-Format gehen jetzt über `--append-system-prompt` der Claude-CLI statt als `<system>`-getaggter User-Content im Prompt (`openai-to-cli.js`: Prompt = nur Verlauf, `systemPrompt` separat; neue `sed`-Zeile schleust `--append-system-prompt`,`options.systemPrompt` ins `buildArgs`-Array von `manager.js`)
**Multi-Threading — echte Parallelität in der App**
- `agent_activity`-Events tragen jetzt die `projectId` (Brain → Proxy `aria_project_id` → Bridge → App); der „ARIA denkt"-Indikator zeigt nur noch den **fokussierten** Kontext statt global zu flackern (`agentActivityByCtx`-Map)
- Kontext-scoped Cancel: neuer Proxy-Endpoint `/cancel {projectId}` killt nur die Subprozesse *eines* Kontexts (`/cancel-all` bleibt fürs NOT-AUS); Bridge-soft-Cancel + App-Abbrechen tragen die fokussierte `projectId`
**Diagnostic — Datei-Zuordnung**
- Projekt-Dropdown pro Datei im Datei-Manager (nutzt `/api/files-set-project`) — auch alt-hochgeladene Dateien nachträglich einem Projekt zuweisen
### Behoben
- **Identität:** fester `IDENTITY_ANCHOR` ganz oben im System-Prompt — ARIA verliert in (Pentest-)Projekten nicht mehr die Rolle bzw. deutet ihre eigene Aufgabe nicht mehr als Prompt-Injection
- **Barge-In kontext-scoped:** eine Frage im Hauptchat blockiert/killt nicht mehr die parallele Arbeit in einem Projekt (Busy-Status kontextgenau aus `queueStatus` statt global)
---
## [0.1.9.7 0.2.0.2] — 2026-07-02 … 2026-07-10 — Projekte & Multi-Threading
Der große Epos: Themen-Bündel („Projekte") im Hauptchat, echt nebenläufig verarbeitet.
### Hinzugefügt
**Projekte (Brain + App + Diagnostic)**
- Named Themen-Bündel, im Hauptchat verankert, per Sprache adressierbar („steige in Projekt X ein", „für Frankreich: …"), CRUD via Meta-Tools + UI
- App: Focus-One-View + Drawer + Queue-Status-Dots + „← Hauptchat"-Button
- Diagnostic: Kontext-Strip + Focus-Filter + Queue-Polling
- Dateien pro Projekt getaggt (Manifest `file_projects.json`, Filter im Datei-Manager)
**Multi-Threading (Brain)**
- Per-Request `project_id` statt globalem `active_project`; per-Projekt-`asyncio.Lock` = Queue-Verhalten pro Kontext, verschiedene Kontexte laufen parallel
- Queue-Aware-Prompting (spätere Nachricht kann laufenden Task als überholt markieren) ohne Extra-LLM-Call
**Voice-Router (Bridge)**
- 30s-Sticky-Kontext, Prefix-Adressierung, Meta-Command-Interception („zurück zum Hauptchat" ohne Brain-Call), Voice folgt App-Focus
**Migration**
- Alt-getaggte Projekt-Nachrichten (in `conversation.jsonl`, aber ohne Tag im `chat_backup.jsonl`) werden nachträglich einsortiert — idempotent, nicht-destruktiv, reihenfolge-erhaltend
### Behoben
- **Leere Projekte:** Drawer resettete den App-Focus beim Öffnen auf `status.active` (im Multi-Threading = null); Diagnostic warf `project_id` beim `chat_history`-Reload weg (server.js + Renderer); untagged ARIA-Bubbles/Backup-Writes aus dem toten Gateway-Watch-Pfad
- **Voice → falscher Kontext:** Registry-Race (`stt_stream_end` poppte die Focus-`projectId` vor dem finalen `stt_endpoint`); App übernimmt jetzt die autoritative Server-`projectId` der STT-Bubble
- **STT-Endpointing:** akustische Stille als robustes Signal statt rein semantischer Stagnation (nicht mehr „hört nach zwei Worten auf" / „merkt Ende nicht")
- **Anhänge:** Bild/Datei + Frage landen im gewählten Projekt statt im Hauptchat (projectId durch die ganze Anhang-Kette)
- **Bild-Bubbles im Diagnostic:** ARIA-Datei-Bubbles tragen `project_id`, werden nicht mehr fälschlich vom Focus-Filter ausgeblendet
---
## [0.0.0.5] — 2026-03-13
### Hinzugefügt
**Diagnostic — Pipeline-Tab**
- Neuer "Pipeline"-Tab im Log-Bereich — zeigt den kompletten Nachrichtenfluss wenn eine Chat-Nachricht über die Diagnostic-UI gesendet wird
- Tracking aller Schritte: Senden → Gateway ACK → Streaming Deltas → Finale Antwort (oder Fehler)
- Zeitmessung: Jeder Schritt zeigt Elapsed-Time seit Pipeline-Start
- Farbcodierung: Blau (Schritte), Grün (Erfolg), Rot (Fehler)
- 60s Timeout — markiert Pipeline als fehlgeschlagen wenn keine Antwort kommt
- Funktioniert für Gateway-direkt und RVS-Nachrichten
### Behoben
**OpenClaw Gateway Event-Format — ARIA antwortet jetzt**
- OpenClaw sendet `event: "agent"` (Streaming-Deltas in `payload.data.delta`) und `event: "chat"` mit `payload.state: "delta"|"final"|"error"`**nicht** `chat:delta`/`chat:final`/`chat:error` wie angenommen
- Antworttext steckt in `payload.message.content[0].text` (Array von Content-Blöcken, nicht flacher String) — `text.slice is not a function` Fehler behoben
- `ackReactionScope` von `"group-mentions"` auf `"all"` geändert — Agent reagierte nur auf @mentions, nicht auf direkte Nachrichten
- Diagnostic Server und Bridge auf neues Event-Format umgestellt
- Legacy-Event-Namen (`chat:delta`, `chat:final`, `chat:error`) als Fallback beibehalten
### Geändert
**OpenClaw Config — Custom Provider Format**
- `openclaw.json` nutzt `models.providers` (Object, nicht Array) mit `api: "openai-completions"`
- Model-Einträge brauchen sowohl `id` als auch `name` Feld
- `aria-setup.sh` schreibt korrekte Config mit Heredoc-Pattern (`'"'"'INNEREOF'"'"'`)
- `DEFAULT_MODEL=proxy/claude-sonnet-4` — mit Provider-Prefix für Custom Provider
- `OPENAI_BASE_URL` und `OPENAI_API_KEY` entfernt — OpenClaw ignoriert diese Env-Vars, nutzt nur `models.providers` Config
---
## [0.0.0.4] — 2026-03-11 / 2026-03-12
### Hinzugefügt
**Diagnostic Container — Selbstcheck-UI**
- Neuer Container `aria-diagnostic` mit Web-UI auf Port 3001
- Status-Karten: OpenClaw Gateway, RVS, Claude Proxy — jeweils mit Dot-Indicator
- Claude Proxy Test: Prüft Erreichbarkeit (`/v1/models`) und sendet Test-Prompt an Claude — zeigt verfügbare Modelle als Tags + `DEFAULT_MODEL` Hinweis für docker-compose.yml
- Auth-Check: "Auth prüfen" Button durchsucht alle bekannten Credential-Pfade im Proxy-Container (`/root/.config/claude/`, `/root/.claude/`, `/root/.claude/auth/`) rekursiv — zeigt gefundene Dateien und deren Inhalt
- Claude Login via UI: "Login starten" Button öffnet interaktives Terminal (xterm.js) in einem Modal-Overlay — führt `claude login` im Proxy-Container aus, volle TUI-Unterstützung (kein ANSI-Stripping mehr nötig)
- xterm.js Terminal: Bidirektionaler Stream über Docker Exec API mit `Tty: true` + HTTP Upgrade auf Raw-TCP-Socket — echtes interaktives Terminal im Browser
- UTF-8 Fix: Eingehende Daten werden als `Uint8Array` an xterm.write() übergeben (statt `atob()` → Latin-1 String, der Multi-Byte UTF-8 zerstört), ausgehende Daten über `TextEncoder` UTF-8-safe kodiert
- Credentials manuell einfügen: "Credentials einfügen" Button — JSON von einem eingeloggten Rechner kopieren und direkt in den Container schreiben (schreibt in beide mögliche Pfade: `.config/claude/` und `.claude/`)
- Docker Exec API: Generische `dockerExec()` (nicht-interaktiv, multiplexed stream) + `attachTerminal()` (interaktiv, Tty, raw TCP socket) für Befehle in laufenden Containern (via Docker Socket)
- Chat-Test: Nachrichten direkt über Gateway oder via RVS senden
- Tabbed Logs: Separate Tabs für Alle, Gateway, RVS, Proxy, Server — mit Zähler pro Tab
- Autoscroll-Pause: Automatisch wenn hochgescrollt, "Nach unten" Button zum Fortsetzen
- TLS Fallback für RVS-Verbindung (wie Bridge und App)
### Geändert
**Bridge → aria-core: OpenClaw Gateway Protokoll**
- Bridge nutzt jetzt das echte OpenClaw Gateway WebSocket-Protokoll (Port 18789 statt 8080)
- Vollständiger Handshake: `connect.challenge``connect` Request (mit Auth-Token) → `hello-ok`
- Nachrichten über `chat.send` Method mit `message` und `idempotencyKey`
- Antworten über `chat:final` Events (statt custom JSON)
- Streaming-Support vorbereitet (`chat:delta` Events werden empfangen)
- Fehlerbehandlung für `chat:error` Events — werden an die App weitergeleitet
- Client-ID: `gateway-client` / Mode: `backend` (OpenClaw akzeptiert nur bestimmte Werte)
**Docker-Compose Überarbeitung**
- Bridge + Diagnostic nutzen `network_mode: "service:aria"` — teilen Netzwerk mit aria-core, kein separates Netz nötig
- `ANTHROPIC_API_KEY` + `ANTHROPIC_BASE_URL` entfernt — OpenClaw rief damit die echte Anthropic API direkt an (401 `invalid x-api-key`), statt den Proxy zu nutzen. Nur noch `OPENAI_*` Vars aktiv
- `DEFAULT_MODEL=openai/claude-sonnet-4-6` — mit `openai/` Prefix, damit OpenClaw den OpenAI-Provider und somit den Proxy nutzt
- `openclaw.env` erstellt — Volume-Mount schlug fehl weil die Datei nicht existierte (Docker erstellte stattdessen ein leeres Verzeichnis)
- `OPENCLAW_GATEWAY_TOKEN` statt `AUTH_TOKEN` — korrekter Env-Var-Name
- `ARIA_AUTH_TOKEN` an Bridge und Diagnostic durchgereicht
- Port 3001 auf aria-Service gemappt (für Diagnostic Web-UI)
- Proxy Claude-Config Volume `:ro``:rw` — Login via Diagnostic-UI braucht Schreibzugriff
**OpenClaw Config-Persistenz**
- Named Docker Volume `openclaw-config` für `/home/node/.openclaw` — OpenClaw-Konfiguration (Model, Auth, Sessions) überlebt Container-Neustarts
- `aria-setup.sh` — Einmaliges Setup-Skript: wartet auf aria-core, setzt Model auf `openai/claude-sonnet-4-6`, startet Container neu
### Behoben
- Handshake fehlgeschlagen `[object Object]` — Fehlermeldung wurde nicht korrekt stringifiziert
- `client.id` und `client.mode` im Connect-Request — OpenClaw akzeptiert nur vordefinierte Werte (`cli`, `gateway-client`, `webchat` etc.)
- `chat.send` nutzt `message` statt `text` als Parameter — OpenClaw Schema-Validierung
- **Claude Proxy bindet auf 0.0.0.0** — `claude-max-api-proxy` bindet hardcoded auf `127.0.0.1`, nicht erreichbar im Docker-Netz. Fix: `standalone.js` wird beim Start gepatcht, liest jetzt `HOST` Env-Var (Upstream-Bug: `startServer()` unterstützt `host`, aber CLI übergibt es nicht)
- **Claude Proxy Crash bei Chat-Completion** — `normalizeModelName()` in `cli-to-openai.js` crasht wenn `model` undefined ist (`TypeError: Cannot read properties of undefined`). Fix: Null-Guard-Patch mit Fallback auf `claude-sonnet-4`
- **OpenClaw 401 `invalid x-api-key`** — OpenClaw rief mit `ANTHROPIC_BASE_URL` + `ANTHROPIC_API_KEY=not-needed` die echte Anthropic API an, nicht den Proxy. Fix: Anthropic-Vars entfernt, nur OpenAI-Provider aktiv (`OPENAI_BASE_URL=http://proxy:3456/v1`). Proxy unterstützt nur `/v1/chat/completions` (OpenAI-Format), nicht `/v1/messages` (Anthropic-Format)
- **App Echo-Bug** — Chat-Nachrichten von RVS wurden ohne Sender-Prüfung als ARIA-Nachricht angezeigt. Bei Ghost-Clients (Doppel-Connections nach Reconnect) erschien die eigene Nachricht nochmals. Fix: `message.payload.sender` wird geprüft, Nachrichten von `user` und `diagnostic` werden ignoriert
---
## [0.0.0.3] — 2026-03-09
### Geändert
**RVS — Architektur-Umbau**
- RVS ist jetzt reiner Relay — kennt keine Tokens, keine Expiry, leitet nur durch
- `TOKEN_EXPIRY` und `RVS_PUBLIC_HOST`/`RVS_PUBLIC_PORT` entfernt
- Rooms leben solange Clients verbunden sind (statt fester Ablaufzeit)
- Multi-Instanz: Mehrere ARIA-VMs können denselben RVS nutzen (z.B. Stefan + Papa)
**Token-Erzeugung auf ARIA-VM statt RVS**
- `generate-token.js` aus `rvs/` entfernt
- Neues `generate-token.sh` im Hauptverzeichnis (läuft auf ARIA-VM)
- Token wird automatisch in `.env` geschrieben
- `./generate-token.sh show` zeigt bestehendes Token als QR nochmal an
**Konfiguration vereinfacht**
- `RVS_URL` ersetzt durch `RVS_HOST`, `RVS_PORT`, `RVS_TLS` (klare Einzelfelder)
- Port einmal in `.env` ändern → wirkt auf RVS docker-compose, Bridge und QR-Code
- `rvs/docker-compose.yml` nutzt `${RVS_PORT:-443}` statt hardcoded Port
**Android App — QR-Code Scanner**
- Echter QR-Code Scanner statt Platzhalter-Alert (`react-native-camera-kit`)
- Vollbild-Kamera mit Overlay, Validierung des QR-Formats
- Kamera-Berechtigung (Android Runtime Permission)
- `AndroidManifest.xml``CAMERA` Permission hinzugefügt
**Voice Bridge — RVS-Anbindung**
- Bridge verbindet sich jetzt parallel zu aria-core (lokal) UND zum RVS (öffentlich)
- Nachrichten von der App werden über RVS → Bridge → aria-core weitergeleitet
- Antworten von aria-core werden über Bridge → RVS → App zurückgeschickt
- Auto-Reconnect mit Exponential Backoff für beide WebSocket-Verbindungen
- Neue Message-Handler: chat, mode, location, file, audio
**Android Build-Fixes**
- `kotlin_version` (snake_case) in `build.gradle` hinzugefügt — `react-native-camera-kit` braucht beide Varianten
- `build.sh` schreibt `org.gradle.java.home` dynamisch in `gradle.properties` — verhindert dass Gradle kaputte JVM-Pfade findet (`/usr/lib/jvm/openjdk-17` ohne bin/java)
- `minSdkVersion` 21 → 23 — `react-native-camera-kit` braucht mindestens API 23
**Android App — Credentials Persistenz**
- Verbindungsdaten (Host, Port, Token) werden nach QR-Scan in AsyncStorage gespeichert
- Beim App-Start automatisch geladen und verbunden — einmal scannen, nie wieder
- Neue Dependency: `@react-native-async-storage/async-storage`
**Docker & Infrastruktur**
- OpenClaw Image fix: `openclaw/openclaw:latest``ghcr.io/openclaw/openclaw:latest`
- Proxy fix: Binary heißt `claude-max-api`, braucht `@anthropic-ai/claude-code` als Peer-Dependency
- Proxy Binary-Name fix: `claude-max-api-proxy``claude-max-api` (npm-Paket heißt anders als die Binary)
- `libportaudio2` in Bridge Dockerfile hinzugefügt — `sounddevice` braucht PortAudio
- `aria-data/config/aria.env.example` hinzugefügt — Voice Bridge Konfigurationsvorlage
**Wake-Word Fix (openwakeword)**
- `WakeWordDetector` umgebaut — sucht Custom-Modell `/voices/wake_aria.onnx`, Fallback auf eingebautes `hey_jarvis`
- Alter Code crashte: `wakeword_models=["aria"]` erwartet Dateipfad, kein Keyword
**TLS Fallback (Bridge → RVS)**
- Bridge versucht zuerst `wss://` (TLS), bei `ssl.SSLError` automatisch Fallback auf `ws://`
- Konfigurierbar über `RVS_TLS_FALLBACK=true` in `.env`
- Loggt deutlich wenn TLS gewollt aber nicht verfügbar ist
**Audio-Rendering für App (Piper TTS via RVS)**
- Bridge rendert Piper TTS → WAV → base64, sendet Text UND Audio gleichzeitig über RVS
- App spielt Audio ab und zeigt Text parallel — Modus entscheidet ob Sprache oder nur Text
- Voice Engine initialisiert IMMER (auch ohne Soundkarte in der VM)
- STT/Wake-Word nur wenn Audio-Hardware vorhanden — graceful degradation
- Neue Dependency: `react-native-fs` (base64 → temp WAV → Sound abspielen)
**Chat-Persistenz (Android App)**
- Chat-Verlauf wird in AsyncStorage gespeichert (letzte 500 Nachrichten)
- Beim App-Start automatisch geladen — Konversation bleibt erhalten
- Linearer 1:1 Chat, keine Threads
**TLS Fallback + Verbindungslog (Android App)**
- App versucht zuerst `wss://`, bei Fehler automatisch Fallback auf `ws://`
- `network_security_config.xml` hinzugefuegt — Android 9+ blockiert sonst `ws://` (Cleartext)
- Verbindungslog im Settings-Tab — zeigt jeden Verbindungsversuch, Fehler, Fallback (scrollbar, max 200px)
- Gespeicherte Config wird beim Start in die Einstellungsfelder geladen
- Fix: TLS-Fallback erzeugte Doppel-Verbindungen (onerror + onclose beide reconnected)
**RVS — Ghost-Client Fix**
- Heartbeat-Intervall 30s → 15s, Cleanup 60s → 30s — tote Clients werden schneller entfernt
- `heartbeat` als erlaubter Nachrichtentyp hinzugefuegt — App-Heartbeats halten Verbindung lebendig
- App-seitiger JSON-Heartbeat zaehlt als Lebenszeichen (zusaetzlich zu WebSocket Ping/Pong)
**Neues Script: `get-voices.sh`**
- Lädt Piper Stimmen (Ramona + Thorsten) von HuggingFace herunter
- Neuer Installationsschritt in README
**ARIA Persönlichkeit**
- `AGENT.md` überarbeitet — ARIA ist jetzt Partnerin auf Augenhöhe (Claude-Charakter)
- Direkt, ehrlich, humorvoll, lösungsorientiert, kein Theater
---
## [0.0.0.2] — 2026-03-08
### Geändert
**Build-Fixes**
- `CI=true` in `build.sh` — verhindert EMFILE durch Metro File-Watcher im Release-Build
- `setup.sh` erstellt Metro-Config-Dateien automatisch (metro.config.js, babel.config.js, .watchmanconfig)
**Release-Script**
- `release.sh` komplett umgebaut — Kennwort wird interaktiv abgefragt statt Token in `.env`
- Gitea-Upload fix: `-F` multipart statt `--data-binary`
- Login-Test vor Release, CHANGELOG.md-Integration für Release Notes
---
## [0.0.0.1] — 2026-03-08
### Hinzugefügt
**Infrastruktur**
- `docker-compose.yml` — ARIA-VM mit Proxy, OpenClaw, Voice Bridge
- `.env.example` — Konfigurationsvorlage (ohne Secrets)
- `release.sh` — Automatisiertes Release (Build, Tag, Gitea Upload mit Kennwort-Abfrage)
**RVS (Rendezvous-Server)**
- WebSocket Relay Server (`rvs/server.js`) — Token-Rooms, Heartbeat, Message Types
- Docker Setup (`rvs/Dockerfile`, `rvs/docker-compose.yml`)
**Token & Pairing**
- `generate-token.sh` — Token-Generator mit QR-Code (läuft auf ARIA-VM, schreibt Token in `.env`)
**Voice Bridge**
- Python Voice Bridge (`bridge/aria_bridge.py`) — Whisper STT, Piper TTS, Wake-Word
- 5 Betriebsmodi (`bridge/modes.py`) — Normal, DND, Whisper, Hangar, Gaming
- Docker Setup (`bridge/Dockerfile`, `bridge/requirements.txt`)
**Android App (ARIA Cockpit)**
- Chat-Screen mit Texteingabe, Voice-Button, Datei/Kamera-Upload
- Settings-Screen mit Verbindungsstatus, Token-Eingabe, Modus-Auswahl, GPS-Toggle, Log-Viewer
- WebSocket-Service mit Auto-Reconnect und Exponential Backoff
- Audio-Service (Mikrofon-Aufnahme, TTS-Wiedergabe)
- Push-to-Talk Button mit Puls-Animation
- Modus-Selektor (5 Modi)
- Build-Tooling: `setup.sh` (7-Schritt Dev-Setup), `build.sh` (Release/Debug APK)
- Metro-Config, Babel-Config, Watchman-Config
**Konfiguration & Daten**
- `aria-data/config/AGENT.md` — ARIAs Persönlichkeit und Sicherheitsregeln
- `aria-data/config/USER.md` — Stefans Präferenzen
- `aria-data/config/TOOLING.md` — VM-Tooling Liste
- `aria-data/skills/README.md` — Skill-Bauanleitung
### Bekannte Probleme
- Android Release-Build: `EMFILE: too many open files` — Fix: `CI=true` in `build.sh`
- JDK 21 inkompatibel mit AGP 8.1 — Fix: Automatischer Fallback auf JDK 17
- `react-native-screens` > 3.27.0 inkompatibel mit RN 0.73.4 — Fix: Version gepinnt