部署 教程
5 分钟完成部署,从 Docker 安装到上线运行,按顺序跟做即可。
getStorageType 或 book.format/book.title 异常,getRemoteBookFilename 也永不返回空串(兑底用 book.hash 作文件名)· 上传失败响应体新增 hint + received 字段 · 下载失败响应体新增 hint + receivedFileKey 字段 · 放宽 download fallback 的 parts.length 检查。v8.12.1:紧急修复 v8.12.0 上游同步误覆盖 Lite 自定义代码:① 下载书籍报 "File not found"(
getRemoteBookFilename 在 'local' 存储类型返回空串 → fileKey 缺文件名段);② 「关于」按钮弹出官方 Readest 页面(AboutWindow 被覆盖成上游版本)。v8.12:上游 Readest v0.11.17 全量同步(逐文件对比,163 个安全文件直接复制 + 21 个新文件添加 + 58 个 Lite 自定义文件保留不覆盖)· 排除 Google Drive/payment/tests · 手动同步 30+ 个类型字段。
v8.11:合并上游 v0.11.17 功能:Markdown (.md) 文件渲染 · PDF/CBZ 对比度选项 · TTS 高亮粒度(单词/句子)· 最近阅读书架 · 自动翻页角落区域 50px 上限 · 清理空高亮 · foliate-js 自动更新(PDF pinch-zoom/翻页性能)。
v8.10.4:恢复跨设备视图设置同步(用户中心 → Manage Sync → View Settings toggle,默认关)。
v8.10.3:登出后隐藏全部书籍(修复 demo books 残留)· 移出分组不再踢出用户。
v8.10.2:笔记导出链接绝对 URL(站外可点击)· Reader 书不在库里时自动重试加载 · 用户管理折叠。
v8.10.1:批量下载 per-URL Cookie/Headers 语法(
URL | cookie:VALUE | header:Key: VALUE)。v8.10:中文汉化(zh-CN + zh-TW 补全 60 个翻译 key)· 笔记导出链接手机默认走 web reader · 登出后清空残留 library.json · 阅读统计(总/今日/本周 + 书榜)· 下载记录折叠。
v8.9:下载任务大增强:进度条/速度/ETA/用时 · 点击任务看完整日志 · 批量下载 · 自动重命名 · Cookie/Headers 高级选项。
v8.8:分块上传规避 Cloudflare 524 超时(大文件自动切 5MB · 服务端流式合并 · 小文件零变化)。
v8.7:跨设备下载任务队列(DownloadTask 表落库 · 用户中心面板 · 5s 轮询 · 暂停/恢复/重试 · 批量操作)。
v8.6:合并上游 Readest 0.11.12 · 图片保存按钮 · 分享永久(∞)+自定义有效期 · 远程下载任务队列 · 安卓自编译源码。
v8.5:配额真正 enforce · 真实配额 UI · SSRF 黑名单 · fire-and-forget 下载。
v8.4:Per-user 加密 vault(AES-GCM + 服务端托管密钥)。
v8.3:账号切换数据隔离。
v8.2:代理开关 · 全站 Readest Lite 品牌。
v8.1:远程下载写 Book 表 · ADMIN_USERNAME env。
v8.0:所有翻译/词典代理强制登录。
v7.0:多用户管理 · 远程书籍下载 · Edge TTS · 字体本地化。
环境准备
只需要 Docker,无需安装 Node.js 或数据库。
- 系统:Linux / macOS / Windows (WSL2)
- Docker:20.10+ 及 Compose V2
- 内存:最低 512MB,推荐 1GB+
- 端口:默认 8225(可改)
安装 Docker
# 一键安装 Docker curl -fsSL https://get.docker.com | sh sudo usermod -aG docker $USER sudo systemctl enable --now docker # 验证 docker --version
newgrp docker 使权限生效。macOS 推荐 Docker Desktop。快速开始
一条命令拉起,30 秒后访问 http://localhost:8225。
docker run -d \ --name readest-lite \ -p 8225:8225 \ -v readest-data:/data \ -e ADMIN_EMAIL=admin@example.com \ -e ADMIN_PASSWORD=changeme \ -e ADMIN_USERNAME=Admin \ -e PUBLIC_BASE_URL=https://read.yourdomain.com \ --restart unless-stopped \ ghcr.io/cshdotcom/readest-lite:latest
CLI 方式环境变量说明
通过 docker run -e 传递,常用 env:
ADMIN_EMAIL(必填):管理员邮箱,首次启动自动创建账号ADMIN_PASSWORD(必填):管理员密码,建议 16+ 位随机字符串ADMIN_USERNAME(可选,v8.1 新增):管理员显示名,用户列表里展示用。未设置时回退到邮箱PUBLIC_BASE_URL(可选,反向代理场景必填):对外访问 URL,用于生成上传/下载文件的签名 URL。例如https://read.yourdomain.com。未设置时默认http://localhost:8225,浏览器外不可达PORT(可选,默认 8225):容器内监听端口,一般不需修改DEEPL_ENABLED=true(可选):启用 DeepL 翻译,需配合DEEPL_FREE_API_KEYS或DEEPL_PRO_API_KEYS
ghcr.io/cshdotcom/readest-lite:v8.12.2(每个版本都有对应 git tag,详见 GitHub Releases)。Docker Compose 部署(推荐)
配置清晰、升级方便、重启自动恢复,适合长期运行。
docker-compose.yml
version: "3.8" services: readest-lite: image: ghcr.io/cshdotcom/readest-lite:latest container_name: readest-lite restart: unless-stopped ports: - "${PORT:-8225}:8225" volumes: - ./data:/data environment: - ADMIN_EMAIL=${ADMIN_EMAIL} - ADMIN_PASSWORD=${ADMIN_PASSWORD} - PUBLIC_BASE_URL=${PUBLIC_BASE_URL:-} - DEEPL_ENABLED=${DEEPL_ENABLED:-false}
.env
ADMIN_EMAIL=admin@example.com ADMIN_PASSWORD=your-secure-password PORT=8225 # 可选:反向代理场景必填 PUBLIC_BASE_URL=https://read.yourdomain.com # 可选:翻译功能(默认关闭) DEEPL_ENABLED=false DEEPL_FREE_API_KEYS= DEEPL_PRO_API_KEYS=
常用命令
docker compose up -d # 启动 docker compose ps # 状态 docker compose logs -f # 日志 docker compose down # 停止
restart: unless-stopped 确保容器在 Docker 重启或意外退出后自动恢复。环境变量
容器启动时读取,修改后需重启生效。
| 变量 | 必填 | 默认 | 说明 |
|---|---|---|---|
| ADMIN_EMAIL | 必填 | — | 管理员邮箱,首次启动自动创建账号 |
| ADMIN_PASSWORD | 必填 | — | 管理员密码,建议 16+ 位随机字符串 |
| ADMIN_USERNAME | 可选 | — | v8.1 新增:管理员显示名,用户列表里展示用。未设置时回退到邮箱 |
| PUBLIC_BASE_URL | 可选 | http://localhost:8225 | 对外访问 URL,反向代理/分享场景必填。例如 https://read.yourdomain.com |
| PORT | 可选 | 8225 | 容器内监听端口,一般不需修改 |
| DEEPL_ENABLED | 可选 | false | 设为 true 启用 DeepL 翻译,需配合 DEEPL_FREE_API_KEYS 或 DEEPL_PRO_API_KEYS |
| JWT_SECRET | 可选 | 派生 | JWT 密钥,不设置时由 ADMIN_EMAIL + ADMIN_PASSWORD 派生 |
.env 加入 .gitignore,避免密码泄露到版本控制。数据持久化
所有数据存储在容器 /data 目录,通过卷挂载确保容器重建不丢失。
目录结构
备份
# 停止容器后打包 tar czf readest-backup-$(date +%Y%m%d).tar.gz data/ # 保留最近 30 天 find . -name "readest-backup-*.tar.gz" -mtime +30 -delete
反向代理
生产环境推荐通过反向代理暴露到公网,并配置 HTTPS。
Nginx
server { listen 443 ssl http2; server_name read.yourdomain.com; ssl_certificate /path/to/fullchain.pem; ssl_certificate_key /path/to/privkey.pem; location / { proxy_pass http://127.0.0.1:8225; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-Proto $scheme; # WebSocket(同步功能必需) proxy_http_version 1.1; proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "upgrade"; proxy_read_timeout 86400; } }
Caddy(更简单)
read.yourdomain.com { reverse_proxy localhost:8225 }
升级更新
定期升级获取最新功能与修复,数据不受影响。
# 拉取最新镜像 docker compose pull # 重建容器(数据在 ./data 不受影响) docker compose up -d # 清理旧镜像 docker image prune -f
多用户管理
管理员可以在用户中心创建和管理普通用户。
创建用户
- 管理员登录后进入「用户中心」
- 在「用户管理」面板点击「新建用户」
- 填写邮箱、密码、显示名称
- 设置存储配额(MB)和翻译配额(KB),0 = 无限
- 点击创建,用户即可用邮箱密码登录
常见问题
启动后无法访问?
docker ps确认容器状态为Upcurl http://localhost:8225在服务器本地测试- 检查防火墙:
sudo ufw allow 8225 docker logs readest-lite查看错误日志
如何修改密码?
修改 .env 中的 ADMIN_PASSWORD,然后 docker compose down && docker compose up -d。
如何换端口?
修改 docker-compose.yml 端口映射:"9000:8225"(左边是对外端口)。
书籍存在哪里?
data/books/uploads/ 存书籍原文,data/books/covers/ 存封面图,容器重建不丢失。
支持多用户吗?
支持!管理员登录后在「用户中心」可以看到「用户管理」面板,可以创建普通用户、设置用户名密码、分配存储和翻译配额。普通用户登录后只能看到自己的账号信息,没有管理权限。
切换账号后,原来账号的书会泄露吗?
v8.3 起不会。登出时系统会彻底清空当前账号的:
- 书库列表(library.json 覆盖为空)
- 同步游标(lastSyncedAtBooks/Configs/Notes 重置为 0)
- 第三方服务凭据(WebDAV/KOSync/Readwise/Hardcover/AI 全部重置)
- App Lock PIN(清空)
- 上传/下载队列(清空)
登录新账号后,系统走全量 pull(since=0),只拉取新账号的云端书。本地 Books/ 目录下的书籍文件保留(不删),但不会出现在新账号的书库列表里——除非新账号的云端也有同 hash 的书。
未登录时导入的书:如果你没登录就导入了书,登录账号后这些书会自动同步到当前登录的账号(不会被清空)。
如何使用远程下载?
在书库页面点击「导入」→「Download from URL」,输入书籍直链地址(如 https://example.com/book.epub)。v8.1 修复了书架不显示问题:下载完成后服务器同时写入 Book 表,新书会出现在书库中,多端 sync 同步可见。
翻译和词典需要登录吗?
v8.0 起所有翻译/词典代理强制要求登录,包括:
/api/translate/google(Google 翻译)/api/proxy/wiki(Wikipedia / Wiktionary 词典查询)/api/proxy/resource(通用资源代理)/api/deepl/translate(DeepL,本就强制登录)
未登录调用返回 401。客户端无需加速器:只要服务器能访问 Google,前端通过代理就能用。
浏览器直接访问 /api/translate/google 显示"认证失败"是 bug 吗?
不是 bug,是预期行为。翻译/词典代理是 POST 接口,需要 Authorization: Bearer <token> 头。浏览器地址栏直接 GET 访问不会带这个头,所以返回 401 "Authentication required"。
v8.2 给三个代理路由加了 GET health check,返回带 hint 字段的 JSON,告诉你如何用 curl 测试:
# 测试 Google 翻译代理(替换 YOUR_TOKEN 和 your-host) curl -H "Authorization: Bearer YOUR_TOKEN" \ -X POST -H "Content-Type: application/json" \ -d '{"text":["hello"],"targetLang":"zh"}' \ https://your-host/api/translate/google # 测试 Wikipedia 代理 curl -H "Authorization: Bearer YOUR_TOKEN" \ "https://your-host/api/proxy/wiki?url=https://en.wikipedia.org/api/rest_v1/page/summary/Hello"
在应用内正常使用(选中文字 → 翻译/词典按钮)会自动带 token,不需要手动操作。
v8.2 代理开关怎么用?
登录后进入「设置 → Integrations → Network」,有「Server Proxy」开关:
- 开启(默认):翻译/词典走服务器代理,客户端无需加速器
- 关闭:客户端直连 Google/Wikipedia 等目标 URL,需要客户端本地网络能访问这些站点(例如客户端在国外网络或自备加速器)
注意:Edge TTS 不受此开关影响(始终保持 wss 直连 + https 代理降级行为)。DeepL 也不受影响(API key 在服务器,必须走代理)。
100TB 配额是硬限制吗?
不是。100TB 是前端展示用的软上限,实际不强制执行——上传代码不查配额,真正的限制只有宿主机磁盘空间。管理员在用户管理面板设置的 storageQuotaMB 字段当前为展示型(v8.3 计划补上 enforce 逻辑)。
翻译和词典需要加速器吗?
不需要(代理开启时)。Google 翻译、Wikipedia、Wiktionary 都通过服务器代理访问。只要服务器能访问 Google(如国外 VPS),客户端无需加速器即可使用。如果关了代理开关,客户端需要自己能访问这些站点。
如何启用 DeepL 翻译?
在 .env 中设置 DEEPL_ENABLED=true 和 DEEPL_FREE_API_KEYS 或 DEEPL_PRO_API_KEYS,重启容器即可。
如何迁移数据?
直接复制整个 data/ 目录到新服务器,用相同参数启动容器即可。SQLite 文件可跨平台使用。