From e1aa8b1bdb114d375b89d2ec119e441a826a12e3 Mon Sep 17 00:00:00 2001 From: josedario87 Date: Mon, 23 Feb 2026 15:33:43 -0600 Subject: [PATCH] feat: integrate Tauri v2 with Android widget and voice assistant - Add Tauri v2 shell (Cargo, tauri.conf.json, capabilities, plugins) - Migrate all fetch() calls to apiFetch() for Tauri-aware HTTP - Migrate WebSocket endpoints to resolveEndpoints() for dynamic URLs - Add ServerConfigDialog for remote server URL configuration - Add tauri.ts lib with isTauri detection, apiFetch wrapper, plugin helpers - Add server-config Pinia store with persistence via plugin-store - Conditional PWA (disabled in Tauri builds) - Android: home screen transcript widget (last 5 messages, 30s refresh) - Android: voice command / share activity (SpeechRecognizer + WebSocket) - Android: signed release APK with auto-copy to installers/ - Remove stale frontend/src-tauri directory --- .gitignore | 33 + frontend/package-lock.json | 279 + frontend/package.json | 18 +- frontend/src/App.vue | 56 +- frontend/src/components/FloatingVoice.vue | 13 +- .../src/components/ServerConfigDialog.vue | 282 + .../transcript-debug/NewSessionModal.vue | 3 +- .../composables/database/useDatabaseApi.ts | 9 +- .../composables/database/useQueryExecutor.ts | 3 +- frontend/src/composables/git/useGitApi.ts | 17 +- .../transcript-debug/useHooksApproval.ts | 7 +- .../transcript-debug/useTranscriptDebug.ts | 19 +- .../src/composables/useEphemeralTerminal.ts | 7 +- frontend/src/composables/useGlobalApproval.ts | 7 +- frontend/src/config/endpoints.ts | 77 +- frontend/src/lib/tauri.ts | 85 + frontend/src/main.ts | 25 +- frontend/src/pages/GitPage.vue | 4 +- frontend/src/pages/SourceCodePage.vue | 7 +- frontend/src/services/dynamicComponents.ts | 13 +- frontend/src/services/session-state-ws.ts | 4 +- frontend/src/services/themeService.ts | 15 +- .../tools/handlers/databaseHandlers.ts | 11 +- .../tools/handlers/fsComponentHandlers.ts | 5 +- .../services/tools/handlers/gitHandlers.ts | 11 +- .../services/tools/handlers/globalHandlers.ts | 9 +- .../tools/handlers/sourceCodeHandlers.ts | 11 +- frontend/src/services/torch.ts | 4 +- frontend/src/services/webmcp.ts | 33 +- frontend/src/services/whisperSocket.ts | 13 +- frontend/src/stores/agents.ts | 25 +- frontend/src/stores/claude-hooks.ts | 3 +- frontend/src/stores/projectCanvas.ts | 27 +- frontend/src/stores/server-config.ts | 109 + frontend/src/stores/session-state.ts | 7 +- frontend/src/stores/snapshots.ts | 9 +- frontend/src/stores/theme.ts | 13 +- frontend/vite.config.ts | 8 +- package.json | 7 +- src-tauri/Cargo.lock | 6235 +++++++++++++++++ src-tauri/Cargo.toml | 23 + src-tauri/build.rs | 3 + src-tauri/capabilities/default.json | 20 + src-tauri/gen/android/app/build.gradle.kts | 97 + .../android/app/src/main/AndroidManifest.xml | 63 + .../java/com/agentui/desktop/MainActivity.kt | 40 + .../java/com/agentui/desktop/ServerConfig.kt | 40 + .../desktop/TranscriptWidgetProvider.kt | 42 + .../agentui/desktop/TranscriptWidgetWorker.kt | 146 + .../agentui/desktop/VoiceCommandActivity.kt | 160 + .../src/main/res/layout/widget_transcript.xml | 70 + .../app/src/main/res/values/strings.xml | 5 + .../main/res/xml/transcript_widget_info.xml | 9 + src-tauri/icons/128x128.png | Bin 0 -> 7459 bytes src-tauri/icons/128x128@2x.png | Bin 0 -> 16348 bytes src-tauri/icons/32x32.png | Bin 0 -> 1474 bytes src-tauri/icons/64x64.png | Bin 0 -> 3223 bytes src-tauri/icons/Square107x107Logo.png | Bin 0 -> 6294 bytes src-tauri/icons/Square142x142Logo.png | Bin 0 -> 8587 bytes src-tauri/icons/Square150x150Logo.png | Bin 0 -> 9181 bytes src-tauri/icons/Square284x284Logo.png | Bin 0 -> 18744 bytes src-tauri/icons/Square30x30Logo.png | Bin 0 -> 1380 bytes src-tauri/icons/Square310x310Logo.png | Bin 0 -> 20684 bytes src-tauri/icons/Square44x44Logo.png | Bin 0 -> 2138 bytes src-tauri/icons/Square71x71Logo.png | Bin 0 -> 3861 bytes src-tauri/icons/Square89x89Logo.png | Bin 0 -> 5033 bytes src-tauri/icons/StoreLogo.png | Bin 0 -> 2491 bytes .../android/mipmap-anydpi-v26/ic_launcher.xml | 5 + .../icons/android/mipmap-hdpi/ic_launcher.png | Bin 0 -> 2305 bytes .../mipmap-hdpi/ic_launcher_foreground.png | Bin 0 -> 9918 bytes .../android/mipmap-hdpi/ic_launcher_round.png | Bin 0 -> 2156 bytes .../icons/android/mipmap-mdpi/ic_launcher.png | Bin 0 -> 2211 bytes .../mipmap-mdpi/ic_launcher_foreground.png | Bin 0 -> 6279 bytes .../android/mipmap-mdpi/ic_launcher_round.png | Bin 0 -> 2143 bytes .../android/mipmap-xhdpi/ic_launcher.png | Bin 0 -> 5108 bytes .../mipmap-xhdpi/ic_launcher_foreground.png | Bin 0 -> 13685 bytes .../mipmap-xhdpi/ic_launcher_round.png | Bin 0 -> 4734 bytes .../android/mipmap-xxhdpi/ic_launcher.png | Bin 0 -> 8446 bytes .../mipmap-xxhdpi/ic_launcher_foreground.png | Bin 0 -> 21375 bytes .../mipmap-xxhdpi/ic_launcher_round.png | Bin 0 -> 7560 bytes .../android/mipmap-xxxhdpi/ic_launcher.png | Bin 0 -> 11701 bytes .../mipmap-xxxhdpi/ic_launcher_foreground.png | Bin 0 -> 30102 bytes .../mipmap-xxxhdpi/ic_launcher_round.png | Bin 0 -> 10101 bytes .../android/values/ic_launcher_background.xml | 4 + src-tauri/icons/icon.icns | Bin 0 -> 209872 bytes src-tauri/icons/icon.ico | Bin 0 -> 30532 bytes src-tauri/icons/icon.png | Bin 0 -> 22586 bytes src-tauri/icons/ios/AppIcon-20x20@1x.png | Bin 0 -> 811 bytes src-tauri/icons/ios/AppIcon-20x20@2x-1.png | Bin 0 -> 1849 bytes src-tauri/icons/ios/AppIcon-20x20@2x.png | Bin 0 -> 1849 bytes src-tauri/icons/ios/AppIcon-20x20@3x.png | Bin 0 -> 3025 bytes src-tauri/icons/ios/AppIcon-29x29@1x.png | Bin 0 -> 1288 bytes src-tauri/icons/ios/AppIcon-29x29@2x-1.png | Bin 0 -> 3024 bytes src-tauri/icons/ios/AppIcon-29x29@2x.png | Bin 0 -> 3024 bytes src-tauri/icons/ios/AppIcon-29x29@3x.png | Bin 0 -> 4830 bytes src-tauri/icons/ios/AppIcon-40x40@1x.png | Bin 0 -> 1849 bytes src-tauri/icons/ios/AppIcon-40x40@2x-1.png | Bin 0 -> 4306 bytes src-tauri/icons/ios/AppIcon-40x40@2x.png | Bin 0 -> 4306 bytes src-tauri/icons/ios/AppIcon-40x40@3x.png | Bin 0 -> 6875 bytes src-tauri/icons/ios/AppIcon-512@2x.png | Bin 0 -> 107928 bytes src-tauri/icons/ios/AppIcon-60x60@2x.png | Bin 0 -> 6875 bytes src-tauri/icons/ios/AppIcon-60x60@3x.png | Bin 0 -> 10751 bytes src-tauri/icons/ios/AppIcon-76x76@1x.png | Bin 0 -> 4009 bytes src-tauri/icons/ios/AppIcon-76x76@2x.png | Bin 0 -> 8902 bytes src-tauri/icons/ios/AppIcon-83.5x83.5@2x.png | Bin 0 -> 9958 bytes src-tauri/src/lib.rs | 11 + src-tauri/src/main.rs | 6 + src-tauri/tauri.conf.json | 39 + 108 files changed, 8155 insertions(+), 151 deletions(-) create mode 100644 frontend/src/components/ServerConfigDialog.vue create mode 100644 frontend/src/lib/tauri.ts create mode 100644 frontend/src/stores/server-config.ts create mode 100644 src-tauri/Cargo.lock create mode 100644 src-tauri/Cargo.toml create mode 100644 src-tauri/build.rs create mode 100644 src-tauri/capabilities/default.json create mode 100644 src-tauri/gen/android/app/build.gradle.kts create mode 100644 src-tauri/gen/android/app/src/main/AndroidManifest.xml create mode 100644 src-tauri/gen/android/app/src/main/java/com/agentui/desktop/MainActivity.kt create mode 100644 src-tauri/gen/android/app/src/main/java/com/agentui/desktop/ServerConfig.kt create mode 100644 src-tauri/gen/android/app/src/main/java/com/agentui/desktop/TranscriptWidgetProvider.kt create mode 100644 src-tauri/gen/android/app/src/main/java/com/agentui/desktop/TranscriptWidgetWorker.kt create mode 100644 src-tauri/gen/android/app/src/main/java/com/agentui/desktop/VoiceCommandActivity.kt create mode 100644 src-tauri/gen/android/app/src/main/res/layout/widget_transcript.xml create mode 100644 src-tauri/gen/android/app/src/main/res/values/strings.xml create mode 100644 src-tauri/gen/android/app/src/main/res/xml/transcript_widget_info.xml create mode 100644 src-tauri/icons/128x128.png create mode 100644 src-tauri/icons/128x128@2x.png create mode 100644 src-tauri/icons/32x32.png create mode 100644 src-tauri/icons/64x64.png create mode 100644 src-tauri/icons/Square107x107Logo.png create mode 100644 src-tauri/icons/Square142x142Logo.png create mode 100644 src-tauri/icons/Square150x150Logo.png create mode 100644 src-tauri/icons/Square284x284Logo.png create mode 100644 src-tauri/icons/Square30x30Logo.png create mode 100644 src-tauri/icons/Square310x310Logo.png create mode 100644 src-tauri/icons/Square44x44Logo.png create mode 100644 src-tauri/icons/Square71x71Logo.png create mode 100644 src-tauri/icons/Square89x89Logo.png create mode 100644 src-tauri/icons/StoreLogo.png create mode 100644 src-tauri/icons/android/mipmap-anydpi-v26/ic_launcher.xml create mode 100644 src-tauri/icons/android/mipmap-hdpi/ic_launcher.png create mode 100644 src-tauri/icons/android/mipmap-hdpi/ic_launcher_foreground.png create mode 100644 src-tauri/icons/android/mipmap-hdpi/ic_launcher_round.png create mode 100644 src-tauri/icons/android/mipmap-mdpi/ic_launcher.png create mode 100644 src-tauri/icons/android/mipmap-mdpi/ic_launcher_foreground.png create mode 100644 src-tauri/icons/android/mipmap-mdpi/ic_launcher_round.png create mode 100644 src-tauri/icons/android/mipmap-xhdpi/ic_launcher.png create mode 100644 src-tauri/icons/android/mipmap-xhdpi/ic_launcher_foreground.png create mode 100644 src-tauri/icons/android/mipmap-xhdpi/ic_launcher_round.png create mode 100644 src-tauri/icons/android/mipmap-xxhdpi/ic_launcher.png create mode 100644 src-tauri/icons/android/mipmap-xxhdpi/ic_launcher_foreground.png create mode 100644 src-tauri/icons/android/mipmap-xxhdpi/ic_launcher_round.png create mode 100644 src-tauri/icons/android/mipmap-xxxhdpi/ic_launcher.png create mode 100644 src-tauri/icons/android/mipmap-xxxhdpi/ic_launcher_foreground.png create mode 100644 src-tauri/icons/android/mipmap-xxxhdpi/ic_launcher_round.png create mode 100644 src-tauri/icons/android/values/ic_launcher_background.xml create mode 100644 src-tauri/icons/icon.icns create mode 100644 src-tauri/icons/icon.ico create mode 100644 src-tauri/icons/icon.png create mode 100644 src-tauri/icons/ios/AppIcon-20x20@1x.png create mode 100644 src-tauri/icons/ios/AppIcon-20x20@2x-1.png create mode 100644 src-tauri/icons/ios/AppIcon-20x20@2x.png create mode 100644 src-tauri/icons/ios/AppIcon-20x20@3x.png create mode 100644 src-tauri/icons/ios/AppIcon-29x29@1x.png create mode 100644 src-tauri/icons/ios/AppIcon-29x29@2x-1.png create mode 100644 src-tauri/icons/ios/AppIcon-29x29@2x.png create mode 100644 src-tauri/icons/ios/AppIcon-29x29@3x.png create mode 100644 src-tauri/icons/ios/AppIcon-40x40@1x.png create mode 100644 src-tauri/icons/ios/AppIcon-40x40@2x-1.png create mode 100644 src-tauri/icons/ios/AppIcon-40x40@2x.png create mode 100644 src-tauri/icons/ios/AppIcon-40x40@3x.png create mode 100644 src-tauri/icons/ios/AppIcon-512@2x.png create mode 100644 src-tauri/icons/ios/AppIcon-60x60@2x.png create mode 100644 src-tauri/icons/ios/AppIcon-60x60@3x.png create mode 100644 src-tauri/icons/ios/AppIcon-76x76@1x.png create mode 100644 src-tauri/icons/ios/AppIcon-76x76@2x.png create mode 100644 src-tauri/icons/ios/AppIcon-83.5x83.5@2x.png create mode 100644 src-tauri/src/lib.rs create mode 100644 src-tauri/src/main.rs create mode 100644 src-tauri/tauri.conf.json diff --git a/.gitignore b/.gitignore index 7ad82ec..12e81aa 100644 --- a/.gitignore +++ b/.gitignore @@ -9,6 +9,39 @@ nul # Voice recordings (training data) server/recordings/*.webm +# Tauri build artifacts +src-tauri/target/ +src-tauri/installers/ + +# Tauri gen: ignore everything except our custom Android sources +src-tauri/gen/* +!src-tauri/gen/android/ +src-tauri/gen/android/* +!src-tauri/gen/android/app/ +src-tauri/gen/android/app/* +!src-tauri/gen/android/app/build.gradle.kts +!src-tauri/gen/android/app/src/ +src-tauri/gen/android/app/src/* +!src-tauri/gen/android/app/src/main/ +src-tauri/gen/android/app/src/main/* +!src-tauri/gen/android/app/src/main/AndroidManifest.xml +!src-tauri/gen/android/app/src/main/java/ +!src-tauri/gen/android/app/src/main/res/ +src-tauri/gen/android/app/src/main/res/* +!src-tauri/gen/android/app/src/main/res/layout/ +src-tauri/gen/android/app/src/main/res/layout/* +!src-tauri/gen/android/app/src/main/res/layout/widget_transcript.xml +!src-tauri/gen/android/app/src/main/res/xml/ +src-tauri/gen/android/app/src/main/res/xml/* +!src-tauri/gen/android/app/src/main/res/xml/transcript_widget_info.xml +!src-tauri/gen/android/app/src/main/res/values/ +src-tauri/gen/android/app/src/main/res/values/* +!src-tauri/gen/android/app/src/main/res/values/strings.xml +src-tauri/gen/android/keystore.jks + +# Old frontend Tauri location +frontend/src-tauri/ + # Agent runtime data .claude-*/plugins/ .claude-*/plans/ diff --git a/frontend/package-lock.json b/frontend/package-lock.json index b34df8d..3daca20 100644 --- a/frontend/package-lock.json +++ b/frontend/package-lock.json @@ -9,6 +9,12 @@ "version": "0.0.0", "dependencies": { "@nucleoriofrio/webmcp": "git+https://gitea.nucleoriofrio.com/nucleo000/webmcp.git", + "@tauri-apps/api": "^2.10.1", + "@tauri-apps/plugin-clipboard-manager": "^2.3.2", + "@tauri-apps/plugin-dialog": "^2.6.0", + "@tauri-apps/plugin-http": "^2.5.7", + "@tauri-apps/plugin-notification": "^2.3.3", + "@tauri-apps/plugin-store": "^2.4.2", "@xterm/addon-fit": "^0.11.0", "@xterm/addon-web-links": "^0.12.0", "@xterm/addon-webgl": "^0.19.0", @@ -19,6 +25,7 @@ "vue-router": "^4.6.4" }, "devDependencies": { + "@tauri-apps/cli": "^2.10.0", "@types/node": "^24.10.1", "@vitejs/plugin-vue": "^6.0.2", "@vue/tsconfig": "^0.8.1", @@ -2415,6 +2422,278 @@ "sourcemap-codec": "^1.4.8" } }, + "node_modules/@tauri-apps/api": { + "version": "2.10.1", + "resolved": "https://registry.npmjs.org/@tauri-apps/api/-/api-2.10.1.tgz", + "integrity": "sha512-hKL/jWf293UDSUN09rR69hrToyIXBb8CjGaWC7gfinvnQrBVvnLr08FeFi38gxtugAVyVcTa5/FD/Xnkb1siBw==", + "license": "Apache-2.0 OR MIT", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/tauri" + } + }, + "node_modules/@tauri-apps/cli": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli/-/cli-2.10.0.tgz", + "integrity": "sha512-ZwT0T+7bw4+DPCSWzmviwq5XbXlM0cNoleDKOYPFYqcZqeKY31KlpoMW/MOON/tOFBPgi31a2v3w9gliqwL2+Q==", + "dev": true, + "license": "Apache-2.0 OR MIT", + "bin": { + "tauri": "tauri.js" + }, + "engines": { + "node": ">= 10" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/tauri" + }, + "optionalDependencies": { + "@tauri-apps/cli-darwin-arm64": "2.10.0", + "@tauri-apps/cli-darwin-x64": "2.10.0", + "@tauri-apps/cli-linux-arm-gnueabihf": "2.10.0", + "@tauri-apps/cli-linux-arm64-gnu": "2.10.0", + "@tauri-apps/cli-linux-arm64-musl": "2.10.0", + "@tauri-apps/cli-linux-riscv64-gnu": "2.10.0", + "@tauri-apps/cli-linux-x64-gnu": "2.10.0", + "@tauri-apps/cli-linux-x64-musl": "2.10.0", + "@tauri-apps/cli-win32-arm64-msvc": "2.10.0", + "@tauri-apps/cli-win32-ia32-msvc": "2.10.0", + "@tauri-apps/cli-win32-x64-msvc": "2.10.0" + } + }, + "node_modules/@tauri-apps/cli-darwin-arm64": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-darwin-arm64/-/cli-darwin-arm64-2.10.0.tgz", + "integrity": "sha512-avqHD4HRjrMamE/7R/kzJPcAJnZs0IIS+1nkDP5b+TNBn3py7N2aIo9LIpy+VQq0AkN8G5dDpZtOOBkmWt/zjA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-darwin-x64": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-darwin-x64/-/cli-darwin-x64-2.10.0.tgz", + "integrity": "sha512-keDmlvJRStzVFjZTd0xYkBONLtgBC9eMTpmXnBXzsHuawV2q9PvDo2x6D5mhuoMVrJ9QWjgaPKBBCFks4dK71Q==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-linux-arm-gnueabihf": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-arm-gnueabihf/-/cli-linux-arm-gnueabihf-2.10.0.tgz", + "integrity": "sha512-e5u0VfLZsMAC9iHaOEANumgl6lfnJx0Dtjkd8IJpysZ8jp0tJ6wrIkto2OzQgzcYyRCKgX72aKE0PFgZputA8g==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-linux-arm64-gnu": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-arm64-gnu/-/cli-linux-arm64-gnu-2.10.0.tgz", + "integrity": "sha512-YrYYk2dfmBs5m+OIMCrb+JH/oo+4FtlpcrTCgiFYc7vcs6m3QDd1TTyWu0u01ewsCtK2kOdluhr/zKku+KP7HA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-linux-arm64-musl": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-arm64-musl/-/cli-linux-arm64-musl-2.10.0.tgz", + "integrity": "sha512-GUoPdVJmrJRIXFfW3Rkt+eGK9ygOdyISACZfC/bCSfOnGt8kNdQIQr5WRH9QUaTVFIwxMlQyV3m+yXYP+xhSVA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-linux-riscv64-gnu": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-riscv64-gnu/-/cli-linux-riscv64-gnu-2.10.0.tgz", + "integrity": "sha512-JO7s3TlSxshwsoKNCDkyvsx5gw2QAs/Y2GbR5UE2d5kkU138ATKoPOtxn8G1fFT1aDW4LH0rYAAfBpGkDyJJnw==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-linux-x64-gnu": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-x64-gnu/-/cli-linux-x64-gnu-2.10.0.tgz", + "integrity": "sha512-Uvh4SUUp4A6DVRSMWjelww0GnZI3PlVy7VS+DRF5napKuIehVjGl9XD0uKoCoxwAQBLctvipyEK+pDXpJeoHng==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-linux-x64-musl": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-x64-musl/-/cli-linux-x64-musl-2.10.0.tgz", + "integrity": "sha512-AP0KRK6bJuTpQ8kMNWvhIpKUkQJfcPFeba7QshOQZjJ8wOS6emwTN4K5g/d3AbCMo0RRdnZWwu67MlmtJyxC1Q==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-win32-arm64-msvc": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-win32-arm64-msvc/-/cli-win32-arm64-msvc-2.10.0.tgz", + "integrity": "sha512-97DXVU3dJystrq7W41IX+82JEorLNY+3+ECYxvXWqkq7DBN6FsA08x/EFGE8N/b0LTOui9X2dvpGGoeZKKV08g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-win32-ia32-msvc": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-win32-ia32-msvc/-/cli-win32-ia32-msvc-2.10.0.tgz", + "integrity": "sha512-EHyQ1iwrWy1CwMalEm9z2a6L5isQ121pe7FcA2xe4VWMJp+GHSDDGvbTv/OPdkt2Lyr7DAZBpZHM6nvlHXEc4A==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/cli-win32-x64-msvc": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/cli-win32-x64-msvc/-/cli-win32-x64-msvc-2.10.0.tgz", + "integrity": "sha512-NTpyQxkpzGmU6ceWBTY2xRIEaS0ZLbVx1HE1zTA3TY/pV3+cPoPPOs+7YScr4IMzXMtOw7tLw5LEXo5oIG3qaQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "Apache-2.0 OR MIT", + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">= 10" + } + }, + "node_modules/@tauri-apps/plugin-clipboard-manager": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/@tauri-apps/plugin-clipboard-manager/-/plugin-clipboard-manager-2.3.2.tgz", + "integrity": "sha512-CUlb5Hqi2oZbcZf4VUyUH53XWPPdtpw43EUpCza5HWZJwxEoDowFzNUDt1tRUXA8Uq+XPn17Ysfptip33sG4eQ==", + "license": "MIT OR Apache-2.0", + "dependencies": { + "@tauri-apps/api": "^2.8.0" + } + }, + "node_modules/@tauri-apps/plugin-dialog": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/@tauri-apps/plugin-dialog/-/plugin-dialog-2.6.0.tgz", + "integrity": "sha512-q4Uq3eY87TdcYzXACiYSPhmpBA76shgmQswGkSVio4C82Sz2W4iehe9TnKYwbq7weHiL88Yw19XZm7v28+Micg==", + "license": "MIT OR Apache-2.0", + "dependencies": { + "@tauri-apps/api": "^2.8.0" + } + }, + "node_modules/@tauri-apps/plugin-http": { + "version": "2.5.7", + "resolved": "https://registry.npmjs.org/@tauri-apps/plugin-http/-/plugin-http-2.5.7.tgz", + "integrity": "sha512-+F2lEH/c9b0zSsOXKq+5hZNcd9F4IIKCK1T17RqMwpCmVnx2aoqY8yIBccCd25HTYUb3j6NPVbRax/m00hKG8A==", + "license": "MIT OR Apache-2.0", + "dependencies": { + "@tauri-apps/api": "^2.10.1" + } + }, + "node_modules/@tauri-apps/plugin-notification": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/@tauri-apps/plugin-notification/-/plugin-notification-2.3.3.tgz", + "integrity": "sha512-Zw+ZH18RJb41G4NrfHgIuofJiymusqN+q8fGUIIV7vyCH+5sSn5coqRv/MWB9qETsUs97vmU045q7OyseCV3Qg==", + "license": "MIT OR Apache-2.0", + "dependencies": { + "@tauri-apps/api": "^2.8.0" + } + }, + "node_modules/@tauri-apps/plugin-store": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/@tauri-apps/plugin-store/-/plugin-store-2.4.2.tgz", + "integrity": "sha512-0ClHS50Oq9HEvLPhNzTNFxbWVOqoAp3dRvtewQBeqfIQ0z5m3JRnOISIn2ZVPCrQC0MyGyhTS9DWhHjpigQE7A==", + "license": "MIT OR Apache-2.0", + "dependencies": { + "@tauri-apps/api": "^2.8.0" + } + }, "node_modules/@types/estree": { "version": "1.0.8", "license": "MIT" diff --git a/frontend/package.json b/frontend/package.json index a83a7f3..d4f548f 100644 --- a/frontend/package.json +++ b/frontend/package.json @@ -8,10 +8,25 @@ "dev": "vite", "build": "vue-tsc -b && vite build", "preview": "vite preview", - "generate-icons": "node scripts/generate-icons.js" + "generate-icons": "node scripts/generate-icons.js", + "tauri": "tauri", + "tauri:dev": "tauri dev", + "tauri:build": "tauri build", + "tauri:android:init": "tauri android init", + "tauri:android:dev": "tauri android dev", + "tauri:android:build": "tauri android build", + "tauri:ios:init": "tauri ios init", + "tauri:ios:dev": "tauri ios dev", + "tauri:ios:build": "tauri ios build" }, "dependencies": { "@nucleoriofrio/webmcp": "git+https://gitea.nucleoriofrio.com/nucleo000/webmcp.git", + "@tauri-apps/api": "^2.10.1", + "@tauri-apps/plugin-clipboard-manager": "^2.3.2", + "@tauri-apps/plugin-dialog": "^2.6.0", + "@tauri-apps/plugin-http": "^2.5.7", + "@tauri-apps/plugin-notification": "^2.3.3", + "@tauri-apps/plugin-store": "^2.4.2", "@xterm/addon-fit": "^0.11.0", "@xterm/addon-web-links": "^0.12.0", "@xterm/addon-webgl": "^0.19.0", @@ -22,6 +37,7 @@ "vue-router": "^4.6.4" }, "devDependencies": { + "@tauri-apps/cli": "^2.10.0", "@types/node": "^24.10.1", "@vitejs/plugin-vue": "^6.0.2", "@vue/tsconfig": "^0.8.1", diff --git a/frontend/src/App.vue b/frontend/src/App.vue index 9311f37..153e829 100644 --- a/frontend/src/App.vue +++ b/frontend/src/App.vue @@ -10,19 +10,27 @@ import FloatingTranscriptDebug from './components/FloatingTranscriptDebug.vue' import TerminalFabStack from './components/transcript-debug/TerminalFabStack.vue' import PwaInstallBanner from './components/PwaInstallBanner.vue' import HooksApprovalModal from './components/HooksApprovalModal.vue' +import ServerConfigDialog from './components/ServerConfigDialog.vue' import { useGlobalApproval } from './composables/useGlobalApproval' import { initWebMCP, getWebMCP } from './services/webmcp' import { initTorch, destroyTorch } from './services/torch' import { initSessionStateWS, destroySessionStateWS } from './services/session-state-ws' -import { endpoints } from './config/endpoints' import { initToolRegistry, activatePageTools, initToolsOnRefresh } from './services/toolRegistry' import { setResponseControls } from './services/tools/handlers/responseHandlers' import { useCanvasStore } from './stores/canvas' import { useProjectCanvasStore } from './stores/projectCanvas' import { useSessionState } from './stores/session-state' +import { isTauri } from './lib/tauri' +import { useServerConfig } from './stores/server-config' const route = useRoute() const router = useRouter() + +// Tauri server config +const serverConfig = isTauri ? useServerConfig() : null +const showServerConfig = ref(false) +const needsServerConfig = computed(() => isTauri && serverConfig && !serverConfig.isConfigured) + const showVoice = ref(false) const showTranscriptDebug = ref(false) const showDebugConsole = ref(false) @@ -293,6 +301,20 @@ watch(() => route.name, (newPage) => { activatePageTools(newPage as PageName) } }) + +// Watch for Tauri server config changes — re-init services when server is configured +if (serverConfig) { + watch(() => serverConfig!.isConfigured, async (configured) => { + if (configured) { + showServerConfig.value = false + // Re-initialize all services with the new server URL + initSessionStateWS() + initWhisperSocket() + await initWebMCP() + await initTorch() + } + }) +}