5.6 KiB
Configuration
Project home · Documentation · 简体中文
For a first installation, follow getting started. This page covers configuration, maintenance, and troubleshooting.
Directories and permissions
BOOKS_DIRcontains your books. Use:rofor read-only access, or:rwplus filesystem write permissions for administrator file management.DATA_DIRstores SQLite, accounts, reading records, keys, covers, scan state, upload staging, remote downloads, and plugin data. It must always be writable.DATA_DIRmust not be the same directory as, or a child of,BOOKS_DIR. Startup rejects that configuration.- The image entrypoint attempts to fix ownership of the data directory itself, then runs as the
readeruser. It does not change book-directory ownership or recursively repair existing data-file permissions.
Read-only books do not prevent account or progress updates in the data directory. To enable uploads, check host ACLs and directory permissions as well as changing the mount to :rw.
Environment variables
These are defaults when running the server directly. The Docker image additionally sets DATA_DIR=/data and WEB_DIR=/app/web, with BOOKS_DIR=/books.
| Variable | Default | Purpose |
|---|---|---|
BOOKS_DIR |
/books |
Book directory |
DATA_DIR |
data under the current working directory |
Server state and caches |
HOST |
0.0.0.0 |
Listen address |
PORT |
8080 |
Listen port |
PUBLIC_URL |
Empty | Public-facing URL; set when using a reverse proxy |
SCAN_INTERVAL |
1800 |
Scheduled scan interval in seconds; 0 disables it |
WATCH_INTERVAL |
60 |
Change-check interval in seconds; 0 disables it |
ALLOW_REGISTRATION |
false |
Allow public registration after the first account |
ACCESS_TOKEN_TTL |
86400 |
Access-token lifetime in seconds |
REFRESH_TOKEN_TTL |
31536000 |
Refresh-token lifetime in seconds |
READER_TOKEN_SECRET |
Generated | Signing secret, at least 16 characters; otherwise stored in DATA_DIR/token.secret |
LOG_LEVEL |
info |
Logging level |
CORS_ORIGINS |
Empty | Comma-separated browser origins; empty reflects the requesting origin |
WEB_DIR |
web under the current working directory |
Built Web client directory |
TTS_URL |
Empty | HTTP speech upstream; empty disables HTTP speech |
TTS_TOKEN |
Empty | Upstream Bearer token |
TTS_VOICES_URL |
<TTS_URL>/voices |
Upstream voice list |
TTS_TIMEOUT_MS |
20000 |
Speech request timeout in milliseconds |
TTS_CACHE_BYTES |
268435456 |
Byte limit for DATA_DIR/tts-cache; 0 disables caching |
Run docker compose up -d after changing environment variables. Keep the signing secret stable to preserve sessions. Accounts, progress, and notes cannot be recovered by rescanning book files.
HTTPS and reverse proxies
Use http://<server-ip>:8080 on your LAN. Use HTTPS for public access to protect login credentials and access tokens.
For Caddy running on the same host as reader:
reader.example.com {
reverse_proxy 127.0.0.1:8080
}
Set PUBLIC_URL=https://reader.example.com. If Caddy also runs in a container, use reader's service address on the container network instead.
For separately hosted frontends, set CORS_ORIGINS to the Web client's actual origin. Source search uses Streamable HTTP: proxies must forward text/event-stream incrementally rather than buffer the entire response. A VPN or tunnel can provide access when you have no public IP.
HTTP text-to-speech
Use Android system speech or browser speechSynthesis when available. To enable an HTTP speech service, configure a compatible upstream in Compose:
environment:
TTS_URL: "http://your-tts-host:5002/tts"
# TTS_TOKEN: "your-token"
# TTS_VOICES_URL: "http://your-tts-host:5002/voices"
TTS_CACHE_BYTES: "268435456"
reader proxies speech requests and does not include a synthesis model. The upstream must implement the expected request protocol; a service's name alone does not establish compatibility. See the TTS API (中文). The address must be reachable from the reader container; localhost inside a container refers to that container.
Troubleshooting
Data directory is not writable at startup
Check docker compose logs --tail=100 reader. For EACCES on /data/token.secret, the database, or caches:
- Confirm
/datais writable and has free space. - If you set
user:,--user, or replace the entrypoint, ensure that user can write the data directory. - Run
docker compose run --rm --no-deps --entrypoint id reader readerto inspect the image'sreaderUID/GID, then correct host directory ownership or ACLs. If you use a custom runtime user, use that user's identity instead. - NFS, SMB, and NTFS may need their own permission configuration rather than
chownalone.
Setting READER_TOKEN_SECRET only avoids writing the secret file. It does not remove the need for writable database and cache storage.
File management returns READ_ONLY_MOUNT
Check whether the mount uses :ro. After switching to :rw and recreating the container, verify the server process can write the target directory. Uploads are available only on the administrator file-management page.
The UI opens but books are missing
Check that the mounted files are readable and supported, then wait for scanning or trigger a scan as an administrator. The scanner skips directories such as .git, @eaDir, and #recycle and does not follow symlinks. Use the library file page to inspect the actual directory.