Successfully resolved the WebSocket "Disconnected" issue in the Bun-compiled standalone executable by implementing a unified Bun server that replaces the incompatible Node.js ws module with Bun's native WebSocket API, without modifying any source code.
When compiling the Auditaria into a standalone Windows executable using Bun, the web interface (-w flag) would show "Disconnected" instead of maintaining a WebSocket connection. This occurred because:
- Module Incompatibility: The
wsnpm module depends on Node.js internals not available in Bun runtime - Multiple Usage Points: Both
packages/cli/src/services/WebInterfaceService.tsandpackages/web-server/src/websocket/websocketHandler.jsuse thewsmodule - Runtime Differences: Bun uses uWebSockets internally, requiring a different API than Node.js
- Web interface loads but shows "Disconnected"
- WebSocket upgrade requests fail or return "Not a WebSocket request"
- Locale files cannot be read from the compiled executable
- Process doesn't stay alive in web mode
A build script that modifies the JavaScript bundle during compilation to:
-
Runtime Detection
- Detects Bun runtime via
typeof Bun !== 'undefined' - Only activates replacements when running in Bun
- Falls back to original code in Node.js environments
- Detects Bun runtime via
-
Unified Server Architecture
- Creates a single
Bun.serve()instance handling both HTTP and WebSocket - Replaces Express server + ws WebSocketServer combination
- Maintains single port for all communication
- Creates a single
-
Module Override Strategy
- Globally replaces
WebSocketServerandWebSocketclasses - Intercepts
require('ws')calls - Patches module cache entries
- Provides API-compatible mock objects
- Globally replaces
-
Asset Embedding
- Embeds 18 web client files as base64 strings
- Embeds locale files (en.json, pt.json) to prevent file system errors
- Serves all assets from memory
-
Compatibility Layer
- Mock WebSocket objects maintain
wsmodule API - Event handlers (
on,send,close) work identically - State management preserved for existing code
- Mock WebSocket objects maintain
# 1. Install Bun on Windows
powershell -Command "irm bun.sh/install.ps1 | iex"
# 2. Build the bundle (creates bundle/gemini.js)
npm run bundle
# 3. Create standalone executable with WebSocket fix
node sea/build-bun-unified.cjs
# 4. Run the executable
auditaria-standalone.exe -w no-browser-
Interactive Mode Fix
// Original (web mode not recognized as interactive) const interactive = !!argv.promptInteractive || process33.stdin.isTTY && question.length === 0; // Fixed (includes web mode) const interactive = !!argv.promptInteractive || !!argv.web || (process33.stdin.isTTY && question.length === 0);
-
WebSocket Server Override
// Replaces all instantiations new (globalThis.WebSocketServer || import_websocket_server.default)
-
Locale Warning Suppression
- Warnings about missing locale directories are commented out
- Locale data loaded from embedded globals instead of file system
sea/build-bun-unified.cjs- The complete build script with all fixesWEBSOCKET-SOLUTION-REPORT.md- This documentation
.github/workflows/build-windows-exe.yml- Updated to use the new build script.gitignore- Updated for Bun artifacts
packages/cli/src/services/WebInterfaceService.ts- Unchangedpackages/web-server/src/websocket/websocketHandler.js- Unchanged- All other source files remain unmodified
In Node.js (npm run dev, npm run build):
- Original Express + ws code executes
- No Bun code runs (runtime check fails)
- WebSockets work normally via
wsmodule
In Bun Executable:
- Runtime detection triggers Bun code path
- Unified Bun server starts on specified port
- HTTP requests serve embedded web client files
- WebSocket upgrades handled by Bun's native API
- All ws module calls redirected to Bun implementation
-
Client Connection
- Browser requests WebSocket upgrade
- Bun.serve() handles upgrade via
server.upgrade(req) - Connection added to global client set
-
Message Exchange
- Client messages parsed and routed to handlers
- Server broadcasts using native
ws.send() - State synchronized across all clients
-
Compatibility Maintenance
- Mock objects preserve existing event handler patterns
on('message'),on('close')etc. work identically- No changes needed in application logic
- ✅ WebSocket shows "Connected" in web interface
- ✅ Real-time message exchange functional
- ✅ No locale warning messages
- ✅ Process stays alive in web mode
- ✅ All existing features preserved
# Build and test locally
node sea/build-bun-unified.cjs
auditaria-standalone.exe -w no-browser
# Open browser to http://localhost:8629
# Verify WebSocket connection
# Check browser console - should show "Connected to Auditaria"The workflow at .github/workflows/build-windows-exe.yml has been updated to:
- Use
npm run bundleinstead ofnpm run build - Execute
sea/build-bun-unified.cjsinstead of direct Bun compile - Include WebSocket support in release notes
- Executable Size: ~125MB (includes all embedded assets)
- Startup Time: Comparable to original
- WebSocket Latency: Native Bun performance (typically faster than ws module)
- Memory Usage: Slightly higher due to embedded assets
When syncing with upstream or updating the codebase:
- No special handling needed for WebSocket code
- Build script handles all transformations automatically
- New
wsmodule usage will be automatically intercepted
If WebSocket issues occur:
- Check browser console for connection errors
- Verify port availability (default 8629)
- Look for
[Bun]prefixed console messages - Ensure Windows Firewall allows the executable
This solution provides a complete, maintainable fix for WebSocket connectivity in Bun-compiled executables without modifying any source code. The build-time transformations ensure compatibility while preserving the ability to run the same codebase in Node.js environments. The approach is transparent to developers and requires no changes to existing development workflows.