Telegram 频道视频自动转存到 115 网盘:部署、排错、测速与迁移全记录

Telegram 频道视频自动转存到 115 网盘:部署、排错、测速与迁移全记录
落魄君子Telegram 频道视频自动转存到 115 网盘:部署、排错、测速与迁移全记录
本文记录一套实际搭建过的 Telegram 频道视频转存方案,并保留搭建过程中遇到的问题、失败链路、诊断方法与迁移思路。文中的公网 IP、频道名称、频道 ID、账号信息、Token、Cookie 和 Session 均使用示例值代替。
请只备份你有权保存的内容,不要将 115 挂载用于多人分发、图床、软件分发或视频外链播放等不规范用途。OpenList 的 115 Open 文档也明确提醒,账号使用方式不规范可能带来封禁风险。
一、目标与最终效果
目标是让服务器长期运行一个自动化任务:
1 | Telegram 频道发布视频 |
本文还会覆盖以下扩展需求:
- 同时监听多个公开或私有频道;
- 启动时补传最近若干个历史视频;
- 批量归档整个频道的历史媒体;
- VPS 磁盘较小时避免被视频塞满;
- OpenList 中目录不刷新、没有新建目录按钮;
my.telegram.org创建应用只显示ERROR;- 私有频道使用
-100...ID 时 Telethon 无法解析; - Telegram 媒体位于其他 DC 时的日志解释;
- 大文件上传到 115 极慢或卡住;
- 判断是 OpenList 问题、115 上传问题,还是 VPS 到 115 的线路问题;
- 将整套服务迁移到香港、日本、国内服务器或家中 NAS。
二、可选链路总览
Telegram 到 115 并不只有一种实现方式。先根据需求选架构,再开始部署。
| 方案 | 链路 | 适合场景 | 优点 | 局限 |
|---|---|---|---|---|
| 方案 A | Telegram 频道 → tg-rclone → rclone → OpenList WebDAV → 115 Open |
自动监听频道 | 组件清晰;OpenList 使用 115 官方开放平台授权;便于浏览与管理 | WebDAV 多一层;大文件可能超时、重试或卡住;速度依赖 VPS 到 115 的线路 |
| 方案 B | Telegram 频道 → Telethon/tg-rclone → 115cli → 115 |
自动监听、大文件直传测试 | 绕过 OpenList WebDAV,链路更短 | 115cli 是非官方工具;使用 115 Cookie;不同版本的大文件上传能力需要实测 |
| 方案 C | Telegram 文件手动转发 → TG115 Bot → CloudDrive2 WebDAV → 115 | 只挑选部分视频保存 | 不需要监听整个频道;转发给自己的 Bot 后自动处理;有队列与磁盘预算设计 | 需要手动转发;依赖闭源 CloudDrive2;不等于自动监听频道 |
| 方案 D | Telegram 频道 → tg-archiver 批量下载 → rclone/115cli 上传 |
一次性搬运历史频道 | 断点、进度和元数据更完整;适合老频道 | 需要较大磁盘;不是实时转存的最佳方案 |
| 方案 E | Telegram 下载节点 → rsync/SFTP → 115 上传节点 → 115 | 单台 VPS 无法同时兼顾 Telegram 和 115 | 可以把 Telegram 线路和 115 线路分别优化 | 多一台机器,运维更复杂 |
| 方案 F | Telegram → 自写 115 Open API 上传器 → 115 | 高级开发者、长期维护 | 可绕过 WebDAV和 Cookie | 需要自行实现 Token 刷新、分片、重试、校验和异常恢复 |
我的实际结论
如果一台 VPS 能同时高速访问 Telegram 和 115,优先测试:
1 | Telethon/tg-rclone → 115cli 直传 |
如果希望使用官方 115 开放平台授权、并且文件不大,可以先测试:
1 | tg-rclone → rclone WebDAV → OpenList → 115 Open |
如果只有少量视频需要保存,而不是全频道自动监听,TG115 的“转发给 Bot”模式更省心。
如果海外 VPS 到 115 的线路极差,继续调 --transfers 通常没有意义,应直接换 VPS 或采用双节点架构。
三、本文实测环境与目录约定
实测旧服务器大致为:
1 | 系统:Debian/Ubuntu 类 Linux |
统一使用以下目录:
1 | /opt/tg115/ |
示例变量统一使用:
1 | VPS IP:203.0.113.10 |
第一部分:OpenList + 115 Open + rclone WebDAV
四、检查服务器环境
1 | docker --version |
检查 5244 端口:
1 | ss -ltnp | grep ':5244' || true |
创建目录:
1 | mkdir -p /opt/tg115/{openlist,rclone,data} |
拉取 tg-rclone:
1 | git clone https://github.com/EdisonJwa/tg-rclone.git |
建议记录当前提交,方便以后知道补丁针对哪个版本:
1 | cd /opt/tg115/tg-rclone |
五、部署 OpenList
5.1 初次调试:直接开放 5244
初次搭建为了方便,可以临时公网访问:
1 | cat > /opt/tg115/docker-compose.yml <<'EOF' |
启动:
1 | cd /opt/tg115 |
浏览器访问:
1 | http://203.0.113.10:5244 |
如果系统启用了 UFW:
1 | ufw status |
如果云厂商还有安全组,也需要临时放行 TCP 5244。
公网直接暴露 5244 只建议用于调试。正式运行应改为绑定
127.0.0.1,再使用 Nginx 和 HTTPS。
5.2 设置管理员密码
1 | docker exec -it openlist ./openlist admin set '请替换为强密码' |
不要把密码写入教程、截图、GitHub 或聊天记录。
六、获取 115 Access Token 与 Refresh Token
OpenList 的 115 Open 驱动使用 115 官方开放平台 API。
操作流程:
- 打开 OpenList 提供的授权页面;
- 下拉框选择“115 验证网盘”;
- 某些界面会显示为“115 网盘(OAuth2)跳转登录”;
- 勾选“使用 OpenList 提供的参数”;
- Client ID 和 Application Secret 留空;
- 点击“获取 Token”;
- 登录 115 并授权;
- 保存 Access Token 与 Refresh Token。
这两个 Token 均属于敏感凭据,不要发给别人。
七、在 OpenList 中挂载 115
进入:
1 | OpenList 管理后台 |
填写:
1 | 驱动:115 开放平台 |
说明:
- 根文件夹 ID 为
0,代表整个 115 根目录; - 如果只希望挂载 115 内的某个目录,可进入该目录后查看浏览器 URL 中
cid=后面的数字; - 保存后,OpenList 首页应出现
115。
7.1 首页提示 storage not found
如果看到:
1 | failed get storage: storage not found; please add a storage first |
不是 OpenList 安装失败,只是还没有添加任何存储。
7.2 OpenList 没有“新建目录”按钮
可能原因:
- 当前会话不是管理员;
- 用户未开启“创建目录或上传”;
- WebDAV 管理权限未开启;
- 当前驱动或前端版本没有显示该入口。
最稳妥的方法是直接在 115 官方网页或 App 中创建:
1 | Telegram |
再回到 OpenList 刷新。
7.3 在 115 创建目录后,OpenList 刷新仍看不到
浏览器 F5 不一定会清除 OpenList 的存储目录缓存。
正确操作:
1 | 进入 /115 |
也可以等待缓存过期,或者在存储设置中临时缩短缓存时间。
八、配置 rclone 连接 OpenList WebDAV
OpenList 与 rclone 将处于同一个 Docker 网络,因此 WebDAV 地址使用容器名,不经过公网:
1 | http://openlist:5244/dav/ |
运行 rclone 配置:
1 | docker run --rm -it \ |
交互填写:
1 | n # New remote |
生成文件:
1 | ls -lah /opt/tg115/rclone |
应该看到:
1 | rclone.conf |
不要公开完整的 rclone.conf。
8.1 测试读取
1 | docker run --rm \ |
应看到:
1 | 115 |
继续:
1 | docker run --rm \ |
应列出 115 中的目录。
8.2 创建 Telegram 目录
1 | docker run --rm \ |
8.3 小文件写入测试
1 | echo "Telegram to 115 test $(date)" > /opt/tg115/data/test.txt |
上传:
1 | docker run --rm \ |
检查:
1 | docker run --rm \ |
只有小文件写入成功以后,才继续配置 Telegram,避免同时排查两端。
第二部分:Telegram API 与 Telethon Session
九、创建 Telegram API 应用
打开:
1 | https://my.telegram.org/apps |
登录后进入:
1 | API development tools |
示例:
1 | App title:TelegramBackup |
创建成功后保存:
1 | App api_id |
不要使用网上公开的 API ID/API Hash。Telegram 官方要求第三方客户端获取自己的凭据。
9.1 创建应用只弹出 ERROR
实际遇到过:
1 | 表单填写正常 |
常见处理顺序:
- 使用稳定 VPN 节点;
- 从登录到创建结束保持同一个出口 IP;
- 不要在提交过程中切换国家或节点;
- 打开无痕窗口重新登录;
- 关闭广告拦截或脚本拦截扩展;
- App title 与 Short name 只使用简单英文和数字;
- 换浏览器;
- 换网络;
- 不要短时间连续点击几十次,避免账号或 IP 触发临时限制。
如果账号曾经创建过 API 应用,应先检查原有 API ID,因为 Telegram 官方说明一个号码当前只能关联一个 API ID。
十、生成 TG_SESSION_STRING
先创建临时环境文件:
1 | cat > /opt/tg115/tg-session.env <<'EOF' |
生成 Session:
1 | docker run --rm -it \ |
交互输入:
1 | 手机号:国际格式,例如 +8613812345678 |
保存输出的:
1 | TG_SESSION_STRING=一长串字符 |
TG_SESSION_STRING相当于长期登录凭据。Telethon 文档明确提醒,拿到 Session 的人可能登录该账号。泄露后应立即在 Telegram“设置 → 设备”中终止对应会话。
写入正式 .env:
1 | nano /opt/tg115/.env |
内容:
1 | API_ID=12345678 |
设置权限:
1 | chmod 600 /opt/tg115/.env |
检查变量是否存在,但不要打印值:
1 | for k in API_ID API_HASH TG_SESSION_STRING; do |
十一、列出账号加入的 Telegram 频道
1 | docker run --rm -it \ |
示例输出:
1 | ID: -1001234567890 | - | 私有频道 A |
使用规则:
- 公开频道可使用
@channel_b; - 私有频道建议使用
-100...数字 ID; .env中不要给数字 ID 添加多余空格;- YAML 中最好加引号,避免被当作普通数字处理。
第三部分:修改 tg-rclone,只转存视频
十二、为什么不能直接使用原版
tg-rclone 原版功能是:
- 监听 Telegram 用户账号可访问的频道/群组;
- 支持私有频道;
- 处理文字、照片、视频、文档、音频、语音、贴纸、位置等;
- 每个文件调用
rclone copyto; - 上传成功后删除本地临时文件;
- 上传失败时保留本地文件,重启后重新入队。
我们的需求是“只转存视频”,因此要修改:
- 忽略文字、图片、音频和普通文档;
- 为下载文件保留
.mp4等扩展名; HISTORY_LIMIT=1应表示最近 1 个视频,而不是最近 1 条消息;- 私有频道使用数字 ID 时,需要从 dialogs 中解析
input_entity/access_hash。
十三、备份原文件并应用补丁
1 | cd /opt/tg115/tg-rclone |
下面的补丁适用于本文记录时的项目结构。仓库更新后如果匹配失败,应对照当前源码手工修改。
1 | python3 - <<'PY' |
检查语法:
1 | python3 -m py_compile /opt/tg115/tg-rclone/monitor.py \ |
没有报错才继续构建。
检查关键段落:
1 | grep -n -A45 -B5 \ |
1 | grep -n -A50 \ |
13.1 终端粘贴大段代码被破坏
实际遇到过 heredoc 粘贴后终端显示异常字符。
处理原则:
- 立即停止,不要构建;
- 从
monitor.original.py恢复; - 使用短补丁脚本,而不是重新粘贴 400 行完整文件;
- 每次都运行
python3 -m py_compile; - 使用
grep或sed检查关键区域。
恢复命令:
1 | cp -f /opt/tg115/tg-rclone/monitor.original.py \ |
十四、配置一个频道做端到端测试
先测试一个频道,不要一开始同时开多个容器。
清理旧配置项:
1 | cd /opt/tg115 |
追加:
1 | cat >> /opt/tg115/.env <<'EOF' |
检查非敏感变量:
1 | grep -E \ |
创建独立数据目录:
1 | mkdir -p /opt/tg115/data/channel-a |
十五、Docker Compose:单频道测试版
1 | cat > /opt/tg115/docker-compose.yml <<'EOF' |
构建:
1 | cd /opt/tg115 |
启动:
1 | docker compose up -d tg-channel-a |
日志:
1 | docker logs -f --tail 100 tg-channel-a |
正常日志过程:
1 | Starting tg-rclone |
注意:上传 worker 是异步运行的,因此可能先出现:
1 | Video backfill finished |
随后才出现:
1 | uploaded & cleaned |
十六、验证是否真正成功
16.1 查看容器是否运行
1 | docker ps --filter "name=tg-channel-a" |
16.2 查看日志
1 | docker logs --tail 50 tg-channel-a |
真正成功的关键标志:
1 | uploaded & cleaned |
16.3 查看 115 目录
1 | docker run --rm \ |
16.4 查看本地是否已删除
1 | find /opt/tg115/data/channel-a -type f -ls |
上传成功后,大视频应消失,只留下:
1 | state.json 或 video_state.json |
16.5 查看下载文件是否仍在增长
1 | watch -n 3 ' |
按 Ctrl+C 只会退出观察,不会停止容器。
十七、Telegram 日志中的“其他 DC”不是错误
日志可能出现:
1 | File lives in another DC |
这是 Telegram 媒体文件位于另一个数据中心,Telethon 正在借用新的 sender 下载媒体,属于正常流程。
只要:
- 容器仍为
Up; - 下载文件大小继续增长;
- 没有 Traceback;
就不要重启。
十八、私有频道报 Cannot find any entity
典型报错:
1 | ValueError: Cannot find any entity corresponding to "-1001234567890" |
原因不是频道 ID 一定错误,而是:
CHANNEL是一个字符串形式的数字 ID;- Telethon 访问私有频道历史消息还需要
access_hash; StringSession主要保存授权信息,不像 SQLite Session 那样持久保存完整实体缓存;- 直接
iter_messages("-100...")可能无法构造正确的 InputPeer。
解决方法就是本文补丁中的:
1 | async for dialog in client.iter_dialogs(): |
然后使用:
1 | client.iter_messages(target_entity) |
十九、FloodWait 与快速重启循环
如果容器因代码错误反复退出,而 Compose 设置了:
1 | restart: unless-stopped |
会形成:
1 | 启动 |
随后可能出现:
1 | Sleeping for 22s on GetContactsRequest flood wait |
正确做法:
1 | cd /opt/tg115 |
先修复代码并重新构建,再启动。不要连续 restart。
二十、从测试模式切换为长期监听
测试时:
1 | HISTORY_LIMIT=1 |
表示启动时找最近 1 个视频。
确认成功后,改成:
1 | HISTORY_LIMIT=0 |
只监听以后发布的新视频:
1 | sed -i \ |
查看:
1 | docker logs --tail 50 tg-channel-a |
应出现:
1 | Skip backfill; listen-only mode. |
二十一、批量补传历史视频
不要一开始设置很大的值,例如:
1 | HISTORY_LIMIT=10000 |
因为可能造成:
- Telegram FloodWait;
- VPS 磁盘被同时下载的文件占满;
- 115 上传队列长期堆积;
- 失败文件持续保留;
- 容器内存和网络压力过大。
推荐分批:
1 | HISTORY_LIMIT=5 |
每批确认完成后再增加。
检查磁盘:
1 | df -h / |
如果 VPS 只有 40GB 左右,至少保留 10~20GB 安全空间。
二十二、多个频道的正确部署方式
原版 tg-rclone 是单 CHANNEL、单 RCLONE_DEST。
有两种办法:
方法 1:每个频道一个容器
优点:
- 配置简单;
- 状态与下载目录互不干扰;
- 某个频道失败不影响其他频道。
建议每个并发容器生成一个独立的 TG_SESSION_STRING。API_ID 和 API_HASH 可以相同,但 Session 独立。
目录:
1 | /opt/tg115/ |
.env.channel-a:
1 | API_ID=12345678 |
.env.channel-b:
1 | API_ID=12345678 |
权限:
1 | chmod 600 /opt/tg115/.env.channel-a |
Compose:
1 | services: |
方法 2:自行改成一个进程监听多个频道
优点是只需要一个 Session 和一个容器,但需要:
- 维护
频道 ID → 115 目录映射; - 为每个频道维护独立状态;
- 防止多个视频同时下载把磁盘占满;
- 在事件处理器中根据
event.chat_id分流。
除非准备长期维护代码,否则每频道一个容器更容易排错。
第四部分:大文件上传慢或卡住的诊断
二十三、一个真实故障样本
实测某视频:
1 | 本地大小:1,119,128,862 bytes,约 1.04 GiB |
Telegram 下载正常完成,但 115 目录一直为空。
docker top 显示:
1 | rclone copyto /data/downloads/3513.mp4 \ |
docker stats 累计值显示:
1 | tg 容器接收约 1.15GB |
/proc/<PID>/io 中的读取量约为视频大小的 3 倍,并且 10 秒内不再增加。
这强烈暗示:
1 | 同一个 1.1GB 文件发生了多轮 PUT/重试 |
这不是普通的“速度稍慢”。
二十四、诊断命令
24.1 看容器累计网络与内存
1 | docker stats --no-stream tg-channel-a openlist |
注意:
NET I/O是容器启动以来的累计值,不是实时速度;- 适合判断是否发生了大量重复传输;
- OpenList 内存异常增大也值得关注。
24.2 看 rclone 子进程
1 | docker top tg-channel-a |
如果看到 rclone copyto,说明上传任务仍未结束。
24.3 看 rclone 是否还在读取本地文件
1 | PID=$(docker top tg-channel-a -eo pid,cmd \ |
判断:
- 数值持续增长:仍在读取或重新读取本地文件;
- 10 秒以上完全不变:可能在等待远端响应;
- 读取量接近文件大小的 2 倍、3 倍:可能发生整文件重试。
这只是诊断线索,不是所有系统上的绝对字节计费。
24.4 看进程等待点
1 | ps -o pid,ppid,stat,etime,wchan:32,cmd -p "$PID" |
例如:
1 | STAT=Sl |
说明进程正在等待网络或事件,不代表上传成功。
24.5 查看远端目录
1 | docker run --rm \ |
24.6 查看 OpenList 日志
1 | docker logs --since 60m openlist 2>&1 | tail -n 300 |
OpenList 没有输出日志并不等于没有问题,仍需结合进程、远端目录和网络统计判断。
24.7 停止任务但保留本地文件
1 | cd /opt/tg115 |
原项目只有在 rclone 返回成功时才删除本地文件。停止后检查:
1 | ls -lh /opt/tg115/data/channel-a/downloads/ |
二十五、为什么 --transfers=4 没让单个视频快四倍
--transfers 主要控制同时传输多少个文件,不等于把一个大视频自动拆成四份。
对于:
1 | 一个 1.1GB 的 MP4 |
WebDAV 后端通常仍表现为一个主要的 PUT 流。单文件多线程是否有效取决于后端和协议支持,不能仅靠提高 --transfers 解决。
因此:
- 多个小文件时,增加 transfers 可能有效;
- 单个大文件时,瓶颈往往在后端、线路、分片实现或服务器响应;
- 盲目提高并发可能增加重试、内存和风控风险。
二十六、OpenList WebDAV 大文件的已知风险
OpenList 的 115 Open 使用官方开放平台 API,但速度和稳定性仍与:
- OpenList 所在服务器网络;
- 115 服务器网络;
- 服务器性能;
- 临时上传凭证有效期;
- WebDAV 客户端行为;
- 文件大小和上传耗时;
有关。
OpenList 项目 Issue 中也出现过:
- 约 1.8GB 文件通过 WebDAV 写入时锁定或 context canceled;
- 15GB 文件上传时临时安全 Token 过期;
- 失败后客户端再次 PUT,产生重复传输。
因此大文件正式生产前必须做真实验收,不能只用几十字节的测试文件判断。
第五部分:115cli 直传方案
二十七、为什么测试 115cli
为了判断瓶颈是否来自 OpenList WebDAV,可以绕过 OpenList:
1 | 本地视频 |
如果 115cli 很快而 OpenList 很慢,说明问题更偏向 WebDAV/OpenList。
如果 115cli 也很慢,则更可能是:
1 | VPS → 115 上传节点 |
的线路问题。
115cli 是非官方项目,支持 Cookie 登录、目录浏览、上传与秒传等操作。请阅读项目免责声明,并以当前版本 README 为准。
需要特别注意:不同版本对大文件分片上传的实现状态可能不同。本文记录时,项目 README 将部分大文件能力列在后续计划中,因此不要在未验收前把它当成绝对稳定的大文件上传器。
二十八、安装 115cli
1 | cd /opt/tg115 |
创建独立 HOME:
1 | mkdir -p /opt/tg115/115cli-home |
二十九、安全登录 115cli
115cli 当前可使用以下 Cookie 字段:
1 | UID |
浏览器登录 115 后,在开发者工具中查看 115 域名 Cookie。
不要直接把 Cookie 写进命令行历史:
1 | read -rsp "Paste 115 Cookie: " PAN115_COOKIE |
登录:
1 | HOME=/opt/tg115/115cli-home \ |
立即清理变量:
1 | unset PAN115_COOKIE |
验证:
1 | HOME=/opt/tg115/115cli-home \ |
列目录:
1 | HOME=/opt/tg115/115cli-home \ |
1 | HOME=/opt/tg115/115cli-home \ |
三十、115cli 上传测速
对现有视频测试:
1 | time HOME=/opt/tg115/115cli-home \ |
某次实测显示:
1 | 约 18 kB/s |
此时可以基本排除“只有 OpenList WebDAV 慢”的判断,因为直传链路也慢。
结论更偏向:
1 | 当前海外 VPS 到 115 上传节点的路由很差 |
这种情况下继续调 Python、rclone 或 OpenList 参数意义不大,应该换上传出口。
按 Ctrl+C 停止测试后,确认本地文件仍在:
1 | ls -lh /opt/tg115/data/channel-a/downloads/ |
三十一、如何把 tg-rclone 改成 115cli 上传
逻辑上可以把原来的:
1 | rclone copyto local remote |
替换为:
1 | 115cli upload local /Telegram/Channel-A/filename |
但正式使用前必须处理:
- 115 Cookie 失效;
- 远端同名文件;
- 上传成功后的真实性校验;
- 秒传与真实上传的区别;
- 进程退出码;
- 中断后的残留文件;
- 失败重试次数;
- 超大文件是否分片;
- Cookie 或 WAF 风控;
- 多频道并发。
因此更稳妥的做法是:
- 在新 VPS 上先进行 100MB 和 1GB 实测;
- 确认速度与稳定性;
- 再将上传 worker 替换为 115cli;
- 保留“成功后删除、失败则保留”的原则;
- 不要只根据命令退出码判断,最好再执行
stat或ls -l校验远端大小。
第六部分:另外几种链路
三十二、TG115:手动挑选视频转存
TG115 的设计是:
1 | 在 Telegram 中看到文件 |
适合:
- 不想监听整个频道;
- 只挑选部分视频;
- 希望通过 Bot 查看任务状态;
- 需要队列、磁盘预算和大文件流式策略。
其正式支持范围主要是本人和 Bot 的一对一私聊。
局限:
- 需要手动转发;
- 依赖 CloudDrive2;
- CloudDrive2 是闭源软件;
- FUSE/特权容器需要额外安全评估;
- “WebDAV 接收完成”与“115 官方端最终入库完成”应分开确认。
三十三、tg-archiver:批量归档整个历史频道
tg-archiver 更适合一次性历史归档:
- 公开或私有频道;
- 群组;
- 保存媒体;
- 保存 Caption、消息 ID、时间等元数据;
- 记录进度;
- 中断后恢复;
- 跳过已下载内容。
典型链路:
1 | Telegram 历史频道 |
适合几百或几千个历史视频,但要提前估算磁盘。
建议:
- 下载与上传串行或小并发;
- 每完成一个文件立即上传;
- 上传成功后再清理;
- 定期备份 progress 和 metadata;
- 不要把全部历史视频一次性落盘后再上传。
三十四、双节点架构
当一台海外 VPS 访问 Telegram 很快,但访问 115 极慢,可以拆分:
1 | 节点 A:Telegram 下载节点 |
推荐节点 B:
- 中国大陆服务器;
- 家中 NAS 或电脑;
- 香港 CMI/CN2;
- 日本或新加坡优质中国方向线路。
不要只看“1Gbps 端口”,必须测试实际到 115 的上传速度。
双节点的优点:
- Telegram 与 115 分别选择最合适线路;
- 节点 A 不保存长期数据;
- 节点 B 可位于家中或国内网络。
缺点:
- 多一次传输;
- 需要 SSH 密钥;
- 需要处理节点 B 不在线的情况;
- 两边都要监控磁盘。
第七部分:整套服务迁移到新 VPS
三十五、先测试新 VPS,再迁移
不要购买后立即搬整套数据。
新 VPS 先安装最小环境:
1 | apt update |
检查:
1 | docker --version |
35.1 先做 115 上传测速
安装 115cli并登录后,创建一个不可压缩的 100MB 随机文件:
1 | dd if=/dev/urandom \ |
上传:
1 | time HOME=/opt/tg115/115cli-home \ |
建议标准:
1 | 低于 1 MB/s:不建议迁移 |
这些只是经验阈值,应按视频大小和数量调整。
通用 Speedtest 不能替代真实 115 上传测试。即使 VPS 对公共测速节点很快,也可能到 115 很慢。
三十六、停止旧 VPS 的写入任务
在旧 VPS:
1 | cd /opt/tg115 |
确认没有 rclone 或 115cli 上传进程:
1 | ps aux | grep -E 'rclone copyto|115cli upload' | grep -v grep |
不要同时在旧、新 VPS 上使用同一个 Session 长期监听同一个频道。
三十七、迁移方式一:只迁移配置和状态
在旧 VPS:
1 | rsync -avh --progress \ |
如果 SSH 不是 22 端口:
1 | rsync -avh --progress \ |
这种方式迁移:
.env;- Telegram Session;
- 代码;
- Compose;
- OpenList 数据;
- rclone 配置;
- 状态与日志;
但不迁移未上传的大视频。
三十八、迁移方式二:连未上传视频一起迁移
先迁移配置,再单独传大文件:
1 | rsync -avh --progress \ |
如果旧 VPS 到新 VPS 的线路较好,这通常比重新从 Telegram 下载更省时间。
注意目标目录:
1 | ssh root@新VPS_IP \ |
三十九、为什么不要复制 Python venv
venv115 中包含:
- Python 解释器路径;
- 软链接;
- 本机安装路径;
- 可能与系统架构或 Python 小版本相关的包。
因此在新 VPS 重建:
1 | rm -rf /opt/tg115/venv115 |
四十、新 VPS 上验证敏感配置
权限:
1 | chmod 600 /opt/tg115/.env* |
检查变量是否存在:
1 | for f in /opt/tg115/.env*; do |
不要执行:
1 | cat .env |
后再截图公开。
四十一、验证 115cli 登录状态
复制 115cli-home 后,登录状态不一定始终有效。
1 | HOME=/opt/tg115/115cli-home \ |
失败则重新使用 Cookie 登录。
不要把 Cookie 写入脚本、Compose 或 GitHub。
四十二、验证 rclone 和 OpenList
启动 OpenList:
1 | cd /opt/tg115 |
测试:
1 | docker run --rm \ |
如果 OpenList OAuth Token 与新 IP 相关的刷新逻辑异常,可重新授权并更新 Access Token/Refresh Token。
四十三、重新构建 Telegram 镜像
不要依赖旧服务器构建好的本地镜像。
1 | cd /opt/tg115 |
先只启动一个频道:
1 | docker compose up -d tg-channel-a |
验证完成后再启动其他频道。
四十四、迁移验收清单
新 VPS 必须全部通过:
- Docker 与 Compose 正常;
- OpenList 可以读取 115;
- rclone 能列出 115 目录;
- 115cli 能显示账号信息;
- 100MB 上传速度符合预期;
- Telegram Session 有效;
- 能解析私有频道;
- 能下载 1 个视频;
- 能上传 1 个视频;
- 115 官方客户端能看到文件;
- 本地文件上传成功后被删除;
- 容器重启后不会重复下载;
- VPS 重启后服务自动恢复;
- 磁盘空间保持在安全线之上。
完成后再清理旧 VPS。
四十五、回滚方案
新 VPS 失败时:
- 保留旧 VPS
/opt/tg115; - 不删除旧 VPS 的待上传视频;
- 停止新 VPS 容器;
- 确保只有一端运行 Telegram Session;
- 重新启动旧端:
1 | cd /opt/tg115 |
第八部分:正式运行的安全与维护
四十六、OpenList 正式环境改为本地监听
Compose:
1 | ports: |
Nginx 示例:
1 | server { |
申请证书:
1 | certbot --nginx \ |
如果 OpenList 仅用于后台管理,还可以进一步限制来源 IP。
四十七、敏感信息清单
以下内容均不能公开:
1 | Telegram API_HASH |
权限:
1 | chmod 600 /opt/tg115/.env* |
.gitignore:
1 | .env |
四十八、Session 泄露后的处理
Telegram:
1 | 设置 |
然后重新生成 TG_SESSION_STRING。
115 Cookie 泄露:
- 在 115 官方端退出相关登录;
- 修改密码;
- 重新获取 Cookie;
- 删除旧
115cli-home登录状态。
OpenList Token 泄露:
- 重新授权;
- 更新 Token;
- 检查账号异常访问。
四十九、常用运维命令
查看所有容器:
1 | docker ps |
查看日志:
1 | docker logs --tail 100 tg-channel-a |
重启单个频道:
1 | docker compose restart tg-channel-a |
停止单个频道:
1 | docker compose stop tg-channel-a |
重新构建:
1 | docker compose build --no-cache tg-channel-a |
查看磁盘:
1 | df -h / |
查找大文件:
1 | find /opt/tg115/data \ |
查看上传进程:
1 | docker top tg-channel-a |
查看 115 目录:
1 | docker run --rm \ |
五十、确认 Docker 开机自启
1 | systemctl is-enabled docker |
如果不是 enabled:
1 | systemctl enable docker |
Compose 服务设置:
1 | restart: unless-stopped |
VPS 重启后检查:
1 | docker ps |
五十一、备份配置
不备份临时视频:
1 | tar \ |
更严格的备份可以排除 venv115:
1 | tar \ |
备份文件本身包含敏感凭据,不能公开。
第九部分:问题速查表
| 现象 | 可能原因 | 处理 |
|---|---|---|
storage not found |
OpenList 未添加存储 | 添加 115 开放平台 |
| 115 新目录在 OpenList 看不到 | 目录缓存 | 在 OpenList 目录内点“刷新”,不要只按 F5 |
| OpenList 没有新建目录 | 权限或前端入口 | 在 115 官方端创建;检查管理员写入/WebDAV权限 |
| SSH 22 端口拒绝 | SSH 不是 22、服务未启动或防火墙 | 查 sshd -T、ss -ltnp;也可临时公网访问 OpenList |
| 创建 Telegram API 应用只显示 ERROR | VPN/IP/浏览器会话或 Telegram 风控 | 固定节点、无痕、重新登录、稍后再试 |
TG_SESSION_STRING 无效 |
Session 撤销、粘贴错误 | 重新生成并检查 .env |
私有频道 -100... 无法解析 |
缺少实体 access_hash | 从 iter_dialogs() 取得 dialog.input_entity |
FloodWait |
启动太频繁或历史扫描太快 | 停止重启循环,让程序等待,减小历史批次 |
File lives in another DC |
媒体在其他 Telegram 数据中心 | 正常现象,等待连接完成 |
| 下载文件在增长但日志不更新 | Telethon 正在下载大文件 | 用 find、du、watch 观察 |
| 日志显示 Listening,但文件仍在本地 | 异步 uploader 正在上传 | docker top 检查 rclone 子进程 |
| rclone 读取量是文件的 3 倍 | 可能发生整文件重试 | 查看 --retries、远端目录、OpenList日志 |
read_bytes 不再增长且 epoll_wait |
在等待远端响应或卡住 | 停止容器保留本地,改用直传测试 |
| OpenList 上传慢,115cli 也慢 | VPS 到 115 的线路差 | 换 VPS、国内/NAS上传节点或双节点 |
| 磁盘持续增长 | 上传失败文件被保留 | 查看日志与 leftovers;先解决上传端 |
| 两个频道状态混乱 | 共享同一 /data |
每个频道独立挂载数据目录 |
| 大段代码粘贴后语法损坏 | 终端 heredoc 混入字符 | 恢复备份,短补丁,运行 py_compile |
第十部分:最终选型建议
只偶尔保存几个文件
1 | TG115 + CloudDrive2 |
把文件转发给自己的 Bot,操作最简单。
自动监听一两个频道,文件不算太大
1 | tg-rclone |
先用 1GB 级真实视频测试,不能只测 test.txt。
希望缩短上传链路
1 | Telethon/tg-rclone |
需要接受非官方 Cookie 登录方式,并对大文件、Cookie 失效和风控做实测。
整个历史频道搬家
1 | tg-archiver |
重点是断点、磁盘预算和上传成功后的清理。
海外 VPS 到 115 极慢
1 | 迁移整套服务到更合适的 VPS |
或者:
1 | Telegram 海外下载节点 |
不要继续依赖参数微调掩盖线路问题。
十一、参考项目与官方资料
- tg-rclone:Telegram → Cloud via rclone
- Telegram 官方:Creating your Telegram Application
- Telethon:Sessions
- OpenList:115 Open 驱动文档
- OpenList:WebDAV 文档
- rclone:WebDAV 后端文档
- OpenList GitHub
- 115cli GitHub
- TG115 GitHub
- tg-archiver GitHub
- OpenList Issue:WebDAV 写入约 1.8GB 文件异常
- OpenList Issue:大文件上传时安全 Token 过期
十二、结语
这次部署最重要的经验不是“找到一条命令”,而是把链路拆开验收:
1 | Telegram 登录 |
每一段都单独验证,才能快速判断问题在哪。
最终实际遇到的关键问题是:
1 | Telegram 下载正常 |
因此根因更可能是旧 VPS 到 115 上传节点的线路,而不是 Telegram 下载程序。正确处理方式不是继续提高并发,而是先测试新的上传出口,再迁移整套服务。
对于长期自动化任务,稳定性优先于“看起来能跑”。真正的生产验收必须包括:
1 | 真实大文件 |
只有全部通过,才能称为 Telegram 频道视频自动转存到 115 的完整链路。





