[错误报告]: 未设置消息类型(mtype)的通知会绕过通知发送范围,企业微信以 touser=@all 广播
Author: q10710Created Sep 18, 2026Updated Sep 18, 2026
Labelsbug
确认
- 我的版本是最新版本,我的版本号与 version 相同。
- 我已经 issue 中搜索过,确认我的问题没有被提出过。
- 我已经 Telegram频道 中搜索过,确认我的问题没有被提出过。
- 我已经修改标题,将标题中的 描述 替换为我遇到的问题。
当前程序版本
v3.0.4
运行环境
Docker
问题类型
主程序运行问题
问题描述
现象
- 通知发送范围(系统设置 → 通知)中,把「站点 / 媒体服务器 / 手动处理 / 插件 / 智能体 / 其它」都设为仅管理员后,企业微信应用可见范围内的非管理员用户仍然能收到这些通知。
- 受影响的通知几乎覆盖所有类型,用户侧观感是「通知发送范围设置没有生效」。
复现步骤
- 系统设置 → 通知:把场景「站点」的发送范围设为「仅管理员」。
- 触发一条**没有设置消息类型(
mtype=None)**的通知。主程序自带的工作流「发送消息」动作就是这种情况:app/workflow/actions/send_message.py构造Message(source=client, userid=params.userid, title="【工作流执行结果】", text=msg_text, link=...),没有传mtype;该动作userid留空时为None。 - 经由企业微信通知渠道(
WECHAT_MODE=app,企业微信应用消息)发送。 - 结果:该企业微信应用可见范围内的全员都收到消息,包含非管理员、以及未勾选任何场景的用户。
期望行为
- 未设置
mtype的通知,应走最保守的投递范围(至少等同「仅管理员」),而不是广播给应用可见范围内的所有人。 - 渠道侧也不应因为
mtype为空而完全跳过通知场景开关校验。
已定位(v3.0.4 源码,均已核对)
app/chain/_messaging.py::_notification_route_action():if message.userid or not message.mtype: return None——mtype为空时直接不读路由配置,action=None。app/chain/_messaging.py::_notification_route_steps():send_original = not action成立,且action为空时遍历不执行 → 最终yield _NotificationRouteDelivery(message=message, ...),即原样投递原消息(targets与userid仍为None)。app/modules/wechat/__init__.py::post_message():if not userid and targets is not None: userid = targets.get('wechat_userid')——targets为None时不会进入该分支,userid保持None。app/modules/wechat/wechat.py::__send_message():if not userid: userid = "@all"→ 请求体{"touser": "@all", "agentid": ...}→ 企业微信应用可见范围内全员。app/modules/__init__.py::check_message():场景开关判据是if not message.userid and message.mtype:——mtype为空时整段被跳过,渠道侧没有第二道闸。WECHAT_ADMINS仅用于「接收指令」的鉴权(modules/_base/notification.py的resolve_config_principal_ids),不限制外发,因此管理员白名单兜不住这个问题。
同类缺口(同一成因)
get_notification_switch()找不到匹配type时同样返回None→ 任何未登记在NotificationSwitchs中的消息类型也会走原样投递 → @all,默认方向不安全。- 用户类场景(资源下载 / 整理入库 / 订阅 =
user,admin)中,若消息没有责任人(username为空),_notification_route_steps()的user分支条件不成立 → 直接走else并break,不会继续投递给 admin,同样退化为 @all 广播。
影响面
- 任何调用
post_message(...)而没设置mtype的通知都会 @all 广播;主程序自带的工作流「发送消息」动作(【工作流执行结果】通知)就属于此类,第三方插件也存在同类调用。 - 实际生效的边界只剩下企业微信「应用可见范围」,因此用户会误判为「通知发送范围配置失效」。
验证方式
- 用主程序真实路由函数
_notification_route_steps()与现网NotificationSwitchs取值做离线模拟(不发送真实消息):带mtype的站点 / 插件类通知只投递给管理员;而mtype=None的通知(工作流执行结果、无责任人的订阅类通知)最终touser=None→ 由渠道兜底为@all。 - 本 Issue 未附加私有日志:问题在代码层面即可复现,为避免带入无关的会话内容,日志区留空。
建议修复方向(供参考)
_notification_route_action()对无mtype的通知返回保守范围(例如admin),或在_notification_route_steps()中当action为空时按admin处理;check_message()在mtype为空时不视为通过场景开关校验;wechat.__send_message()的userid兜底改为管理员,或让广播必须由调用方显式声明。
发生问题时系统日志和配置文件
### Doctor 摘要
状态:healthy
运行环境:Docker
汇总:total=14 error=0 warn=1 advisory=1 fixed=0
关键发现:
- [warn/advisory] 最近日志存在插件异常;来源:autosignin.log;命中:5 条,去重后 2 条;建议:可使用安全模式启动后检查插件配置。
### 日志筛选依据
策略:time_window_and_keyword_block_match
时间窗口:最近 60 分钟
窗口起点:2026-09-18T20:03:51
关键词:未提供具体关键词
单文件最多保留:80 行
提示:未提供具体关键词,已跳过日志正文收集以避免误带无关日志。
命中文件:无本 Issue 由 MoviePilot Agent 协助用户提交。
Source: jxxghp/MoviePilot