简体中文
安全
Rust-Srec 会处理访问令牌、平台 Cookie、通知凭据、录制文件和弹幕数据。主机和每份备份都应按敏感基础设施管理。
认证边界
- 立即修改
admin/admin123!。应用会强制初始账号改密,但默认凭据仍不得暴露到网络。 - 为
JWT_SECRET和SESSION_SECRET生成至少 32 字符且互不相同的随机值。轮换JWT_SECRET会使访问令牌失效,应按 API 客户端中断来安排。 - 访问令牌有效期较短;刷新令牌是会轮换的会话凭据,保护级别应等同密码。
AUTH_DISABLED=true仅用于本机开发。后端只会在绑定回环地址时接受它,生产流程不得依赖该选项。该模式下,只有Origin位于API_CORS_ORIGINS允许列表内(或与请求自身的Host相同)的请求才会被受理;同时Host必须是回环名称或所配置的绑定地址——后者用于阻断 DNS 重绑定页面访问未认证的 API。仅在你能控制的来源上放宽该列表。- 连续登录失败会按账号限流(默认每 15 分钟 5 次),并另有一个宽松得多的按来源地址配额;被限流的请求直接返回
429和Retry-After等待时间,不再执行一次密码哈希。来源地址取自 TCP 对端且不信任X-Forwarded-For,因此在自带前端或任何反向代理之后,所有登录都会归到代理身上——不要依赖按地址的配额来隔离不同客户端。详见配置。 - 令牌中带有角色名,导出内容也包含用户账号,但路由层并未据此强制执行权限策略,也没有对接外部身份提供商。详见能力边界。
未知用户的登录尝试会执行与当前密码格式相同的有界 Argon2 验证工作。未知用户与 错误密码返回相同的凭据错误;只有密码正确时才返回账号已禁用。已被限流的请求 仍不会执行密码验证工作。
完整后端访问权限属于管理权限
已认证的登录会话或具有完整访问权限的 API 密钥,可以管理后端进程和文件。 仅向可信任其以运行后端的操作系统账户身份执行操作的人员和集成授予这些凭据。 令牌中的角色名称不会限制这项权限;目前没有仅能管理录制、却无法修改可执行 配置的独立操作员角色。
这项权限包括通过 execute 管道步骤直接执行命令,以及在 BaiduPCS 请求中指定 可执行文件路径。它也包括间接执行:引擎和处理器设置可选择工具程序,预设可 包含命令步骤,配置导入可引入这些设置,供后续录制或任务使用。文件路径、上传 目标以及移动和删除步骤,可以读取、传输、替换或删除服务账户有权访问的数据。 因此,来自其他来源的配置导入或预设,应按将在该账户下运行的代码进行审查。
只读 API 密钥受端点和工具允许列表限制;集成只需要受支持的读取操作时,应使用 只读密钥。它不提供录制操作员角色。参阅 API 密钥与 MCP。 操作系统权限、服务沙箱和容器挂载限制后端的访问范围,应仅授予必需的文件系统、 网络和设备权限。完整后端访问权限本身不会授予超出该运行环境的权限。
可撤销的登录会话
访问令牌和轮换的刷新令牌属于同一个持久化登录会话。退出登录会撤销该会话, 包括已经签发的访问令牌,但不会使其他设备退出。退出全部会话会撤销该用户的 所有登录会话与刷新令牌。修改密码会在同一数据库事务中撤销已有会话,需要用新 密码重新登录。禁用账号同样会撤销其会话,重新启用账号不会恢复旧令牌。 成功导入配置会撤销全部登录会话与刷新令牌。
每个可能授予访问权限的会话请求都会检查持久化的撤销状态与当前用户状态; 数据库故障时不会回退到缓存的允许结果。这些操作不会撤销单独管理的 API 密钥。
升级到绑定会话的访问令牌后,之前签发且未绑定会话的 JWT 将无法继续认证。 仍有效的旧刷新令牌可以换取绑定会话的新令牌对;否则需要重新登录。即使旧访问 令牌尚未到期,客户端也必须处理这次刷新或重新登录的兼容性切换。
刷新令牌轮换
客户端必须串行发送刷新请求,并在再次刷新前保存替换后的令牌。每个刷新令牌 只能签发一个替换令牌。旧令牌的消耗和新令牌的保存一起提交;数据库操作失败时 两者一起回滚。
REVOKE_ALL_ON_REFRESH_TOKEN_REUSE 默认为 true。重放尚未关闭的会话中 已经消耗的刷新令牌,会原子撤销该用户的全部登录会话与刷新令牌,包括已签发的 访问令牌。设为 false 时仅拒绝重放,不撤销其他会话。对于已经退出的会话, 重放其令牌不会导致其他设备退出。
REFRESH_TOKEN_REUSE_GRACE_SECS 默认为 0。设置为正数后,在最初吊销时间 起的指定秒数内重放,不会触发其他会话的吊销,但请求仍会失败,且绝不会再签发 一对令牌。与早期版本不同,宽限期不再允许使用已吊销的令牌刷新。在原子轮换 竞争中失败的请求遵循相同重用策略,因此默认设置下也会吊销获胜请求的访问令牌和刷新令牌。 客户端必须串行刷新,包括多个标签页或服务端实例发起的请求。
下载和日志 WebSocket 每五秒重新验证其登录会话或 API 密钥,每次检查最多等待 三秒。凭据撤销、到期、账号限制、权限不足或检查失败都会关闭连接,即使连接 正阻塞在发送数据的过程中。日志归档下载授权只能使用一次,有效期五分钟, 使用时会重新验证签发它的身份。
网络与会话安全
在前端之前终止 TLS,仅在反向代理不发送 X-Forwarded-Proto: https 时设置 COOKIE_SECURE=true,并用防火墙限制两个宿主机端口。没有直接 API 消费者时保持后端私有;不要向匿名互联网客户端公开 Swagger、媒体代理或日志接口。
自带的前端容器以非特权账号运行其应用服务(nginx 仍以 root 启动以绑定 80 端口,并由非特权工作进程处理请求),并为每个请求(包括错误响应)返回 X-Content-Type-Options: nosniff 与 Referrer-Policy: strict-origin-when-cross-origin。如果它前面的反向代理也发送这些响应头,请只在一处设置。容器不限制页面嵌入,仪表盘等可以通过 iframe 嵌入 Web 界面;如需禁止,请在反向代理上添加 X-Frame-Options 或 CSP frame-ancestors 指令。
流代理默认阻止私网目标。开启 stream_proxy_allow_private_targets 后,已认证用户可让服务请求内部地址;仅在明确的局域网摄像头或转流场景开启。
网页和桌面播放器的中转请求均使用该直播源的代理设置。 后端在请求前检查每个媒体目标和重定向;不使用代理时,直连还会检查实际连接所用的地址。 已保存的代理或系统代理,对经过它的所有流量(从直播检查、账号登录到下载和播放)而言都是 受信任的网络出口:它能看到平台流量,可位于私网,并负责远端 DNS 和路由。只使用你愿意托付 账号的代理,并在该代理上限制内部目标访问,因为后端无法验证代理所在网络返回的不同 DNS 结果。 代理登录信息仅保留在后端;网页播放列表链接使用浏览器会话,不嵌入后端访问令牌。
流代理和 URL 解析共享最长五秒的全局配置快照。应用写入和已提交的配置导入会立即 使缓存失效。直接修改数据库可能需要五秒才会生效;刷新失败时不会重用过期快照。 管理接口读取仍直接获取最新数据。
凭据刷新存储
Cookie、令牌和登录信息只保存在账号凭据配置中。刷新会把新的 Cookie 及平台返回的 令牌一起保存到该凭据配置;写入失败时保留原凭据,平台未返回的令牌保持原值。 账号被编辑、停用、替换或删除之后才完成的刷新或登录会被丢弃,不会覆盖它。 包含账号字段的配置写入会被拒绝,而不会被保存。
密钥与文件
- 限制
.env、DATA_DIR、CONFIG_DIR、LOG_DIR、配置导出和备份媒体的访问。 - systemd 主机上,后端密钥位于
/etc/rust-srec/rust-srec.env,权限0640、属主root:rust-srec,其中包含JWT_SECRET、VAPID 密钥和各类工具路径覆盖项。文件中的每一项都会覆盖 unit 自身的Environment=设置,因此修改它等于修改服务配置,而不只是修改密钥。 - unit 中的
UMask=0027让录制文件写为-rw-r-----,对rust-srec用户组保持可读;把某个账号加入该组,就等于授予它读取全部录制文件和状态目录的权限。应有意识地授予该权限,而不是直接调低UMask=。 - 已保存代理的用户名和密码以明文保存在数据库和配置导出中。API 和 Web 界面会显示代理的用户名,但从不返回密码。
- 账号凭据配置(Cookie、令牌和登录信息)及房间密码会出现在配置导出中;通知渠道可能包含 SMTP 密码、机器人令牌、Webhook 密钥和自定义请求头。
- 百度网盘登录会话保存在 BaiduPCS-Go 的配置目录中(
BAIDUPCS_GO_CONFIG_DIR,Docker 中为/app/config/BaiduPCS-Go),请像保护 Cookie 一样保护并备份该目录。勾选“记住凭据以便自动重新登录”后,登录凭据还会以明文保存在应用数据库(tool_credentials表)中,与平台 Cookie 相同;退出登录时会删除。手动与自动登录均通过标准输入传递凭据,不放入子进程参数或环境变量。私有临时配置目录会阻止 CLI 保存命令历史,只把成功登录的账号导入原配置,保留其他账号、设置和历史记录。临时目录仅属主可访问(Unix 权限 0700,Windows 使用受保护的属主专用 ACL),确认子进程清理后删除;若无法确认清理,则保留私有目录并锁定账号操作,直到后端重启。具有特权的主机访问以及所配置的可执行程序仍属于信任边界。 - 分享日志或截图前,隐藏令牌、私有 URL、用户名、Cookie 和文件系统路径。
- 容器不要挂载不必要的宿主机目录或设备;只有所选管道需要时才添加 GPU 设备。
- 把
execute、上传、移动或删除源文件等管道步骤视为具有文件系统和网络权限的代码来审查。
仓库提供的 systemd unit 已经以非特权方式运行服务,并启用 ProtectSystem=strict、NoNewPrivileges=yes、空的 CapabilityBoundingSet= 和 SystemCallFilter=@system-service,因此除状态目录、日志目录和 ReadWritePaths= 之外,进程看到的系统都是只读的。请保留这些设置,需要写权限时逐个路径添加。
PrivateDevices=yes 会隐藏 /dev/dri 和 /dev/nvidia*:系统健康页不会出现 GPU 区块,ffmpeg 也会回退到软件编码。启用硬件转码需要在 drop-in 中设置 PrivateDevices=no,并为渲染节点添加 DeviceAllow=;这属于有意放宽沙箱,应按此对待。
完全权限 API 凭据可以选择工具可执行程序和配置路径。这相当于允许使用后端的操作系统身份运行程序,并不是受限的操作员角色。请只配置可信的 BaiduPCS-Go 程序。
漏洞处理
不要在公开 Issue 报告疑似漏洞。请使用 GitHub 私密漏洞报告,说明受影响版本、影响和已移除密钥的最小复现。安全修复进入 main 并随后续版本发布。