👁 49

昨晚十点多,网盘面板还能正常打开,但一点进 /Disk/123Pan 这个目录就废了,列目录、上传、重命名统统失手,页面上只有一行:

写入失败:failed init storage: request failed with status: 403 Forbidden

先把结论放前面:文件一个都没丢,账号也没被封,是 OpenList 这个客户端被联通云盘的边缘节点挡在门外了。整件事跟容器、数据库、token 过期都没关系。

一、症状:只有联通云盘那个存储挂了

面板能登录、别的目录能进、后台能看日志,说明服务本身活着。真正报错的只有一个存储——挂载点是 /Disk/123Pan 的联通云盘(WoPan 驱动)。同一台机器上 123 云盘正常,天翼和阿里云盘各有各的毛病,但报错文案完全不一样,后面我列了张对照表。

换句话说:如果只是某一个网盘挂了、其他存储好好的,别急着怀疑 OpenList 本身。

二、排查:容器活着,token 也没过期

三步先排掉最常见的误判:

  • 容器 Up,本机 127.0.0.1:7076 请求 2 ms 返回 200 —— 不是后端假死;
  • 用库里现成的 access_token 直接去打联通云盘的接口,能通 —— 不是 token 失效;
  • 日志里只有存储初始化失败,没有 panic、没有容器退出 —— 不是崩了。

那么问题只剩一个方向:请求长什么样。日志去掉重复行之后就这么几行:

INFO  [wopan] init storage: /Disk/123Pan
ERROR [wopan] failed init storage: request failed with status: 403 Forbidden
...(后面几行同样的报错,略)

三、定位:封的是 go-resty 的 User-Agent

拿同一个 access_token、同一个接口,只改请求头里的 User-Agent,结果直接分裂:

User-Agent HTTP 返回
浏览器 UA(Mozilla/5.0 … Chrome/141) 200 RSP_CODE 0000 服务调用成功
go-resty/2.16.5(OpenList 默认) 403 联通拦截页(HTML,不是 JSON)
空 UA(什么都不带) 200 正常 JSON

结论很干脆:2026-10-20 起,联通云盘边缘节点把 Go resty 的默认 UA 拉黑了,只拦 go-resty/x.y.z 这个字符串,浏览器 UA 和空 UA 都放行。

而 OpenList / AList 的联通云盘驱动底层就是 go-resty,SDK 只在分片上传那一个环节设过 UA,列目录、取下载地址、刷新 token 全是默认 UA 裸奔。所以表现就是:能登录、能看到存储条目,一初始化就 403。

四、官方进度:修是修了,但还没发版

这不是你一个人遇到。OpenList 仓库今天集中冒出几条相关记录:

编号 内容 状态
#3218 [BUG] 联通云盘无法使用 已关闭
#3220 给所有联通请求加浏览器 UA(另一位提交) 关闭,未合并
#3222 加 UA + 初始化前先刷新 token,附单元测试 已合并进 main
alist #9674 同款修复,提交给 3.x 还开着

合并时间是 2026-10-20 20:38(北京时间),提交 57cd71c,三个文件、+249/−9。修复除了给请求加浏览器 UA,还顺手补了两件事:access token 为空或长度不足时先刷新再初始化、刷新后的 token 写回存储配置。

但关键问题是:v4.2.7 是 10-15 发的,比这次修复早五天。所以现在去 Docker Hub 拉官方镜像,装上去照样 403 —— 得等下一个版本。

五、怎么办:三条路,按省事程度排

1)等官方新版(大多数人选这个)

关注 release 页面,出 v4.2.8 之后直接换镜像或换二进制,数据目录不用动。这段时间里能用就先用网页端顶着。

2)自己编一个(我现在跑的就是这条)

思路很简单:在驱动初始化时把 UA 设成浏览器 UA。改动就一行,但要连带补前端产物,否则起不来。

git clone --depth 1 -b v4.2.7 https://github.com/OpenListTeam/OpenList.git
# 编辑 drivers/wopan/driver.go,在 DefaultWithRefreshToken 之后加一行:
#     d.client.SetUserAgent(wopan.DefaultUA)

# 前端产物仓库里没有,必须单独下,否则启动报 index.html not exist
tar xzf openlist-frontend-dist-v4.2.7.tar.gz -C public/dist --strip-components=1

CGO_ENABLED=0 go build -tags=jsoniter 
  -ldflags "-s -w -X 'github.com/OpenListTeam/OpenList/v4/internal/conf.Version=v4.2.7+wopanua'" 
  -o openlist .

替换前务必做两件事:备份旧二进制和 data.db;拿一份 data.db 副本在别的端口起个测试实例,确认那个存储的状态从报错变成 work,再动生产。

我第一次编的时候忘了补前端产物,容器直接起不来,报 index.html not exist, you may forget to put dist of frontend to public/dist,硬生生 502 了十几分钟才回滚。所以别省这一步。

3)还在用 AList 3.x

官方那个 PR 还没合,只能自己照同样思路改 drivers/wopan/driver.go,或者先退回网页端。

六、别把 403 和 8005 搞混

这次排查里最容易走偏的地方:同一台机器上几个云盘同时报错,但原因完全不同。我整理了一张对照表,看到报错先对号入座。

报错 真正含义 怎么处理
403 Forbidden 客户端 UA 被拦 升级 / 打 UA 补丁
8005 登录失败 refresh token 真失效了 重新登录联通云盘
需要二次设备校验 天翼云盘风控 网页登录过一次验证
refresh token 错误 阿里云盘授权过期 重新授权

我这边就有两个号是 8005,跟这次 403 一点关系没有,得重新登录取 token。之前写过一个把 token 一键写进 OpenList 的 Chrome 插件,就是干这个用的:联通云盘 token 一键写入 OpenList。

七、一句提醒

如果你也在 10-20 之后突然发现联通云盘挂载失败,先去看日志里有没有 go-resty 和 403。有,就是这次的事,等新版或者打补丁;没有,再往 token 和风控方向查。

别急着重装、删库、清配置 —— 这波 403 跟你的数据一点关系都没有,重装一百遍也一样 403。等官方 v4.2.8 出来,这条就彻底过去了。

OpenList 仓库
Issue #3218
PR #3222
提交 57cd71c