先分清两件事:规则命中 ≠ 你肉眼以为的「站点」
Clash 对每一个出站连接做的是有序的决策链:从 rules 第一条扫到最后一条,命中即停止。日志里的 matched rule(有些 GUI 写成 rule、policy、matcher)对应的就是这一条停止点。如果你只看浏览器地址栏里的域名,却忽略跳转、CDN、WebSocket、DoH、二次握手背后的主机名,就很容易误判「规则写对了却不生效」。
另一类高频误会,是把 matched rule 当成「最终落地的节点」。多数情况下,规则只是把流量交给某个策略组名;策略组内部还可能嵌套别的策略组,或由 url-test、fallback 自动改选。因此日志若显示命中了某一策略组名,仍需继续往下看实际 outbound 是哪个叶子节点。
YAML 结构与字段详解可参考站内《Clash YAML 规则分流完全指南》;本篇假设你已能导入订阅并有一份可运行的配置。
第一步:锁定「那一条」连接,而不是一整屏滚动日志
打开客户端的连接日志(或内核日志视图),在你复现问题的同时触发访问——例如点开目标网页、重启 App、或在终端发起一条 curl。立刻暂停滚动,用时间戳、进程名(若 GUI 展示)、目标地址与协议四要素对齐到你关心的连接。
若同一页面在短时间内建立了十几条 TLS 连接,其中一部分可能指向完全不同的 CDN 主机名;你只盯着第一条而忽略后续条目,就会觉得「规则来回乱跳」。做法是:找到失败现象出现时相邻的几条记录,逐条记下它们的 matched rule,再看是否有同一后缀家族未被覆盖。
使用 TUN 或系统透明代理时,某些连接会以 IP 展示;这时域名规则未必参与匹配,而与 IP-CIDR、GEOIP、RULE-SET 的行为有关。若你开了嗅探(sniff),日志里的主机名可能与原始目标不一致——这不是 bug,而是你排查时必须接受的「内核视角」。
第二步:暂时抬高日志级别,保证能看见 rule 命中
不同图形客户端把日志级别藏在「配置 / 内核设置 / 开发者选项」等不同入口;核心是:在排障窗口内让内核打出每条连接的匹配结果。若沿用静默级别,你只能看到笼统错误码,无法讨论 FINAL 或某条 DOMAIN-SUFFIX。
建议在调试完成后把级别降回默认,避免海量磁盘写入与隐私顾虑。团队共用机器时,短时间内完整的 debug 日志可能包含域名与应用行为摘要,注意分享前脱敏。
少数场景下,你还要对照DNS 日志:Fake-IP、Redir-Host 与直连 DNS 的表现会影响「内核手上拿到的第一个域名/IP」。这与分流交织在一起时,看起来像规则失灵,实际是解析路径分叉,可与Fake-IP 与 DNS 排查篇交叉阅读。
第三步:读出 matched rule,并对照 YAML 里的真实条目
当你在某个连接条目上看到 matched rule(或等价字段),请立即打开 YAML,用全文搜索确认是否存在同名引用。典型几种映射关系:
- 命中结果是
DIRECT、REJECT或某个代理策略组名——这与你在 rules 段末尾写的第三个字段一致。 - 命中结果显示来自某条
RULE-SET——记住 rule-set 只是一层封装,展开后的条目顺序插入在主规则的某个位置;若你以为写在 GEOIP 之上,却被 RULE-SET 内更宽泛的条目抢先,应以展开后的全局顺序为准。 - 命中结果显示进程规则(如 PROCESS-NAME)——适用于特定操作系统与权限模型,换客户端或关闭 TUN 后行为可能变化。
若日志给出的 matched rule 文本无法在 YAML 中找到对应项,优先怀疑生效配置不是你编辑的那份(远端配置覆写、订阅内置 rules、Merge 顺序)。复制客户端「当前运行配置」导出核对,是最快的求真办法。
第四步:判断命中的是「具体策略」还是 FINAL/MATCH 兜底
列表末尾通常有一条兜底:MATCH,某个策略组,或在某些教程里被称作 FINAL。它的语义非常简单:前面所有规则都没命中,才把连接交给默认策略组。因而当你看到日志反复命中兜底,请不要急着再加一层关键词规则;应先追问——「为什么前面的规则没有拦住它?」
常见原因包括:
- 维度错位:写了 DOMAIN-SUFFIX,实际连接却以 IP 进入匹配路径;需要 sniff、DNS 或补充 IP 规则。
- 顺序错位:一条过于宽泛的规则(大面积 DOMAIN-KEYWORD、整条 GEOIP)排在自定义细则之前。
- 主机名错位:站点静态资源挂在另一个后缀下,没有被你的清单覆盖。
校园网或 Captive Portal 场景里,认证域名若提前走代理会导致「全都上不了网」,本质是规则顺序问题而非节点质量问题;可参考校园网分流顺序篇里的置顶直连思路,再把同样的顺序思维搬到你的环境里。
第五步:沿 proxy-groups 拆解「第二次决策」
当 matched rule 指向某个策略组名时,真正的节点还可能经历第二层、第三层决策。举例:rules 命中「国外流量」组,而「国外流量」是一个 url-test,它会间隔探测并从候选节点里选一个延迟最低的;你在 GUI 里手动切到「节点 A」,但若 url-test 定时刷新后又切回「节点 B」,表象仍是「走错节点」。
排查建议是:
- 若策略组类型为
select,核对当前选中项是否为预期叶子节点。 - 若为
url-test/fallback,核对候选列表顺序、探测 URL、interval,以及失败判定阈值。 - 若存在嵌套——「国外流量」下面挂的不是节点而是另一个策略组——需要递归展开直到叶子。
这也是为什么「策略组顺序」四个字经常被低估:它不仅包括 rules 表里谁先匹配,也包括 proxy-groups 声明里谁在 proxies 列表前排、fallback 失败后顺延到谁。
第六步:把 DNS、嗅探与规则命中写成一张对照表
完成前五步后,把观察落到纸上(或备忘录):每一列分别是连接目标(日志)、matched rule、对应 YAML 行、策略组展开路径、最终 outbound。你会发现大量「走错节点」投诉,最终在表里体现为:
- matched rule 本来就是对的,错在 nested url-test;或
- matched rule 指向兜底,说明细则根本没轮到;或
- 日志目标主机与脑海中域名不一致,DNS/sniff 需要单独收敛。
这张表也方便你与社群或同事沟通:不问「我感觉规则有问题」,而是给出一行日志 + 一行 YAML,讨论成本会明显下降。
| 日志症状 | 更可能的解释 | 下一步动作 |
|---|---|---|
| 始终命中 MATCH/FINAL | 前置规则维度不对或顺序被抢占 | 按第三步从上到下核对序号;检查 RULE-SET 插入点 |
| matched rule 正确但节点乱跳 | url-test/fallback 或订阅刷新改写延迟 | 暂时改成 select 固定叶子验证路径 |
| 同站有时直连有时代理 | 多 CDN 主机名或 HTTP/3 切换 | 抓取多条连接日志比对 SNI 与解析 |
| 规则改动似乎永不生效 | 配置文件未重载或存在覆写层 | 导出运行中配置 diff;重启内核 |
常见问题(正文摘要)
matched rule 对了,节点仍不对,最常见是哪一类原因?
最常见是策略组二次选择:日志停在父组名字上,而父组内部仍在自动择优。先用 select 固定一个低速稳定的叶子验证;确认无误后再恢复 url-test。
我是不是应该把 FINAL 写成直连更安全?
没有普世答案。兜底走向取决于你的风险偏好:全局直连可能泄漏长尾海外请求;全局代理可能拖慢国内站点。关键是有意识地选择,并用日志验收长尾域名是否与你设想一致。
开源内核与 GUI 日志术语不一致怎么办?
以内核导出日志为准。GUI 可能对字段做了本地化缩写;若术语含混,直接在内核日志检索同一连接的 destination 与 rule 字段。
写在最后:验证比堆砌规则更重要
Clash 的魅力在于透明:只要你愿意读日志,分流就不是玄学。把这六步固化成肌肉记忆——锁定连接、抬高日志级别、读懂 matched rule、识别 FINAL/MATCH、拆解嵌套策略组顺序、并最终把 DNS 与嗅探纳入同一张对照表——绝大多数「走错节点」都能在半小时内有定论。
相比盲目复制网上的超长规则列表,先把规则命中看清楚,再去扩充 RULE-SET,维护成本更低,也不容易在升级 Meta 内核后因语法迁移产生静默偏差。若你希望把客户端安装与订阅导入收敛到单一可信入口,可使用本站提供的下载页获取免费客户端并与团队共享订阅链接,减少每人一套散装配置带来的隐性错位。
系统学习 YAML 写法请回到《Clash YAML 规则分流完全指南》;更多专栏文章见技术专栏。