QuQu (蛐蛐)

repository·main·Indexed 24 days ago

https://github.com/yan5xu/ququ

An open-source, privacy-focused desktop voice input and text processing tool for Chinese users. It provides local speech recognition via FunASR and intelligent text optimization using OpenAI-compatible LLMs (such as Tongyi Qianwen, Kimi, and Zhipu AI). The application features a recording-to-transcription-to-optimization lifecycle with automatic pasting capabilities.

Tokens
7.6K
Snippets
5
Records
37
Agent score
80%

What's inside ququ

  1. Install QuQu using uv (Recommended)

    main

    The recommended way to initialize the project is using uv, a modern Python package manager that automatically manages Python versions and dependencies to avoid environment conflicts.

    Prerequisites

    • Node.js 18+ and pnpm
    • macOS 10.15+, Windows 10+, or Linux

    Installation Steps

    1. Clone the repository and enter the directory.
    2. Install Node.js dependencies using pnpm.
    3. Install uv if you haven't already.
    4. Use uv sync to initialize the Python environment (this will automatically download Python 3.11 and all required dependencies).
    5. Download the FunASR models.
    6. Start the application.

    Note: uv handles the Python environment isolation for you.

    # 1. 克隆项目
    git clone https://github.com/yan5xu/ququ.git
    cd ququ
    
    # 2. 安装 Node.js 依赖
    pnpm install
    
    # 3. 安装 uv (如果尚未安装)
    # macOS/Linux:
    curl -LsSf https://astral.sh/uv/install.sh | sh
    # Windows:
    # powershell -ExecutionPolicy ByPass -c "irm https://astral.sh/uv/install.ps1 | iex"
    
    # 4. 初始化 Python 环境 (uv 会自动下载 Python 3.11 和所有依赖)
    uv sync
    
    # 5. 下载 FunASR 模型
    uv run python download_models.py
    
    # 6. 启动应用!
    pnpm run dev
  2. Install QuQu using system Python

    main

    If you prefer using your existing system Python environment, follow these steps:

    Prerequisites

    • Node.js 18+ and pnpm
    • Python 3.8+

    Installation Steps

    1. Clone the repository and enter the directory.
    2. Install Node.js dependencies using pnpm.
    3. Create and activate a virtual environment (recommended).
    4. Install the required Python packages: funasr, modelscope, torch, torchaudio, librosa, and numpy.
    5. Download the FunASR models.
    6. Start the application.

    Note: Manual installation requires you to manage the virtual environment and dependencies yourself.

    # 1. 克隆项目
    git clone https://github.com/yan5xu/ququ.git
    cd ququ
    
    # 2. 安装 Node.js 依赖
    pnpm install
    
    # 3. 创建虚拟环境 (推荐)
    python3 -m venv .venv
    source .venv/bin/activate  # Linux/macOS
    # .venv\Scripts\activate   # Windows
    
    # 4. 安装 Python 依赖
    pip install funasr modelscope torch torchaudio librosa numpy
    
    # 5. 下载 FunASR 模型
    python download_models.py
    
    # 6. 启动应用!
    pnpm run dev
  3. Install QuQu using embedded Python environment

    main

    For production builds or complete isolation, QuQu supports an embedded Python environment.

    Installation Steps

    1. Clone the repository and enter the directory.
    2. Install Node.js dependencies using pnpm.
    3. Prepare the embedded Python environment using pnpm run prepare:python.
    4. (Optional) Verify the environment with pnpm run test:python.
    5. Start the application with pnpm run dev.

    Note: This method is intended for production deployment to ensure no external dependencies are required.

    # 1-2. 同上克隆项目并安装 Node.js 依赖
    
    # 3. 准备嵌入式 Python 环境
    pnpm run prepare:python
    
    # 4. 测试环境是否正常
    pnpm run test:python
    
    # 5. 启动应用
    pnpm run dev
  4. App Component Overview

    main
    The App component is the main entry point for the QuQu application. It manages the core user interface, including recording controls, text display for transcribed and AI-optimized text, model status monitoring, and settings navigation. It integrates with Electron APIs for system-level actions like pasting text and managing windows, while providing fallback mechanisms for web environments.
  5. How the application initializes and handles environment-specific logic

    main

    The application uses an initializeApp function to configure the runtime environment. Key behaviors include:

    • Electron Integration: Checks for window.electronAPI to determine if it is running in an Electron environment. If present, errors are logged via window.electronAPI.log('error', ...).
    • Global Error Handling: Sets up listeners for error and unhandledrejection events to capture and log errors (to Electron or the console).
    • UI/UX Defaults:
      • Sets the document language to zh-CN.
      • Disables default drag-and-drop behaviors (dragover, drop).
      • In production, disables the context menu (contextmenu).
    • Theme Management: Detects and listens to system color scheme changes (prefers-color-scheme: dark) to toggle the .dark class on document.documentElement.
    • Development Tools: In development mode, it enables Hot Module Replacement (HMR) for App.jsx and starts performance/memory monitoring (logging performance measures and heap usage every 30 seconds).
  6. Understand the FunASR model lifecycle stages

    main

    The useModelStatus hook manages the model through several distinct stage values. Understanding these stages is critical for building appropriate UI feedback:

    StageDescription
    checkingInitial state while the hook is verifying files and server status.
    need_downloadModel files are missing from the local system.
    downloadingThe downloadModels process is currently active.
    loadingModel files are present, but the FunASR server is still initializing/loading them into memory.
    readyThe model is fully loaded and the server is ready to process requests.
    errorAn error occurred during checking, downloading, or loading.

    Note: The hook automatically polls for status changes every 3 seconds if the model is not yet ready or isDownloading (and not on a settings/control page).

  7. How the application lifecycle and managers are initialized

    main

    The application follows a specific initialization sequence in main.js to ensure all dependencies are ready before the UI is presented:

    1. Environment Setup: The setupProductionPath() function runs first to ensure Python and other critical binaries are in the system PATH for production builds (macOS/Windows).
    2. Logging & Error Handling: A LogManager is initialized, and global handlers for uncaughtException and unhandledRejection are attached to capture errors.
    3. Manager Instantiation: Core managers (EnvironmentManager, WindowManager, DatabaseManager, etc.) are instantiated.
    4. Database Initialization: The databaseManager is initialized using a directory provided by the environmentManager.
    5. IPC Setup: IPCHandlers are initialized, receiving all manager instances to facilitate communication between the main process and renderer processes.
    6. App Startup (startApp):
      • Initializes funasrManager (non-blocking).
      • Creates the Main Window and Control Panel Window via windowManager.
      • Sets up the System Tray via trayManager.

    This sequence ensures that when the windows are created, the underlying services (database, clipboard, speech recognition) are already operational.

  8. Detect Electron environment via window.electronAPI

    main

    The application identifies if it is running within an Electron container by checking for the existence of window.electronAPI.

    This is used to:

    1. Enable specialized logging: window.electronAPI.log('error', message).
    2. Enable application control: window.electronAPI.closeWindow().
    3. Determine if certain features (like the context menu) should be restricted.
  9. How the audio processing pipeline works

    main

    When stopRecording is called, the hook executes a multi-stage pipeline:

    1. Audio Capture: The MediaRecorder collects audio chunks (WebM/Opus).
    2. Format Conversion: The WebM Blob is converted to a WAV format (16000Hz, mono) using an AudioContext and a custom audioBufferToWav utility.
    3. Transcription: The WAV data is sent to the backend via window.electronAPI.transcribeAudio.
    4. Immediate UI Update: If window.onTranscriptionComplete is defined, the raw transcription is sent to the UI immediately.
    5. AI Optimization (Optional): If the enable_ai_optimization setting is true, the hook calls window.electronAPI.processText(raw_text, 'optimize') to refine the text.
    6. Persistence: The final transcription (either raw or optimized) is saved via window.electronAPI.saveTranscription.
    7. Final UI Update: If window.onAIOptimizationComplete is defined, the final enhanced result is sent to the UI.

    Note: This hook relies on the presence of window.electronAPI for backend communication. In a standard web environment, it falls back to mock results.

  10. Locate QuQu data, log, cache, and model directories

    main

    QuQu stores its persistent data in platform-specific directories based on the application name 蛐蛐:

    • Windows: %USERPROFILE%\AppData\Roaming\蛐蛐
    • macOS: ~/Library/Application Support/蛐蛐
    • Linux: ~/.config/蛐蛐
    • Other: ~/.蛐蛐

    Within the data directory, the following subdirectories are managed:

    • logs/: Application log files.
    • cache/: Temporary cache files.
    • models/: AI/ASR model files.
  11. Manage Recording and AI Optimization Lifecycle

    main

    The application follows a specific lifecycle for voice-to-text processing:

    1. Recording: Triggered via toggleRecording(). The UI enters a recording state.
    2. Transcription: Once recording stops, the useRecording hook handles transcription. Upon completion, window.onTranscriptionComplete is triggered, which updates originalText.
    3. AI Optimization: The application then waits for AI optimization. When complete, window.onAIOptimizationComplete is triggered, updating processedText.
    4. Auto-Paste: After successful AI optimization, the application attempts to automatically paste the text using safePaste().

    Developers interacting with the underlying hooks should note that originalText represents the raw FunASR output, while processedText represents the enhanced version.

  12. Configure AI models in QuQu

    main

    After starting the application, you can configure your preferred AI service provider via the Settings page.

    To enable intelligent optimization (polishing, error correction, and summarization), you must provide:

    • API Key
    • Base URL
    • Model Name

    QuQu supports any OpenAI-compatible service and is optimized for domestic Chinese models such as Tongyi Qianwen (通义千问), Kimi, and Zhipu AI (智谱AI). Configurations are saved locally.