| .github | ||
| drizzle | ||
| examples | ||
| public | ||
| src | ||
| tests | ||
| .gitattributes | ||
| .gitignore | ||
| Dockerfile | ||
| drizzle.config.pg.ts | ||
| drizzle.config.sqlite.ts | ||
| empty-module.ts | ||
| eslint.config.mjs | ||
| LICENSE | ||
| next.config.ts | ||
| NOTICE.txt | ||
| package.json | ||
| playwright.config.ts | ||
| pnpm-lock.yaml | ||
| postcss.config.mjs | ||
| README.md | ||
| tailwind.config.ts | ||
| template.env | ||
| tsconfig.json | ||
📄🔊 OpenReader WebUI
OpenReader WebUI is an open source text to speech document reader web app built using Next.js, offering a TTS read along experience with narration for EPUB, PDF, TXT, MD, and DOCX documents. It supports multiple TTS providers including OpenAI, Deepinfra, and custom OpenAI-compatible endpoints like Kokoro-FastAPI and Orpheus-FastAPI
- 🎯 Multi-Provider TTS Support
- Kokoro-FastAPI: Supporting multi-voice combinations (like
af_heart+af_bella) - Orpheus-FastAPI
- Custom OpenAI-compatible: Any TTS API with
/v1/audio/voicesand/v1/audio/speechendpoints - Cloud TTS Providers (requiring API keys)
- Deepinfra: Kokoro-82M + models with support for cloned voices and more
- OpenAI API (
): tts-1, tts-1-hd, and gpt-4o-mini-tts w/ instructions
- Kokoro-FastAPI: Supporting multi-voice combinations (like
- 🛜 (Updated) Server-side Sync and Storage
- (New) External Library Import enables importing documents to the browser's storage from a folder mounted on the server
- (Updated) Sync documents between the browser and server to get them on other browsers or devices
- 🎧 Server-side Audiobook Export in m4b/mp3, with resumable, chapter-based export and regeneration
- 📖 Read Along Experience providing real-time text highlighting during playback (PDF/EPUB)
- (New) Word-by-word highlighting uses word-by-word timestamps generated server-side with whisper.cpp (optional)
- 🧠 Smart Sentence-Aware Narration merges sentences across pages/chapters for smoother TTS
- 🚀 Optimized Next.js TTS Proxy with audio caching and optimized repeat playback
- 🎨 Customizable Experience
- 🎨 Multiple app theme options
- ⚙️ Various TTS and document handling settings
- And more ...
🐳 Docker Quick Start
Prerequisites
- Recent version of Docker installed on your machine
- A TTS API server (Kokoro-FastAPI, Orpheus-FastAPI, Deepinfra, OpenAI, etc.) running and accessible
Note: If you have good hardware, you can run Kokoro-FastAPI with Docker locally (see below).
1. 🐳 Start the Docker container
Minimal (no persistence, auth disabled unless you set auth env vars):
docker run --name openreader-webui \
--restart unless-stopped \
-p 3003:3003 \
ghcr.io/richardr1126/openreader-webui:latest
Fully featured (persistent storage + server library import + KokoroFastAPI in Docker + optional auth):
docker run --name openreader-webui \
--restart unless-stopped \
-p 3003:3003 \
-v openreader_docstore:/app/docstore \
-v /path/to/your/library:/app/docstore/library:ro \
-e API_BASE=http://host.docker.internal:8880/v1 \
-e API_KEY=none \
-e BETTER_AUTH_URL=http://localhost:3003 \
-e BETTER_AUTH_SECRET=<paste_the_output_of_openssl_here> \
ghcr.io/richardr1126/openreader-webui:latest
You can remove the /app/docstore/library mount if you don't need server library import.
You can remove both BETTER_AUTH_* env vars to keep auth disabled.
Notes:
API_BASEshould point to your TTS API server's base URL (if running Kokoro-FastAPI locally in Docker, usehttp://host.docker.internal:8880/v1).BETTER_AUTH_URLshould be your externally-facing URL for this app (for examplehttps://reader.example.comorhttp://localhost:3003).- To enable auth, set both
BETTER_AUTH_URLandBETTER_AUTH_SECRETgenerated withopenssl rand -base64 32.- If you set
POSTGRES_URL, the container will attempt to run migrations against it. Ensure the database is accessible.
Docker environment variables (Click to expand)
| Variable | Purpose | Example / Notes |
|---|---|---|
API_BASE |
Default TTS API base URL (server-side) | http://host.docker.internal:8880/v1 |
API_KEY |
Default TTS API key | none or your provider key |
BETTER_AUTH_URL |
Enables auth when set with BETTER_AUTH_SECRET |
External URL for this app, e.g. http://localhost:3003 or https://reader.example.com |
BETTER_AUTH_SECRET |
Enables auth when set with BETTER_AUTH_URL |
Generate with openssl rand -base64 32 |
POSTGRES_URL |
Use Postgres for auth storage instead of SQLite | If set, startup migrations target Postgres |
GITHUB_CLIENT_ID |
Optional GitHub OAuth sign-in | Requires GITHUB_CLIENT_SECRET |
GITHUB_CLIENT_SECRET |
Optional GitHub OAuth sign-in | Requires GITHUB_CLIENT_ID |
Docker volume mounts (Click to expand)
| Mount | Type | Recommended | Purpose | Example |
|---|---|---|---|---|
/app/docstore |
Docker named volume | Yes | Persists server-side storage (documents, audiobook exports, settings, SQLite DB if used) | -v openreader_docstore:/app/docstore |
/app/docstore/library |
Bind mount (host folder) | Optional + :ro |
Exposes an existing folder of documents for Server Library Import | -v /path/to/your/library:/app/docstore/library:ro |
To import from the mounted library: Settings → Documents → Server Library Import
Note: Every file in the mounted library is imported into the client browser's storage. Keep the library reasonably sized to avoid performance issues.
Visit http://localhost:3003 to run the app and set your settings.
2. ⚙️ Configure the app settings in the UI
- Set the TTS Provider and Model in the Settings modal
- Set the TTS API Base URL and API Key if needed (more secure to set in env vars)
- Select your model's voice from the dropdown (voices try to be fetched from TTS Provider API)
3. ⬆️ Updating Docker Image
docker stop openreader-webui && \
docker rm openreader-webui && \
docker pull ghcr.io/richardr1126/openreader-webui:latest
🗣️ Local Kokoro-FastAPI Quick-start (CPU or GPU)
You can run the Kokoro TTS API server directly with Docker. We are not responsible for issues with Kokoro-FastAPI. For best performance, use an NVIDIA GPU (for GPU version) or Apple Silicon (for CPU version).
Kokoro-FastAPI (CPU)
docker run -d \
--name kokoro-tts \
--restart unless-stopped \
-p 8880:8880 \
-e ONNX_NUM_THREADS=8 \
-e ONNX_INTER_OP_THREADS=4 \
-e ONNX_EXECUTION_MODE=parallel \
-e ONNX_OPTIMIZATION_LEVEL=all \
-e ONNX_MEMORY_PATTERN=true \
-e ONNX_ARENA_EXTEND_STRATEGY=kNextPowerOfTwo \
-e API_LOG_LEVEL=DEBUG \
ghcr.io/remsky/kokoro-fastapi-cpu:v0.2.4
Adjust environment variables as needed for your hardware and use case.
Kokoro-FastAPI (GPU)
docker run -d \
--name kokoro-tts \
--gpus all \
--user 1001:1001 \
--restart unless-stopped \
-p 8880:8880 \
-e USE_GPU=true \
-e PYTHONUNBUFFERED=1 \
-e API_LOG_LEVEL=DEBUG \
ghcr.io/remsky/kokoro-fastapi-gpu:v0.2.4
Adjust environment variables as needed for your hardware and use case.
⚠️ Important Notes:
- For best results, set the
-e API_BASE=for OpenReader's Docker tohttp://kokoro-tts:8880/v1- For issues or support, see the Kokoro-FastAPI repository.
- The GPU version requires NVIDIA Docker support and works best with NVIDIA GPUs. The CPU version works best on Apple Silicon or modern x86 CPUs.
Local Development Installation
Prerequisites
-
Node.js (recommended: use nvm)
-
pnpm (recommended) or npm
npm install -g pnpm -
A TTS API server (Kokoro-FastAPI, Orpheus-FastAPI, Deepinfra, OpenAI, etc.) running and accessible Optionally required for different features:
-
FFmpeg (required for audiobook m4b creation only)
brew install ffmpeg -
libreoffice (required for DOCX files)
brew install libreoffice -
whisper.cpp (optional, required for word-by-word highlighting)
# clone and build whisper.cpp (no model download needed – OpenReader handles that) git clone https://github.com/ggml-org/whisper.cpp.git cd whisper.cpp cmake -B build cmake --build build -j --config Release # point OpenReader to the compiled whisper-cli binary echo WHISPER_CPP_BIN=\"$(pwd)/build/bin/whisper-cli\"Note: The
WHISPER_CPP_BINpath should be set in your.envfile for OpenReader to use word-by-word highlighting features.
Steps
-
Clone the repository:
git clone https://github.com/richardr1126/OpenReader-WebUI.git cd OpenReader-WebUI -
Install dependencies:
With pnpm (recommended):
pnpm i # or npm i -
Configure the environment:
cp template.env .env # Edit .env with your configuration settingsAuth is recommended for contributors and is enabled when both values are set:
-
Set
BETTER_AUTH_URLto your local URL (default:http://localhost:3003) -
Generate a
BETTER_AUTH_SECRETand paste it into.env:openssl rand -base64 32
Note: To disable auth, remove either
BETTER_AUTH_URLorBETTER_AUTH_SECRET.Note: The base URL for the TTS API should be accessible and relative to the Next.js server
-
-
Run auth DB migrations:
-
Production / Docker: Migrations run automatically on startup via
pnpm start. -
Development: Run explicitly:
pnpm migrate
Note: If you set
POSTGRES_URLin.env, migrations will target Postgres instead of local SQLite.Generating migrations (contributors):
pnpm generategenerates migrations for both SQLite and Postgres (requiresPOSTGRES_URL).
Manual Drizzle Kit runs:
- SQLite migrate:
npx drizzle-kit migrate --config drizzle.config.sqlite.ts - Postgres migrate:
npx drizzle-kit migrate --config drizzle.config.pg.ts - SQLite generate:
npx drizzle-kit generate --config drizzle.config.sqlite.ts - Postgres generate:
npx drizzle-kit generate --config drizzle.config.pg.ts
-
-
Start the development server:
With pnpm (recommended):
pnpm dev # or npm run devor build and run the production server:
With pnpm:
pnpm build # or npm run build pnpm start # or npm startVisit http://localhost:3003 to run the app.
💡 Feature requests
For feature requests or ideas you have for the project, please use the Discussions tab.
🙋♂️ Support and issues
If you encounter issues, please open an issue on GitHub following the template (which is very light).
👥 Contributing
Contributions are welcome! Fork the repository and submit a pull request with your changes.
❤️ Acknowledgements
This project would not be possible without standing on the shoulders of these giants:
- Kokoro-82M model
- Kokoro-FastAPI
- whisper.cpp
- ffmpeg
- react-pdf npm package
- react-reader npm package
Docker Supported Architectures
- linux/amd64 (x86_64)
- linux/arm64 (Apple Silicon, Raspberry Pi, SBCs, etc.)
Stack
- Framework: Next.js (React)
- Containerization: Docker
- Storage:
- Dexie.js IndexedDB wrapper for client-side storage
- PDF:
- EPUB:
- Markdown/Text:
- UI:
- TTS: (tested on)
- Deepinfra API (Kokoro-82M, Orpheus-3B, Sesame-1B)
- Kokoro FastAPI TTS
- Orpheus FastAPI TTS
- NLP:
- compromise NLP library for sentence splitting
- cmpstr String comparison library
- whisper.cpp for TTS timestamps (word-by-word highlighting)
License
This project is licensed under the MIT License.