diff --git a/CLAUDE.md b/CLAUDE.md index 6fd28e0..d050355 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -1,107 +1,131 @@ -# Claude Desktop +# Claude Desktop — Projekt-Kontext -Native Tauri-2.0-Desktop-App die Claude Code/Agent SDK als Backend nutzt. Sprach-Interface, Live-Aktivität, Guard-Rails. Eigenes Pendant zur VSCodium-Sidebar mit voller Kontrolle über das System. +Native Tauri-2.0-Desktop-App die Claude Code/Agent SDK als Backend nutzt. +Schneller und maechtiger als Codium + Claude Code Extension. -Detail-Übersicht + Status: [README.md](README.md). Phasen-Stand: [ROADMAP.md](ROADMAP.md). +**Stand: 22.04.2026 — Alle Roadmap-Phasen (3-6) abgeschlossen.** + +Detail-Uebersicht: [README.md](README.md) | Phasen-Status: [ROADMAP.md](ROADMAP.md) | Aenderungen: [CHANGELOG.md](CHANGELOG.md) ## Tech-Stack -- **Backend**: Rust 2021, Tauri 2 (`tauri = "2"` mit `tray-icon`-Feature), tokio, mysql_async, rusqlite, reqwest -- **Frontend**: SvelteKit 2, Svelte 5, TypeScript, Vite 5, paneforge (Multi-Pane-Layout) -- **AI**: `@anthropic-ai/claude-agent-sdk` + `@anthropic-ai/claude-code` -- **Sprache**: Whisper (STT lokal), TTS Cloud-Streaming -- **DB**: claude-DB (MySQL 192.168.155.11 `claude`) für Wissensbasis, SQLite lokal für Sessions/Persistenz -- **Build**: NixOS-Dev-Shell (`shell.nix`), Forgejo CI für AppImage +- **Backend**: Rust 2021, Tauri 2 (`tray-icon`), tokio, mysql_async, rusqlite, reqwest, libc +- **Frontend**: SvelteKit 2, Svelte 5 (Runes: $state/$derived/$effect), TypeScript, Vite 5, paneforge +- **AI**: `@anthropic-ai/claude-agent-sdk` (query-Funktion), Ollama (optional, lokal) +- **Sprache**: whisper-cli (STT, lokal), piper-tts (TTS, lokal, 5 deutsche Stimmen) +- **DB**: MySQL (claude-db, 192.168.155.11) fuer Wissensbasis, SQLite lokal fuer Sessions/Settings/Queue +- **IPC**: Unix Domain Socket (bevorzugt) oder stdio JSON-Lines +- **Build**: NixOS shell.nix, Forgejo Actions → AppImage ## Wichtige Pfade -- Rust-Module: [src-tauri/src/](src-tauri/src/) — 16 Module (`main.rs`, `lib.rs`, `claude.rs`, `db.rs`, `guard.rs`, `voice.rs`, `hooks.rs`, `ide.rs`, …) -- UI-Komponenten: [src/lib/components/](src/lib/components/) — 24 Panels -- Routes: [src/routes/](src/routes/) (`+layout.svelte`, `+page.svelte`, `presentation/+page.svelte`) -- VS-Code-Extension: [vscode-extension/](vscode-extension/) (Bridge auf WebSocket-Port 7890) -- Workflow: [.forgejo/workflows/build-appimage.yml](.forgejo/workflows/build-appimage.yml) -- Dev-Shell: [shell.nix](shell.nix) -- Tauri-Config: [src-tauri/tauri.conf.json](src-tauri/tauri.conf.json), [src-tauri/Cargo.toml](src-tauri/Cargo.toml) +| Was | Pfad | +|-----|------| +| Rust-Module (18) | `src-tauri/src/` | +| UI-Komponenten (27) | `src/lib/components/` | +| Stores | `src/lib/stores/` (app.ts, events.ts) | +| Bridge | `scripts/claude-bridge.js` (~1100 Zeilen) | +| Hauptlayout | `src/routes/+page.svelte` | +| Chat-Fenster | `src/routes/chat-window/+page.svelte` | +| Praesentation | `src/routes/presentation/+page.svelte` | +| CI/CD | `.forgejo/workflows/build-appimage.yml` | +| Dev-Shell | `shell.nix` | -## Build & Run +## Architektur-Kurzreferenz -### Native Dev (Hot-Reload) -```bash -nix-shell shell.nix --run 'npm ci && npm run tauri:dev' +### Kommunikationskette +``` +User → ChatPanel.svelte → invoke('send_message') → claude.rs + → Bridge (UDS/stdio) → query() → Claude API → Events zurueck + → claude.rs handle_bridge_message() → emit() → events.ts → UI ``` -### Native Production-Build (NixOS — **Pflicht-Weg auf NixOS!**) -```bash -# Cargo-target NICHT auf SMB-Mount! → I/O-Errors. Lokales tmpfs nutzen: -CARGO_TARGET_DIR=/tmp/claude-target \ - nix-shell shell.nix --run 'npm run tauri build -- --bundles appimage' -# Bundling kann mit pkg-config-Bug crashen — Binary unter -# /tmp/claude-target/release/claude-desktop ist trotzdem fertig & startbar: -nix-shell shell.nix --run /tmp/claude-target/release/claude-desktop +### Bridge-Daemon (Phase 3) +- **Socket**: `/tmp/claude-bridge.sock` +- **PID-File**: `/tmp/claude-bridge.pid` +- Start: `node claude-bridge.js --socket /tmp/claude-bridge.sock` +- Rust verbindet sich per `UnixStream::connect()` +- Auto-Reconnect bei Verbindungsverlust (3 Versuche) +- Fallback auf stdio wenn UDS fehlschlaegt + +### ClaudeState (claude.rs) +```rust +pub struct ClaudeState { + pub connection: Option, // Stdio oder Uds + pub request_counter: u64, + pub agents: Vec, +} ``` -### CI-Build via Forgejo Actions -Commit mit `[appimage]` in der Message → Build auf `16-Forgejo-Runner-AppImage` (Debian) → Upload in Package-Registry. Triggert auch bei Tag-Push `v*`. +### Agent-Modi (claude-bridge.js) +| Modus | Beschreibung | Prompt | +|-------|-------------|--------| +| `solo` | Claude arbeitet direkt | Kein Orchestrator | +| `handlanger` | Haupt-Agent delegiert an Haiku-Worker | ORCHESTRATOR_PROMPTS.handlanger | +| `experten` | 4 Experten: Research/Implement/Test/Review | ORCHESTRATOR_PROMPTS.experten | +| `auto` | Heuristik waehlt Modus nach Nachrichtenlaenge/-inhalt | chooseAutoMode() | -## NixOS-Spezialfall — AppImage funktioniert NICHT +### MCP-Hub (Phase 4) +- 6 Server aus `~/.claude.json` → beim Bridge-Start per `set-mcp-servers` injiziert +- Tauri-Commands: `list_mcp_servers`, `add_mcp_server`, `remove_mcp_server` +- Bridge: `queryOptions.mcpServers = mcpServerConfigs` -Das vom CI gebaute AppImage hat auf NixOS einen WebKit2GTK ↔ Mesa ABI-Konflikt (`EGL_BAD_PARAMETER` im WebKitWebProcess). **Keine** Kombination aus `WEBKIT_DISABLE_DMABUF_RENDERER` / `_COMPOSITING_MODE` / `_SANDBOX_THIS_IS_DANGEROUS` / `GDK_BACKEND=x11` / `LIBGL_ALWAYS_SOFTWARE` löst es. Workarounds erschöpft → **immer nativ bauen via `shell.nix`**. Vollständige Diagnose: KB-Eintrag #381. +### Offline-Queue (Phase 5) +- SQLite-Tabelle `offline_queue` +- Commands: `queue_message`, `list_queued_messages`, `flush_offline_queue`, `clear_offline_queue`, `queue_count` +## Build & Deploy + +```bash +# Dev (Hot-Reload) +CARGO_TARGET_DIR=/tmp/claude-desktop-target nix-shell --run "npx tauri dev" + +# Produktion +CARGO_TARGET_DIR=/tmp/claude-desktop-target nix-shell --run "npx tauri build -- --bundles appimage" + +# CI: Commit mit [appimage] → Forgejo baut automatisch +# WICHTIG: CARGO_TARGET_DIR nie auf SMB-Mount! +``` + +### CI-Eigenheiten +- Runner: `16-Forgejo-Runner-AppImage` (Debian Bookworm) +- AppImage-Filename mit Leerzeichen → `tr ' ' '-'` vor Upload +- DELETE vor PUT (Forgejo 409 Conflict) +- Custom-AppRun muss `apprun-hooks/linuxdeploy-plugin-gtk.sh` sourcen (KB #384) +- Ntfy-Notifications auf Topic `vk-builds` + +## NixOS-Spezialfall + +AppImage hat WebKit2GTK/Mesa ABI-Konflikt auf NixOS → **immer nativ bauen** via `shell.nix`. Auf Debian/Ubuntu/Fedora/Arch funktioniert das AppImage problemlos. ## Konventionen -- **Sprache**: Deutsch in Code-Kommentaren, README, CHANGELOG, Commit-Messages, UI-Strings -- **Modell-Defaults**: Sonnet 4.6 für normale Tasks, Opus für Komplex, Haiku für Routineanfragen — UI-Auswahl im Footer -- **Guard-Rails**: alle System-Aktionen über `guard.rs` klassifizieren (Safe / Moderate / Critical / Blocked) — siehe `src-tauri/src/guard.rs` -- **Audit**: jede Tool-Ausführung landet im Audit-Log (`audit.rs` → SQLite + UI-Panel) -- **Sessions**: persistent in SQLite, restartbar -- **Bridge zur VSCodium-Extension**: Port 7890, einfaches WebSocket-Protokoll, in `ide.rs` definiert +- **Sprache**: Deutsch in Code-Kommentaren, README, Commits, UI +- **Svelte 5**: Runes (`$state`, `$derived`, `$effect`), `onclick` statt `on:click` +- **Guard-Rails**: Alle System-Aktionen ueber `guard.rs` klassifizieren +- **Audit**: Jede Tool-Ausfuehrung im Audit-Log +- **Sessions**: Persistent in SQLite, nach Projekt gefiltert +- **PaneForge**: `{#key}` verwenden wenn Panes dynamisch ein-/ausgeblendet werden -## Workflow-Eigenheiten (CI/CD) +## Haeufige Probleme & Loesungen -Beim Anpassen von [.forgejo/workflows/build-appimage.yml](.forgejo/workflows/build-appimage.yml) **nicht vergessen**: -- AppImage-Filename hat Leerzeichen → vor Upload `tr ' ' '-'` (curl-URL-Bug) -- Vor jedem Upload **DELETE auf `latest/` UND `VERSION/`** (Forgejo wirft 409 Conflict bei PUT auf existing) -- Custom-AppRun **muss `apprun-hooks/linuxdeploy-plugin-gtk.sh` sourcen + `AppRun.wrapped` aufrufen**, sonst finden WebKit-Subprozesse ihre Helpers nicht (KB #384) -- Re-Bundle nach AppRun-Patch mit `appimagetool --no-appstream` -- Ntfy-Notifications inline (nicht via `data/ntfy-action`, weil das Repo cross-org ist — für `data-it/*`-Repos siehe KB #220 für vollständige URL-Variante) +| Problem | Loesung | +|---------|---------| +| Rusqlite Borrow-Lifetime | `let result = stmt.query_map(...)?.collect(); result` | +| UTF-8 Panic bei Truncation | `char_indices().take_while()` statt `&s[..n]` | +| PaneForge Resize nach Detach | `{#key $chatDetached}` um PaneGroup | +| Piper-TTS nicht gefunden | `nix-env -f '' -iA piper-tts`, Modelle in `~/.local/share/claude-desktop/models/` | +| Bridge-Nachricht nicht parsbar | `match serde_json::from_str()` statt `if let Ok()` | +| Unhandled Promise Rejection | Global Handler in Bridge (uncaughtException + unhandledRejection) | -## Wissensbasis (Claude-DB) +## Wissensbasis-Referenzen -Bei spezifischen Bug-Themen vorab `mysql_search_knowledge` mit Schlüsselwort: - -| Thema | KB-ID | -|---|---| -| Pipeline-Übersicht | #311 | -| Debian-Runner Setup | #371 | -| libssl-dev / openssl-sys | #372 | -| NixOS WebKit-EGL-Crash | #381 | -| Cargo auf SMB → CARGO_TARGET_DIR | #382 | -| Custom-AppRun + linuxdeploy-Hook | #384 | -| Bluetooth 5.2 ≠ LE Audio | #385 | -| Tauri shell.nix-Vorlage | #248 | -| Forgejo Package-Registry 409 | #161 | -| Ntfy-Pattern (cross-org URL) | #190/#191/#220 | - -## Häufige Befehle - -```bash -# Build-Status checken -curl -sS -u "token:" \ - 'https://git.data-it-solution.de/api/v1/repos/data/claude-desktop/actions/tasks?limit=3' | jq - -# AppImage frisch ziehen (Standard-Linux) -rm -f ~/Applications/Claude-Desktop.AppImage -curl -sSL -o ~/Applications/Claude-Desktop.AppImage \ - -u "token:" \ - 'https://git.data-it-solution.de/api/packages/data/generic/claude-desktop/latest/Claude-Desktop_0.1.0_amd64.AppImage' -chmod +x ~/Applications/Claude-Desktop.AppImage - -# Native NixOS-Start (nach einmaligem Build) -nix-shell shell.nix --run /tmp/claude-target/release/claude-desktop - -# Build-Logs aus Forgejo-Container ziehen (bei Failure) -ssh unraid "docker cp 18-Forgejo:\$(docker exec 18-Forgejo find /data/gitea/actions_log/data/claude-desktop -name '.log.zst' | head -1) /tmp/build.log.zst" -ssh unraid "zstd -d -c /tmp/build.log.zst" | tail -100 -``` +| KB-ID | Thema | +|-------|-------| +| #248 | Tauri + SvelteKit shell.nix | +| #311 | CI/CD Pipeline | +| #371 | Debian Forgejo-Runner | +| #381 | NixOS WebKit-EGL-Crash | +| #382 | Cargo auf SMB | +| #384 | Custom-AppRun | diff --git a/README.md b/README.md index 7034640..0f853be 100644 --- a/README.md +++ b/README.md @@ -1,491 +1,242 @@ -# Claude Desktop — Nativer AI-Assistent +# Claude Desktop -Eigenständige Desktop-Anwendung die Claude Code als Backend nutzt, mit nativem UI, Live-Übersicht und kontrolliertem OS-Zugriff. +Nativer AI-Desktop-Assistent fuer Linux. Schneller und maechtiger als Codium + Claude Code Extension. -## Status (Stand 2026-04-20) - -**Variante A (Native Desktop-App) ist umgesetzt** — Tauri 2.0 + SvelteKit 5, Phase 1-13 fertig (siehe [ROADMAP.md](ROADMAP.md)). Variante B (autonome VM) bleibt Vision. - -Was läuft: -- 4-Panel-Layout, 24 UI-Komponenten (Chat, Activity, Memory, Audit, Knowledge, Voice, Hooks, IDE, Programs, Performance, Settings, …) -- 16 Rust-Backend-Module (`claude.rs`, `db.rs`, `guard.rs`, `memory.rs`, `voice.rs`, `hooks.rs`, `ide.rs`, …) -- Sprach-Interface mit Push-to-Talk (`VoicePanel`), Whisper STT -- Modell-Auswahl Haiku/Sonnet/Opus, Token-/Kosten-Anzeige -- Subagent-Hierarchie, Multi-Agent-Modi, Hook-System -- Session-Persistenz (SQLite), Audit-Log -- VS-Code-Extension `claude-desktop-bridge` (steuert VSCodium aus der App heraus, WebSocket-Port 7890) -- CI/CD-Pipeline (Forgejo Actions) → AppImage in Package-Registry - -## Installation - -### AppImage (Debian/Ubuntu/Fedora/Arch — **nicht NixOS**) - -```bash -mkdir -p ~/Applications -curl -sSL -o ~/Applications/Claude-Desktop.AppImage \ - -u "token:" \ - 'https://git.data-it-solution.de/api/packages/data/generic/claude-desktop/latest/Claude-Desktop_0.1.0_amd64.AppImage' -chmod +x ~/Applications/Claude-Desktop.AppImage -~/Applications/Claude-Desktop.AppImage -``` - -Auf NixOS hat das AppImage einen WebKit2GTK ↔ Mesa ABI-Konflikt → siehe nächster Abschnitt. - -### NixOS — nativer Build (Pflicht) - -Das AppImage läuft auf NixOS nicht (KB-Eintrag #381 zur Diagnose). Stattdessen lokal bauen mit der mitgelieferten `shell.nix`: - -```bash -cd "/mnt/17 - Entwicklungen/20 - Projekte/ClaudeDesktop" - -# Cargo-Target auf lokales tmpfs (SMB-Mount macht Cargo-Build-Errors) -CARGO_TARGET_DIR=/tmp/claude-target \ - nix-shell shell.nix --run 'npm ci && npm run tauri build -- --bundles appimage' - -# Tauri-Bundling kann an pkg-config-Bug scheitern — Binary reicht aber: -nix-shell shell.nix --run /tmp/claude-target/release/claude-desktop -``` - -Permanenter Wrapper: - -```bash -cat > ~/.local/bin/claude-desktop <<'EOF' -#!/usr/bin/env bash -cd "/mnt/17 - Entwicklungen/20 - Projekte/ClaudeDesktop" -exec nix-shell shell.nix --run /tmp/claude-target/release/claude-desktop -EOF -chmod +x ~/.local/bin/claude-desktop -``` - -### Development - -```bash -cd "/mnt/17 - Entwicklungen/20 - Projekte/ClaudeDesktop" -nix-shell shell.nix --run 'npm ci && npm run tauri:dev' # mit Hot-Reload -``` - -## CI/CD-Pipeline - -Workflow: `.forgejo/workflows/build-appimage.yml` - -| Trigger | Was passiert | -|---|---| -| Push auf `main` mit `[appimage]` in Commit-Message | AppImage bauen + in Package-Registry hochladen | -| Push eines Tags `v*` | zusätzlich als Release-Asset anhängen | - -**Runner:** `16-Forgejo-Runner-AppImage` (Debian Bookworm, glibc, mit linuxdeploy + appimagetool + Tauri-Build-Stack vorinstalliert). Der Standard-Alpine-Runner kann Tauri-AppImages nicht bauen (musl-Inkompatibilität von linuxdeploy). Setup des Runners: KB-Eintrag #371. - -**Workflow-Eigenheiten** (gut zu wissen wenn was ändern): -- AppImage-Filename mit Leerzeichen (`Claude Desktop_…`) wird vor Upload zu `Claude-Desktop_…` umbenannt (curl-URL-Bug) -- Vor jedem Upload werden alte Versionen gelöscht (Forgejo Package-Registry weist PUT auf existierenden Pfad mit HTTP 409 ab) -- Custom-AppRun mit NixOS-Detection wird nach `tauri build` eingesetzt + mit `appimagetool` re-bundled. Der Hook `apprun-hooks/linuxdeploy-plugin-gtk.sh` darf dabei nicht überschrieben werden (KB #384), sonst finden WebKit-Subprozesse ihre Helpers nicht -- Ntfy-Notifications (Build-Start/Success/Failure) — Topic `vk-builds` - -Ntfy-Setup für andere Projekte: KB #190/#191/#220. - -## VS-Code-Extension `claude-desktop-bridge` - -Eigenes Subprojekt unter [vscode-extension/](vscode-extension/). Ermöglicht Claude Desktop, VSCodium fernzusteuern (Datei öffnen, Cursor-Position setzen, Terminal-Befehle absetzen) über einen WebSocket-Server (Port 7890 default). - -```bash -cd vscode-extension -npm ci && npm run compile -# Verpacktes vsix: claude-desktop-bridge-0.1.0.vsix -codium --install-extension claude-desktop-bridge-0.1.0.vsix -``` - -Befehle in VSCodium: `Claude Desktop: Verbindung starten/beenden`. Die App meldet sich beim Start automatisch. - -## Projektstruktur (Stand) - -``` -ClaudeDesktop/ -├── src-tauri/src/ # 16 Rust-Module -│ ├── main.rs # Entry (setzt WEBKIT_DISABLE_*-Defaults für Linux) -│ ├── lib.rs # Tauri-App-Setup -│ ├── claude.rs # Claude Agent SDK Integration -│ ├── db.rs # MySQL (claude-DB) + SQLite-Persistierung -│ ├── guard.rs # Guard-Rails (Critical/Moderate/Safe) -│ ├── hooks.rs # Hook-System -│ ├── memory.rs # Memory/Knowledge-Graph -│ ├── voice.rs # Whisper STT + Voice-Activity-Detection -│ ├── ide.rs # Bridge zur VSCodium-Extension -│ ├── audit.rs, knowledge.rs, programs.rs, session.rs, -│ │ teaching.rs, update.rs, context.rs -│ └── ... -├── src/ # SvelteKit Frontend -│ ├── routes/+layout.svelte -│ ├── routes/+page.svelte -│ ├── routes/presentation/+page.svelte -│ └── lib/components/ # 24 UI-Panels -├── vscode-extension/ # VSCodium-Bridge -├── .forgejo/workflows/ # CI/CD -├── shell.nix # NixOS Dev-Shell -├── ROADMAP.md # Phase-Status -├── TEST-ROADMAP.md # Test-Plan -├── tools.yaml # MCP-Tool-Inventar -└── package.json -``` - -## Wissensbasis-Referenzen (für künftige Sessions) - -| KB-ID | Thema | -|---|---| -| #311 | Diese Pipeline (Workflow-Tricks) | -| #371 | Debian Forgejo-Runner Setup | -| #372 | libssl-dev für openssl-sys | -| #381 | NixOS WebKit2GTK EGL-Crash → native build | -| #382 | Cargo auf SMB → CARGO_TARGET_DIR umleiten | -| #384 | Custom-AppRun + linuxdeploy-Hook | -| #248 | Tauri 2.0 + SvelteKit auf NixOS shell.nix | +**Tech-Stack:** Tauri 2.0 (Rust) + SvelteKit 5 + Claude Agent SDK (Node.js) +**Codebase:** ~24.000 Zeilen, 154 Commits, 27 Svelte-Komponenten, 18 Rust-Module --- -## Motivation +## Schnellstart -Claude Code in VSCodium funktioniert, hat aber Grenzen: -- Sidebar-Chat ist eng, keine eigene Fensterverwaltung -- Kein Überblick was Claude gerade tut (Dateien, Befehle, DB-Queries) -- Kein "Stopp"-Button bei laufenden Aktionen -- Keine Präsentations-Ansicht für Ergebnisse -- Keine native OS-Integration (Fenster steuern, Programme öffnen) +```bash +# Development (Hot-Reload) +cd "/mnt/17 - Entwicklungen/20 - Projekte/ClaudeDesktop" +CARGO_TARGET_DIR=/tmp/claude-desktop-target nix-shell --run "npx tauri dev" -## Vision +# Produktion (AppImage) +CARGO_TARGET_DIR=/tmp/claude-desktop-target nix-shell --run "npx tauri build -- --bundles appimage" -### Variante A: Native Desktop-App (begleitend) - -Claude arbeitet begleitend — der User sieht alles mit und kann jederzeit eingreifen. - -``` -┌─────────────────────────────────────────────────────┐ -│ Claude Desktop [─][□][×]│ -├──────────────┬──────────────────────────────────────┤ -│ │ │ -│ 💬 Chat │ 📋 Live-Aktivität │ -│ │ │ -│ Du: Fixe │ ▶ Lese product/price.php:1609 │ -│ den Bug in │ ▶ Grep "addMoreActions" in 3 Files │ -│ der Preis- │ ▶ Edit actions_produktkarte.class.php│ -│ seite │ ✓ Deploy nach /var/www/dolibarr/... │ -│ │ │ -│ Claude: │ ⚠ Will deployen auf PROD │ -│ Gefunden, │ [Erlauben] [Ablehnen] │ -│ der Hook... │ │ -│ ├──────────────────────────────────────┤ -│ │ 📊 Ergebnis-Präsentation │ -│ │ │ -│ │ Vorher: list=0 (unsichtbar) │ -│ │ Nachher: list=3 (auf Karte) │ -│ │ │ -│ │ [Diff anzeigen] [Screenshot] │ -│ │ │ -├──────────────┴──────────────────────────────────────┤ -│ [⏹ STOPP] CPU: 2% │ DB: claude │ Git: main │ -└─────────────────────────────────────────────────────┘ +# CI: Commit mit [appimage] im Message → Forgejo Runner baut + uploaded automatisch ``` -**Kernfeatures:** -- **Chat-Panel** — Aufgaben eingeben, Antworten lesen -- **Live-Aktivität** — Echtzeit was Claude tut (Dateien, Befehle, Queries) -- **Kritische Aktionen** — Popup bei Prod-Deploy, DB-Änderungen, Git Push -- **Präsentations-View** — Nach einer Aufgabe: Vorher/Nachher, Diffs, Screenshots -- **STOPP-Button** — Sofort alles abbrechen -- **Statusleiste** — Aktive DB, Git-Branch, CPU/RAM +--- -**Technologie-Stack:** -- **Tauri 2.0** (Rust + WebView) — native App, ~5 MB statt 200 MB Electron -- **SvelteKit** — Frontend (gleiche Technologie wie Leckerbuch, VDE Katalog) -- **Claude Code SDK** (`@anthropic-ai/claude-code`) — AI-Backend -- **Claude DB** — Direkte MySQL-Anbindung (kein REST-Umweg) -- **MCP-Tools** — Docker, Forgejo, Wissensbasis - -### Variante B: Autonome VM (selbständig arbeitend) - -Claude hat einen eigenen Rechner (VM) mit Desktop und arbeitet Aufgaben selbständig ab. Der User überwacht remote. +## Architektur ``` -┌──────────────────────────────────────────┐ -│ Unraid Server │ -│ │ -│ ┌────────────────────────────────────┐ │ -│ │ VM: Claude Agent │ │ -│ │ │ │ -│ │ ┌──────────┐ ┌───────────────┐ │ │ -│ │ │ Desktop │ │ Claude Agent │ │ │ -│ │ │ (XFCE) │←→│ Computer Use │ │ │ -│ │ │ │ │ Terminal │ │ │ -│ │ │ Dolibarr │ │ Claude DB │ │ │ -│ │ │ Browser │ │ MCP Tools │ │ │ -│ │ │ IDE │ │ Git/Forgejo │ │ │ -│ │ └──────────┘ └───────────────┘ │ │ -│ │ ↕ │ │ -│ │ VNC/noVNC (Port 6080) │ │ -│ └────────────────────────────────────┘ │ -│ │ -│ Netzwerk: ISOLIERT von Prod! │ -│ - Eigenes VLAN / Bridge │ -│ - Zugriff nur auf Test-DB │ -│ - Kein SSH zu Unraid │ -│ - Kein Zugriff auf Prod-Dolibarr │ -└──────────────────────────────────────────┘ - ↕ - Eddy (Browser → VNC) - Sieht Claude arbeiten - Kann jederzeit eingreifen -``` - -**Wie Claude Computer Use funktioniert:** -1. Claude bekommt einen Screenshot des Desktops -2. Claude analysiert was er sieht -3. Claude sendet Maus-/Tastatur-Befehle -4. Nächster Screenshot → nächste Aktion -5. Kann jedes Programm bedienen das ein Mensch bedienen kann - -**Sicherheitskonzept für die VM:** -- **Netzwerk-Isolation** — eigenes VLAN, kein Zugriff auf Prod-Server -- **Nur Test-DB** — dolibarr_test auf 192.168.155.11, nie Prod-DB -- **Kein SSH nach außen** — keine SSH-Keys zu Unraid oder anderen Servern -- **Snapshot-basiert** — VM-Snapshot vor jeder Aufgabe, Rollback bei Problemen -- **Audit-Log** — jeder Befehl, jede Aktion wird geloggt -- **Zeitlimit** — maximale Laufzeit pro Aufgabe -- **Kill-Switch** — ein Befehl stoppt alles sofort - -**Use Cases für die VM:** -- Dolibarr-Module entwickeln und testen (Browser + Terminal) -- Automatische Code-Reviews über mehrere Repos -- Dokumentation erstellen mit Screenshots -- UI-Tests durchführen (Dolibarr durchklicken, Fehler finden) -- Batch-Aufgaben (alle Module updaten, Lang-Dateien synchronisieren) - -## Empfehlung: Stufenweise vorgehen - -### Stufe 1: Native Desktop-App (Variante A) -- Sofort umsetzbar mit vorhandenem Wissen (Svelte, Tauri) -- Claude arbeitet begleitend, User behält Kontrolle -- Ersetzt die VSCodium-Sidebar durch bessere UX -- Geschätzter Aufwand: 2-3 Wochen Grundgerüst - -### Stufe 2: Autonome VM (Variante B) — später -- Erst wenn Stufe 1 stabil läuft und Vertrauen aufgebaut ist -- Guard-Rails und Audit-Log müssen wasserdicht sein -- Netzwerk-Isolation auf Unraid einrichten -- Geschätzter Aufwand: 1-2 Wochen Setup, dann iterativ - -## Architektur — Variante A im Detail - -### Projektstruktur -``` -ClaudeDesktop/ -├── src-tauri/ # Rust-Backend (Tauri) -│ ├── src/ -│ │ ├── main.rs # App-Einstiegspunkt -│ │ ├── claude.rs # Claude SDK Integration -│ │ ├── db.rs # Direkte MySQL-Anbindung -│ │ └── guard.rs # Sicherheits-Regeln -│ ├── Cargo.toml -│ └── tauri.conf.json -├── src/ # SvelteKit Frontend -│ ├── routes/ -│ │ ├── +layout.svelte # Haupt-Layout (Chat + Panels) -│ │ ├── chat/ # Chat-Ansicht -│ │ ├── activity/ # Live-Aktivität -│ │ ├── presentation/ # Ergebnis-Präsentation -│ │ └── settings/ # Einstellungen -│ ├── lib/ -│ │ ├── claude-bridge.ts # Kommunikation mit Tauri-Backend -│ │ ├── db.ts # Claude-DB Queries -│ │ └── stores.ts # Svelte Stores (State) -│ └── app.html -├── package.json -├── svelte.config.js -├── vite.config.ts -└── README.md +┌──────────────────────────────────────────────────────────┐ +│ SvelteKit Frontend │ +│ 27 Svelte-Komponenten (Chat, Voice, Guard-Rails, ...) │ +├──────────────────────────────────────────────────────────┤ +│ Tauri IPC │ +├──────────────────────────────────────────────────────────┤ +│ Rust Backend │ +│ 18 Module (claude.rs, db.rs, guard.rs, voice.rs, ...) │ +├──────────────────────┬───────────────────────────────────┤ +│ SQLite (lokal) │ Unix Domain Socket / stdio │ +│ Sessions, Settings │ ↕ │ +│ Memory, Audit │ Claude Bridge (Node.js) │ +│ Offline-Queue │ @anthropic-ai/claude-agent-sdk │ +├──────────────────────┤ ↕ │ +│ MySQL (claude-db) │ Claude API (Anthropic) │ +│ Wissensbasis │ + MCP-Server (6 Stueck) │ +└──────────────────────┴───────────────────────────────────┘ ``` ### Datenfluss -``` -User-Eingabe (Chat) - ↓ -SvelteKit Frontend - ↓ (Tauri IPC) -Rust Backend - ↓ -Claude Code SDK (Node.js child process) - ↓ -Claude API (Anthropic) - ↓ -Tool-Ausführung (Bash, Dateien, DB, MCP) - ↓ -Ergebnis zurück an Frontend - ↓ -Live-Aktivität + Präsentation anzeigen -``` -### Claude-DB Integration -Statt REST-API (aktuell) → direkte MySQL-Verbindung im Rust-Backend: -```rust -// Direkte DB-Abfrage, kein MCP-Umweg -let results = db.query( - "SELECT * FROM knowledge WHERE MATCH(title,content) AGAINST(? IN BOOLEAN MODE)", - &[search_term] -).await?; -``` -- Schneller (kein HTTP-Roundtrip) -- Keine Token-Limits bei großen Ergebnissen -- Full-Text-Search direkt in MySQL +1. **User** → Eingabe im ChatPanel (Text/Sprache/File-Drop) +2. **Frontend** → `invoke('send_message')` via Tauri IPC +3. **Rust** → Sticky Context + KB-Hints laden, an Bridge senden +4. **Bridge** → `query()` mit Claude Agent SDK, Events streamen +5. **Claude API** → Antwort + Tool-Calls (Bash, Read, Edit, MCP, ...) +6. **Bridge** → Events via JSON-Lines an Rust zurueck +7. **Rust** → `emit()` Events ans Frontend +8. **Frontend** → Live-Rendering (Text, Tools, Subagents) -### Guard-Rails im nativen Programm -```rust -enum ActionRisk { - Safe, // Dateien lesen, Code schreiben → automatisch - Moderate, // Git commit, lokaler Deploy → Statusbar-Hinweis - Critical, // Prod-Deploy, DB-Schema, Git Push → Popup + Bestätigung - Blocked, // rm -rf, force push main → hart blockiert -} -``` +### Bridge-Modi -## Sprach-Interface — Reden mit Claude +| Modus | Beschreibung | Wann | +|-------|-------------|------| +| **UDS-Daemon** | Bridge als eigenstaendiger Prozess, ueberlebt App-Neustart | Standard (bevorzugt) | +| **stdio** | Bridge als Child-Process mit stdin/stdout | Fallback wenn UDS fehlschlaegt | -### Konzept +Socket-Pfad: `/tmp/claude-bridge.sock`, PID-File: `/tmp/claude-bridge.pid` -Echtes Gespräch mit Claude — reden, unterbrechen, weiterreden. Kein "Aufnahme starten/stoppen", sondern natürlicher Dialog. +--- -``` -┌─────────────────────────────────────────────────┐ -│ │ -│ 🎤 Du sprichst │ -│ ↓ │ -│ Whisper (Speech-to-Text, lokal) │ -│ ↓ │ -│ VAD erkennt: "User hat aufgehört zu reden" │ -│ ↓ │ -│ Text → Claude API → Antwort-Text │ -│ ↓ │ -│ TTS (Text-to-Speech) → Lautsprecher 🔊 │ -│ ↓ │ -│ Du unterbrichst → VAD erkennt Sprache │ -│ → TTS stoppt sofort │ -│ → Whisper nimmt deine neue Eingabe auf │ -│ → Kreislauf beginnt von vorn │ -│ │ -└─────────────────────────────────────────────────┘ -``` +## Dateistruktur -### Technologie +### Rust Backend (`src-tauri/src/`) -| Komponente | Technologie | Läuft wo | -|---|---|---| -| **Speech-to-Text** | OpenAI Whisper (whisper.cpp) | Lokal auf NixOS, kein Cloud-Upload | -| **Voice Activity Detection** | Silero VAD oder WebRTC VAD | Lokal, erkennt Sprache vs. Stille | -| **Text-to-Speech** | OpenAI TTS API oder ElevenLabs | Cloud (Streaming) | -| **Interrupt-Erkennung** | VAD + sofortiger TTS-Stopp | Lokal | +| Datei | Zeilen | Funktion | +|-------|--------|----------| +| `lib.rs` | ~340 | App-Setup, Tray-Icon, Global Hotkey (Super+C), Plugin-Init | +| `claude.rs` | ~1000 | **Kernmodul**: Bridge-Kommunikation (UDS/stdio), MCP-Hub, Ollama, send_message | +| `db.rs` | ~800 | SQLite: Sessions, Messages, Settings, Projekte, Monitor-Events, Fehler-Tracking | +| `knowledge.rs` | ~1000 | MySQL-Wissensbasis: Suche, Cache (60s TTL), KB-Hints, Smart Hints v2 | +| `session.rs` | ~300 | Session-CRUD, Offline-Queue (queue/flush/clear) | +| `guard.rs` | ~250 | Guard-Rails: Safe/Moderate/Critical/Blocked, Permissions | +| `memory.rs` | ~200 | Persistentes Gedaechtnis: Auto-Load, Patterns, Cross-Session | +| `context.rs` | ~300 | 3-Schichten Context: Sticky/Projekt/Hints, Render fuer Prompt | +| `voice.rs` | ~355 | Whisper STT + Piper TTS (5 deutsche Stimmen), offline | +| `hooks.rs` | ~200 | Hook-System: SessionStart, PreToolUse, PostToolUse | +| `audit.rs` | ~150 | Audit-Log: Alle Aktionen mit Timestamp + Risk-Level | +| `programs.rs` | ~300 | D-Bus Aktionen, Screenshot-Capture, Xvfb | +| `ide.rs` | ~200 | VSCodium-Extension Bridge (WebSocket Port 7890) | +| `clipboard.rs` | ~150 | Clipboard-Watch: Code/URL/Fehler erkennen | +| `teaching.rs` | ~150 | Praesentations-/Schulungsmodus (separates Fenster) | +| `chat_window.rs` | ~100 | Chat-Detach: Separates Fenster herausloesen/zurueckholen | +| `update.rs` | ~250 | Auto-Updater: Forgejo Package Registry, Lock-Datei | +| `commands.rs` | ~100 | Slash-Command Registry (scannt ~/.claude/commands/) | -### Gesprächs-Modi +### Frontend (`src/lib/components/`) -**Freies Gespräch** — wie mit einem Kollegen reden: -- Du redest, Claude hört zu (Whisper transkribiert live) -- Pause > 1,5 Sekunden → Claude antwortet -- Du unterbrichst → Claude stoppt sofort, hört dir zu -- Claude kann nachfragen wenn etwas unklar ist +| Komponente | Funktion | +|-----------|----------| +| `ChatPanel.svelte` | **Hauptkomponente**: Nachrichtenliste, Eingabe, File-Drop, Modus-Indikator | +| `SessionList.svelte` | Sidebar: Sessions, Projekt-Wechsel, Suche | +| `ActivityPanel.svelte` | Live-Aktivitaet: Tool-Calls, Agent-Status | +| `AgentView.svelte` | Subagent-Hierarchie als Baumansicht | +| `MonitorPanel.svelte` | System-Monitor: API/Tool/Error Events | +| `PerformancePanel.svelte` | Token-/Kosten-Statistiken | +| `GuardRailsPanel.svelte` | 3-Tab: Live-Feed / Regeln / Blockiert | +| `VoicePanel.svelte` | Push-to-Talk, Gespraechsmodus, TTS-Wiedergabe | +| `ContextPanel.svelte` | Sticky Context anzeigen/editieren | +| `MemoryPanel.svelte` | Persistentes Gedaechtnis CRUD | +| `KnowledgePanel.svelte` | Wissensbasis durchsuchen | +| `HooksPanel.svelte` | Hook-Verwaltung | +| `SettingsPanel.svelte` | VS-Code-artiges Settings mit Suche/Kategorien | +| `ProgramsPanel.svelte` | D-Bus Aktionen, Screenshot, Xvfb | +| `IdePanel.svelte` | VSCodium-Verbindung Status | +| `AuditLog.svelte` | Audit-Eintraege durchsuchen | +| `QuickActions.svelte` | Ctrl+K Kommandopalette | +| `CommandPalette.svelte` | Slash-Command Autocomplete (/-Eingabe) | +| `CodeBlock.svelte` | Syntax-Highlighting + Copy-Button | +| `DiffView.svelte` | Diff-Anzeige fuer Code-Aenderungen | +| `MermaidDiagram.svelte` | Mermaid-Diagramme rendern | +| `StopButton.svelte` | Abbruch-Button waehrend Agent laeuft | +| `UpdateDialog.svelte` | Auto-Update Bestaetigungsdialog | +| `FilePreview.svelte` | Datei-Vorschau (Text/Bild) | +| `AnimatedCode.svelte` | Code-Tipp-Animation fuer Praesentation | +| `AutoCorrectionModal.svelte` | Fehler-Pattern Vorschlag | -**Diktier-Modus** — Claude führt aus was du sagst: -- "Fixe den Bug in der Preisseite, der Umrechnungsfaktor wird nicht berücksichtigt" -- Claude arbeitet, kommentiert per Sprache was er tut -- Du kannst jederzeit "Stopp" oder "Warte mal" sagen +### Bridge (`scripts/claude-bridge.js`) -**Präsentations-Modus** — Claude erklärt was er gemacht hat: -- "Zeig mir was du geändert hast" -- Claude öffnet Diff-View und erklärt per Sprache die Änderungen -- Du kannst zwischenfragen: "Warum hast du das so gemacht?" +~1100 Zeilen Node.js. Zentrale Datei fuer die Claude-Kommunikation: -### Stimmen-Optionen +- **query()** via `@anthropic-ai/claude-agent-sdk` — streamt Events +- **Multi-Agent-Modi**: Solo / Handlanger (Haiku-Worker) / Experten (4 spezialisierte Agents) / Auto +- **Subagent-Tracking**: Map mit toolUseId → agentId/type/depth +- **MCP-Server Injection**: Configs von Rust empfangen, in queryOptions injizieren +- **Ollama-Integration**: Auto-Detect beim Start, local-query fuer einfache Tasks +- **Auto-Retry**: 3x Backoff bei Rate-Limit/5xx/Netzwerkfehler +- **Session-Resume**: Stale Session-ID → automatisch neue Session starten +- **UDS-Server-Modus**: `--socket /tmp/claude-bridge.sock` fuer Daemon-Betrieb -**OpenAI TTS API:** -- 6 Stimmen (alloy, echo, fable, onyx, nova, shimmer) -- Sehr natürlich, Streaming-fähig (~200ms Latenz) -- Kosten: ~$15 pro 1M Zeichen +### Stores (`src/lib/stores/`) -**ElevenLabs:** -- Hunderte Stimmen, eigene Stimmen klonbar -- Noch natürlicher, emotionaler -- Deutsch-Support gut -- Kosten: ab $5/Monat (30 Min) +| Store | Inhalt | +|-------|--------| +| `app.ts` | activeSession, activeProject, agentMode, chatDetached, processingPhase | +| `events.ts` | Event-Handler fuer alle Bridge-Events (text, result, tool-start/end, ...) | +| `updateTrigger.ts` | Reactive Trigger fuer Panel-Updates | -**Lokal (Piper TTS):** -- Kostenlos, keine Cloud -- Deutsche Stimmen verfügbar -- Qualität gut aber nicht so natürlich wie Cloud -- Keine Latenz durch Netzwerk +--- -### Latenz-Budget (Ziel: < 2 Sekunden) +## Features komplett -``` -VAD erkennt Stille: ~300ms -Whisper transkribiert: ~500ms (lokal, whisper.cpp mit GPU) -Claude API Antwort: ~800ms (erstes Token, Streaming) -TTS erstes Audio: ~200ms (Streaming) -───────────────────────────────── -Gesamt bis erste Silbe: ~1.800ms -``` +### Phase 1-2 (v0.1.0 — 14.04.2026) +- Tauri 2.0 + SvelteKit 5 Grundgeruest +- 4-Panel Layout, Claude Bridge (stdio), Guard-Rails +- SQLite + Session-Management, Claude-DB Integration +- 3-Schichten Context, Multi-Agent-Modi, Hook-System +- VSCodium-Extension, Programm-Steuerung (D-Bus, Xvfb) +- Praesentationsmodus, System-Monitor, Subagent-Hierarchie +- Auto-Updater, Slash-Commands, KB-Hints, Error-Patterns -Mit Streaming: Claude beginnt zu "reden" während er noch denkt — wie ein Mensch der anfängt zu antworten bevor der Gedanke fertig ist. +### Phase 3: Performance (22.04.2026) +- KB-Cache (RAM, 60s TTL), Bridge Warm-Start, Lazy Panel-Load +- Session-Resume Fix, Auto-Retry (3x Backoff), Heartbeat +- FIFO Message Queue, **Bridge-Daemon** (UDS), **Unix Socket IPC** -### Integration in die Desktop-App +### Phase 4: Codium-Killer Features +- Projekt-Wechsel (Ein-Klick), **MCP-Hub nativ** (6 Server) +- Guard-Rails UI (3 Tabs), Persistent Memory, Quick-Actions (Ctrl+K) +- Voice (Whisper + Piper, offline), Settings-Panel, Chat-Detach +- Aktivitaets-Phasen (Denkt/Streamt/Tool/Subagent) -``` -┌─────────────────────────────────────────────────────┐ -│ Claude Desktop [─][□][×]│ -├──────────────┬──────────────────────────────────────┤ -│ │ │ -│ 💬 Chat │ 📋 Live-Aktivität │ -│ │ │ -│ (Text wird │ ▶ Lese product/price.php │ -│ live mit- │ ▶ Edit actions_produktkarte.class.php│ -│ geschrieben │ ✓ Deploy nach /var/www/dolibarr/... │ -│ während │ │ -│ gesprochen) │ │ -│ │ │ -├──────────────┴──────────────────────────────────────┤ -│ 🎤 ████████░░░░░░ Zuhören... [🔇 Stumm] [⏹] │ -└─────────────────────────────────────────────────────┘ -``` +### Phase 5: Lokale KI + Offline +- Whisper.cpp + Piper-TTS (komplett offline, 5 deutsche Stimmen) +- **Ollama-Integration** (Auto-Detect, local-query) +- **Offline-Queue** (SQLite, flush bei Reconnect) -- Mikrofon-Leiste unten zeigt Pegel -- Gesprochenes wird als Text im Chat mitgeschrieben (Transkript) -- Claudes Antwort wird gleichzeitig als Text angezeigt und vorgelesen -- Stumm-Taste schaltet Mikrofon aus (nur Text-Modus) +### Phase 6: Desktop-Integration +- D-Bus Actions (10 Aktionen), Clipboard-Watch, File-Drop +- Screenshot-Analyse, Global Hotkey (Super+C) -### Whisper lokal auf NixOS +--- -```nix -# In configuration.nix -environment.systemPackages = with pkgs; [ - whisper-cpp # C++ Port, schnell, CPU/GPU - # oder - openai-whisper # Original Python, braucht mehr RAM -]; -``` +## MCP-Server (6 Stueck, automatisch geladen) -Whisper "small" oder "medium" Modell reicht für Deutsch — ~500 MB RAM, Echtzeit auf CPU. +| Name | Funktion | Transport | +|------|----------|-----------| +| `forgejo` | Git: Repos, Issues, PRs, Releases | stdio | +| `claude-db` | MySQL Wissensbasis: Suche, CRUD | SSE (MCP-Hub) | +| `playwright` | Browser-Automatisierung | stdio | +| `context7` | Library-Dokumentation | stdio | +| `portainer` | Docker-Container-Management | stdio | +| `homeassistant` | Smart-Home Steuerung | stdio | -## Voraussetzungen +Configs in `~/.claude.json` → werden beim Bridge-Start automatisch injiziert. -### Für Variante A (Desktop-App) -- NixOS: `rustc`, `cargo`, `nodejs`, `tauri-cli` in der Nix-Config -- Anthropic API Key (bereits vorhanden) -- Claude Code SDK npm-Paket -- MySQL-Client-Library für Rust (`sqlx` oder `mysql_async`) +--- -### Für Variante B (VM) -- Unraid: VM mit Linux + Desktop (Ubuntu/Debian + XFCE) -- VNC-Server in der VM -- noVNC-Container auf Unraid für Browser-Zugriff -- Isoliertes Netzwerk (VLAN oder Bridge) -- Claude API Key + Computer Use Beta-Zugang +## CI/CD -## Offene Fragen +**Workflow:** `.forgejo/workflows/build-appimage.yml` +**Runner:** `16-Forgejo-Runner-AppImage` (Debian Bookworm) +**Trigger:** `[appimage]` in Commit-Message auf `main` -- [ ] Anthropic API Key Kosten für Computer Use (Screenshot-intensiv)? -- [ ] Tauri 2.0 auf NixOS — Nix-Paket verfügbar? -- [ ] Claude Code SDK — stabil genug für Production? -- [ ] VM auf Unraid — genug RAM/CPU frei? +1. Commit mit `[appimage]` → Push +2. Forgejo Runner baut AppImage (~8-10 Min) +3. Upload in Forgejo Package Registry +4. Ntfy-Notification (Topic: `vk-builds`) +5. App zieht Update beim naechsten Start (Auto-Updater) + +**NixOS:** AppImage hat WebKit2GTK/Mesa ABI-Konflikt → lokaler Build mit `shell.nix` noetig. Nix-Wrapper in `~/.local/bin/claude-desktop`. + +--- + +## Tastenkuerzel + +| Kuerzel | Aktion | +|---------|--------| +| `Super+C` | Claude-Eingabe von ueberall oeffnen | +| `Ctrl+K` | Quick-Actions Palette | +| `Ctrl+Enter` | Nachricht senden | +| `Escape` | Quick-Actions/Autocomplete schliessen | +| `/` | Slash-Command Autocomplete | + +--- + +## Wissensbasis-Referenzen + +| KB-ID | Thema | +|-------|-------| +| #248 | Tauri 2.0 + SvelteKit auf NixOS shell.nix | +| #311 | CI/CD Pipeline (Workflow-Tricks) | +| #371 | Debian Forgejo-Runner Setup | +| #381 | NixOS WebKit2GTK EGL-Crash | +| #382 | Cargo auf SMB → CARGO_TARGET_DIR | +| #384 | Custom-AppRun + linuxdeploy-Hook | + +--- + +## Nicht geplant + +- Multi-User / Team-Features +- Cloud-Sync +- Plugin-System (overkill fuer 1-User-App) +- Electron-Port (Tauri bleibt)