Files
Meeting_Assistant/openspec/changes/archive/2025-12-22-add-embedded-backend-packaging/design.md
egg e7a06e2b8f chore: Archive all pending OpenSpec proposals
Force archive the following proposals:
- add-audio-device-selector (complete)
- add-embedded-backend-packaging (19/26 tasks)
- add-flexible-deployment-options (20/21 tasks)

New specs created:
- audio-device-management (7 requirements)
- embedded-backend (8 requirements)

Updated specs:
- transcription (+2 requirements for model download progress)

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2025-12-22 08:44:04 +08:00

4.3 KiB

Design: Embedded Backend Packaging

Context

Meeting Assistant uses a three-tier architecture: Electron Client → FastAPI Middleware → MySQL/Dify. For enterprise deployment, administrators want to distribute a single executable that users can run without additional setup. The backend must still connect to remote MySQL and Dify services (no local database).

Stakeholders:

  • Enterprise IT administrators (simplified deployment)
  • End users (double-click to run)
  • Developers (maintain backward compatibility)

Goals / Non-Goals

Goals

  • Package backend as a sidecar executable using PyInstaller
  • Electron manages backend lifecycle (start on launch, stop on close)
  • Single config.json for all configuration (frontend, backend, whisper)
  • Health check ensures backend is ready before showing UI
  • Backward compatible with existing separate-deployment mode
  • Show Whisper model download progress to improve UX

Non-Goals

  • Embedding MySQL database (still remote)
  • Embedding LLM model (still uses Dify API)
  • Removing external authentication (still requires company SSO)
  • Pre-bundling Whisper model (user downloads on first run)

Decisions

Decision 1: Use PyInstaller for Backend Packaging

What: Package FastAPI + uvicorn as standalone executable using PyInstaller --onedir mode.

Why:

  • Consistent with existing transcriber sidecar approach
  • --onedir provides faster startup than --onefile
  • Team already has PyInstaller expertise

Alternatives considered:

  • Nuitka: Better optimization but longer build times
  • cx_Freeze: Less community support for FastAPI

Decision 2: Configuration via Extended config.json

What: Add backend section to existing config.json with database, API, and auth settings.

Why:

  • Single configuration file for users to manage
  • Runtime modifiable without rebuilding
  • Consistent with existing whisper config pattern

Schema:

{
  "apiBaseUrl": "http://localhost:8000/api",
  "backend": {
    "embedded": true,
    "host": "127.0.0.1",
    "port": 8000,
    "database": { "host": "", "port": 33306, "user": "", "password": "", "database": "" },
    "externalApis": { "authApiUrl": "", "difyApiUrl": "", "difyApiKey": "", "difySttApiKey": "" },
    "auth": { "adminEmail": "", "jwtSecret": "", "jwtExpireHours": 24 }
  }
}

Decision 3: Health Check Before Window Display

What: Electron polls /api/health endpoint before creating main window.

Why:

  • Prevents "connection refused" errors on startup
  • Provides clear feedback if backend fails to start
  • Maximum 30 attempts with 1-second intervals

Decision 4: Backward Compatibility via Feature Flag

What: backend.embedded: false (default) preserves existing behavior; true enables embedded mode.

Why:

  • Existing deployments continue working unchanged
  • Gradual migration path for enterprises
  • Same codebase supports both deployment models

Decision 5: Huggingface Hub Progress Callback for Model Download

What: Intercept huggingface_hub download progress and emit JSON status messages.

Why:

  • faster-whisper uses huggingface_hub internally
  • Can emit progress without modifying faster-whisper source
  • JSON format consistent with existing sidecar protocol

Risks / Trade-offs

Risk Impact Mitigation
PyInstaller hidden imports missing Backend fails to start Comprehensive hidden-import list; test on clean Windows
Config file contains sensitive data Security exposure Document security best practices; consider encryption
Backend startup timeout Poor UX Increase timeout; show loading indicator
Port 8000 already in use Backend fails Allow configurable port; detect and report conflicts

Migration Plan

For New Deployments (All-in-One)

  1. Build with --embedded-backend flag
  2. Configure config.json with database/API credentials
  3. Distribute single exe to users

For Existing Deployments (Separate Backend)

  1. No changes required
  2. Ensure backend.embedded: false in config
  3. Continue using existing backend deployment

Rollback

  • Set backend.embedded: false to disable embedded backend
  • Deploy backend separately as before

Open Questions

  • Should we add config validation UI on first startup?
  • Should backend port be auto-discovered if 8000 is in use?