一、手册定位与 YAML 结构总览
Clash 系客户端(以及作为运行核心的 mihomo 内核)读取一个 YAML 格式的配置文件来决定所有行为。订阅链接的本质就是一个托管在服务端、随时可拉取更新的配置文件;客户端界面上的每一个开关,最终也都会落到这个文件的某个字段上。读懂它的结构,等于同时读懂了订阅内容、客户端设置项与内核日志三者之间的对应关系,排查问题时不必再逐个界面乱点。
本页与使用指南的分工是「轻上手、重查阅」:指南负责带着完成一次从导入订阅到验证联通的完整流程,本页负责在流程之外系统回答「这个字段是什么意思、还能怎么写」。两页互为补充,遇到指南里一笔带过的字段,按上方目录跳到对应章节即可。
顶层结构:五大区块
一份完整的配置文件从上到下大致分成五个区块。它们在文件中的书写顺序不影响解析结果,但绝大多数订阅都按下表顺序组织,阅读别人的配置时可以据此快速定位:
| 区块 | 作用 | 典型字段 |
|---|---|---|
| 通用字段 | 端口、运行模式、日志、局域网共享等全局行为 | mixed-port、mode、log-level |
dns | 内核接管域名解析的方式,含 Fake-IP | enhanced-mode、nameserver |
proxies | 逐条列出可用的代理节点及其协议参数 | type、server、port |
proxy-groups | 把节点组织成可选择、可测速的策略组 | type: select、url-test |
rules | 按顺序匹配流量,决定走哪个策略组 | DOMAIN-SUFFIX、GEOIP、MATCH |
配置文件放在哪、改哪一份
动手之前先弄清自己要改的是哪一份文件,这一步搞错会出现「改了半天毫无变化」的典型困惑。客户端通常把配置分成三层保存:一是从订阅链接拉取下来的原始文件,存放在客户端的配置目录里(桌面端多为用户目录下的应用数据文件夹,移动端在应用私有目录),它会被下一次订阅更新整体覆盖,原则上不要直接编辑;二是你自己新建的本地配置文件,完全由自己维护,适合自建节点或纯手写规则的场景;三是覆写/合并文件,只写差异部分,由客户端在加载时叠加到订阅内容之上,这才是长期维护订阅时的正确改法,详见第八章。判断当前生效的是哪一份,最直接的办法是在客户端的配置列表里看哪一项处于启用状态,再结合日志开头打印的配置路径确认。改完后必须触发一次「重载配置」,内核不会自动监听文件变化;部分客户端在切换配置时会保留旧的运行状态,遇到反复无常的表现,完全退出客户端再启动是最干净的验证方式。
YAML 语法三条铁律
YAML 对格式极其敏感,配置报错里九成是语法问题而不是字段问题。写配置前先记住三条:第一,缩进只能用空格,一个 Tab 字符就足以让整个文件解析失败,且报错行号往往指向文件更靠后的位置,不易察觉;第二,冒号后面必须有一个空格,port:7890 是非法写法,port: 7890 才对;第三,节点名称里含有表情符号、井号、引号或以特殊字符开头时,整个字符串要用双引号包起来,否则可能被解析成注释或语法结构。行首的 # 表示注释,调试时想临时停用某条规则,在行首加井号比直接删除更稳妥。术语拿不准时可查术语表的「订阅与配置」分类。
二、通用字段:端口、模式与运行参数
通用字段位于文件顶层,不属于任何缩进块,决定内核以什么姿态运行。下面是一段可直接作为起点的最小可用配置:
mixed-port: 7890
allow-lan: false
mode: rule
log-level: info
ipv6: false
external-controller: 127.0.0.1:9090
端口族:mixed-port 与它的兄弟们
mixed-port 是目前最常用的端口字段,在同一个端口上同时接受 HTTP 与 SOCKS5 两种协议的入站连接,系统代理指向它即可,无需再分开配置。老配置里常见的 port(纯 HTTP)与 socks-port(纯 SOCKS5)如今仍然有效,适合需要把两种协议分开给不同软件使用的场景。此外还有 redir-port 与 tproxy-port,它们面向 Linux 上的透明代理与软路由部署,普通桌面用户不需要配置。端口取值避开 1024 以下的系统保留段;如果启动时日志报 bind: address already in use,说明端口被其他程序(常见是另一个未退出的代理进程)占用,换一个端口号或结束占用进程即可。
mode:三种运行模式
| 取值 | 行为 | 适用场景 |
|---|---|---|
rule | 每个连接按 rules 区块逐条匹配后分流 | 日常默认,兼顾速度与准确 |
global | 忽略规则,所有流量走全局选定的策略 | 临时测试某个节点是否可用 |
direct | 所有流量直连,不经过任何节点 | 排查「到底是不是代理的问题」 |
客户端界面上的「规则/全局/直连」切换按钮改的就是这个字段。排障时先切 direct 确认本地网络正常,再切 global 确认节点可用,最后回到 rule 检查规则,是最快的三段定位法。
其余高频字段
allow-lan 设为 true 时,局域网内其他设备可以把网关代理指向本机端口,让电视盒子、游戏机共享代理;开启后建议配合 bind-address 限定监听网卡,避免在公共网络上把端口暴露给陌生设备。log-level 从详细到安静依次为 debug、info、warning、error、silent,排查规则命中情况时临时调到 debug,能在日志里看到每条连接命中了哪条规则。external-controller 开放一个 RESTful 接口供面板类工具读取状态与切换节点,若填写了 secret 字段则访问接口需带同样的密钥,示例一律用假值如 secret: "xxxx"。ipv6 默认关闭,在 IPv6 环境不完整的网络里贸然开启反而会引入解析超时。
三、DNS 段:解析模式与 Fake-IP
很多「规则明明写对了却不生效」「部分网站时通时断」的问题根源都在 DNS。内核之所以要自带一套 DNS 配置,是因为分流规则里大量存在基于域名和地理位置的判断:如果解析这一步被污染或者绕开了内核,后面的匹配就是在错误的答案上做决定。下面是一段常见的 DNS 区块:
dns:
enable: true
listen: 0.0.0.0:1053
enhanced-mode: fake-ip
fake-ip-range: 198.18.0.1/16
fake-ip-filter:
- "*.lan"
- "+.local"
nameserver:
- https://223.5.5.5/dns-query
fallback:
- https://1.1.1.1/dns-query
fallback-filter:
geoip: true
geoip-code: CN
enhanced-mode:fake-ip 与 redir-host
fake-ip 模式下,内核收到域名查询时不做真实解析,直接从 fake-ip-range 指定的保留网段(默认 198.18.0.1/16)里返回一个「假地址」,并记住域名与假地址的映射;等应用真的向这个假地址发起连接时,内核凭映射还原出域名再做规则匹配。好处是省掉一次解析等待、域名规则命中率极高;代价是某些依赖真实 IP 的场景(局域网设备发现、部分游戏联机、需要回传 IP 的验证服务)会拿到假地址而出错——这正是 fake-ip-filter 存在的意义:列在其中的域名跳过假地址逻辑,返回真实解析结果。redir-host 模式则始终返回真实 IP,兼容性更好但解析链路更长。两种模式的完整原理对比,可读博客文章《Fake-IP 模式是什么》。
nameserver 与 fallback 的分工
nameserver 是默认上游,通常填地理位置较近、响应快的服务器;fallback 是备用上游,当 fallback-filter 判断默认上游返回的结果可疑(例如 geoip: true 时,境外域名却解析出了本地地区的 IP)时改用备用结果。上游地址支持四种写法:纯 IP(UDP 53)、tls://(DoT)、https://(DoH)与 quic://(DoQ),加密写法可以避免解析请求在链路上被篡改。注意 nameserver 里至少要有一个能直连解析的地址,否则会出现「先有鸡还是先有蛋」:解析代理服务器域名本身也需要 DNS。
enhanced-mode 或修改 fake-ip-range 之后,系统与浏览器里可能仍缓存着旧的解析结果,表现为改完配置反而集体断网。重启客户端并刷新系统 DNS 缓存(Windows 执行 ipconfig /flushdns)后再验证。四、代理节点字段:proxies 逐项说明
proxies 是一个列表,每个元素描述一条节点。日常使用订阅时这一段由订阅服务端生成,一般不需要手写;但读懂它有两个实际价值:一是节点连不上时能从字段层面判断问题(端口写错、传输层参数缺失、加密方式不匹配),二是需要临时加一条自建节点时不必依赖任何转换工具。所有协议共享四个基础字段:name(组内引用的唯一标识,重名会导致解析失败)、type(协议类型)、server 与 port。udp: true 声明该节点转发 UDP 流量,语音通话、游戏类应用依赖它。
三种常见协议的字段形态
proxies:
- name: "示例-SS"
type: ss
server: node1.example.com
port: 8388
cipher: aes-128-gcm
password: "your-password"
udp: true
- name: "示例-VMess"
type: vmess
server: node2.example.com
port: 443
uuid: 00000000-0000-0000-0000-000000000000
alterId: 0
cipher: auto
tls: true
network: ws
ws-opts:
path: /ws
headers:
Host: node2.example.com
- name: "示例-Trojan"
type: trojan
server: node3.example.com
port: 443
password: "your-password"
sni: node3.example.com
Shadowsocks(ss)的核心是 cipher 与 password 必须与服务端完全一致,加密方式差一个字母连接就会静默失败。VMess 用 uuid 做身份凭证,alterId 在现行协议下固定填 0;network 决定传输层形态,取 ws 时需要配套 ws-opts 写明路径与 Host 头,取 grpc 时对应 grpc-opts。Trojan 天然运行在 TLS 上,sni 与证书域名不一致时握手会被拒绝,自签证书的测试环境可加 skip-cert-verify: true,生产使用不建议。
mihomo 扩展协议
作为当前主流的运行内核,mihomo 在上述经典协议之外还支持 VLESS、Hysteria2、TUIC 等更新的协议类型,各自有独立的字段集(如 Hysteria2 的 up/down 带宽声明)。是否可用取决于客户端内置的内核版本,这也是客户端对比页建议优先选择基于 mihomo 内核的客户端(如全平台的 Clash Plus、桌面端的 Clash Verge Rev)的原因之一:老内核的客户端遇到新协议节点会直接报「unsupport proxy type」并拒绝加载整份配置。
五、策略组字段:proxy-groups 四种类型
如果说 proxies 是原材料,proxy-groups 就是把原材料组织成「可决策单元」的一层:规则不直接指向节点,而是指向策略组,由组内逻辑(手动选择或自动测速)决定最终出口。这一层设计让「换节点」不需要动任何规则。四种组类型行为如下:
| type | 决策方式 | 关键字段 |
|---|---|---|
select | 由用户在客户端界面手动选定 | proxies |
url-test | 定期测延迟,自动选最快的成员 | url、interval、tolerance |
fallback | 按列表顺序取第一个可用成员 | url、interval |
load-balance | 把连接分散到多个成员上 | strategy |
proxy-groups:
- name: "节点选择"
type: select
proxies:
- 自动测速
- 示例-SS
- 示例-VMess
- DIRECT
- name: "自动测速"
type: url-test
url: http://cp.example.com/generate_204
interval: 300
tolerance: 50
lazy: true
proxies:
- 示例-SS
- 示例-VMess
字段细节与嵌套技巧
自动类组的 url 应指向一个返回 204 状态码的轻量地址(各客户端都内置了默认测速地址,不填则用默认值),interval 以秒为单位控制复测周期,300 是常见取值;tolerance 是切换阈值——新旧节点延迟差小于该毫秒数时不切换,避免两条延迟接近的线路来回横跳导致连接频繁重置。lazy: true 让组在未被使用时跳过测速,节点数多时能明显减少后台流量。组的成员既可以是节点名,也可以是另一个组名或内置策略 DIRECT(直连)、REJECT(拒绝连接),因此可以搭出「手动组套自动组」的层级:平时选「自动测速」放手不管,特殊时期手动钉住某条节点。唯一要避免的是两个组互相引用形成环,内核会在启动时报错拒绝加载。组名同样要求全局唯一,且会被规则原文引用,改组名时记得同步改动所有引用它的规则行。
六、规则语法:rules 匹配与优先级
rules 是分流的裁决层。每当有新连接产生,内核从列表第一条开始逐条比对,命中即停止,后面的规则不再参与;因此规则的书写顺序就是优先级本身,同样一批规则换个顺序,分流结果可能完全不同。每条规则的通用格式是 类型,匹配值,策略,策略可以是组名、节点名或内置的 DIRECT/REJECT:
rules:
- DOMAIN,dl.example.com,节点选择
- DOMAIN-SUFFIX,example.org,节点选择
- DOMAIN-KEYWORD,tracker,REJECT
- IP-CIDR,192.168.0.0/16,DIRECT,no-resolve
- IP-CIDR6,fd00::/8,DIRECT,no-resolve
- GEOSITE,cn,DIRECT
- GEOIP,CN,DIRECT
- RULE-SET,ads,REJECT
- MATCH,节点选择
规则类型对照
| 类型 | 匹配对象 | 说明 |
|---|---|---|
DOMAIN | 域名完全一致 | 最精确,只命中一个域名 |
DOMAIN-SUFFIX | 域名后缀 | 命中该域名及全部子域,最常用 |
DOMAIN-KEYWORD | 域名含关键词 | 范围最宽,易误伤,慎用 |
IP-CIDR / IP-CIDR6 | 目标 IP 网段 | 配 no-resolve 使用见下文 |
GEOIP | 目标 IP 的地理归属 | 依赖 GeoIP 数据库 |
GEOSITE | 域名分类库 | 依赖 GeoSite 数据库 |
PROCESS-NAME | 发起连接的进程名 | 桌面端按软件分流 |
RULE-SET | 外部规则集 | 引用 rule-providers 定义的集合 |
MATCH | 无条件命中 | 兜底规则,必须放最后一条 |
no-resolve 与排序原则
IP 类规则默认会触发一次域名解析来拿到目标 IP 再比对——如果这条规则本意只想匹配「本来就以 IP 直连」的流量(例如局域网网段),这次解析纯属浪费,还可能拖慢每个连接。在规则末尾追加 no-resolve 参数即可声明「目标是域名时直接跳过本条」。排序上遵循两个原则:精确的、代价低的放前面(DOMAIN 系),需要解析或查库的放后面(GEOIP);拒绝类规则尽量靠前,让广告请求在进入更重的匹配之前就被拦下。GEOSITE 与 GEOIP 的判断准确度取决于本地数据库的新旧,数据库长期不更新会造成分流失准,更新方式详见《GeoIP 与 GeoSite 数据库过期怎么办》。
一份规则表的推荐骨架
不同人的规则表内容差别很大,但骨架大体一致,按下面的顺序组织可以避免多数排序陷阱:最前面放局域网与本机网段的直连规则,并带上 no-resolve,保证内网访问不受任何后续规则干扰;其次放广告与追踪类的拒绝规则,越早拦下越省资源;第三段放你自己的例外规则,例如公司内网域名强制直连、某个下载工具强制走特定节点;第四段放按分类库书写的大批量规则,如 GEOSITE 系;第五段放 GEOIP 一类需要查库的 IP 规则;最后一条固定是 MATCH 兜底。需要提醒的是,兜底策略指向哪个组决定了「未被任何规则命中的流量」的默认走向:指向代理组意味着默认走代理、白名单式思路,指向 DIRECT 则是默认直连、黑名单式思路,两种取向没有优劣,但要与前面的规则内容保持一致,否则会出现大量意料之外的分流结果。
log-level 临时调到 debug,或在客户端的连接面板查看每条活动连接标注的规则来源,比逐条猜测高效得多。七、订阅与规则集:proxy-providers 与 rule-providers
把几百条节点和上万条规则直接写进主配置文件,既臃肿又难更新。Provider 机制把它们抽成可独立拉取、独立缓存、按周期自动刷新的外部资源:主配置只负责「引用」,内容托管在远端。这也是现代订阅生态的标准形态——你的订阅链接,通常就是一个 proxy-providers 意义上的节点清单。
proxy-providers:节点来源托管
proxy-providers:
main:
type: http
url: "https://sub.example.com/subscribe?token=xxxx"
path: ./providers/main.yaml
interval: 3600
health-check:
enable: true
url: http://cp.example.com/generate_204
interval: 600
type: http 表示从远端拉取,配套 url 与本地缓存路径 path;type: file 则直接读本地文件,适合手工维护的自建节点清单。interval 控制自动重新拉取的秒数;health-check 让内核周期性对清单里的节点测活,供策略组筛选。策略组要使用 Provider 里的节点时,用 use 字段代替(或搭配)proxies 字段:
proxy-groups:
- name: "订阅节点"
type: url-test
use:
- main
url: http://cp.example.com/generate_204
interval: 300
rule-providers:规则集托管
rule-providers:
ads:
type: http
behavior: domain
format: yaml
url: "https://sub.example.com/rules/ads.yaml"
path: ./ruleset/ads.yaml
interval: 86400
规则集最容易踩的坑是 behavior 与文件内容不匹配。它有三个取值:domain(文件里全是域名)、ipcidr(全是网段)、classical(每行都是完整的「类型,值」规则)。远端文件明明是域名清单却声明成 classical,加载不会报错,但一条也匹配不上,排查时极具迷惑性。format 支持 yaml 与 text,mihomo 还支持体积更小、加载更快的二进制 mrs 格式。声明好的集合通过 RULE-SET,ads,REJECT 这样的规则行接入主规则表,更新规则集不再需要改主配置,这正是它对长期维护最大的价值。示例里的 token=xxxx 是占位假值,实际以订阅服务提供的完整链接为准。
八、覆写与合并:让订阅更新不冲掉本地修改
直接编辑订阅下发的配置文件有一个致命问题:下一次订阅自动更新时,远端内容会整体覆盖本地文件,你手工加的规则、改的 DNS 全部归零。覆写(Override)与合并(Merge)机制解决的就是这件事——把「你的修改」与「订阅的内容」分开存放,每次订阅更新后由客户端自动把修改重新叠加上去。改配置之前先确认自己用的客户端支持哪种机制:
| 客户端 | 机制 | 说明 |
|---|---|---|
| Clash Plus(首推) | 覆写配置 | 全平台一致的覆写入口,按订阅分别挂载 |
| Clash Verge Rev | Merge + Script | YAML 声明式合并,复杂逻辑可用脚本改写 |
| FlClash | 覆写面板 | 常用字段(端口/DNS/规则)图形化覆写 |
| Clash Meta for Android | 配置附加 | 移动端提供基础的字段覆盖能力 |
声明式合并的写法
以 Clash Verge Rev 的 Merge 为例,合并文件本身也是一段 YAML:顶层直接写出的字段(如 mixed-port)会整体替换订阅里的同名字段;带 prepend-/append- 前缀的字段则把内容插入到订阅对应列表的头部或尾部,常用于在订阅规则之前加自己的高优先级规则:
mixed-port: 7893
prepend-rules:
- DOMAIN-SUFFIX,corp.example.com,DIRECT
- PROCESS-NAME,steam.exe,节点选择
append-proxies:
- name: "自建-备用"
type: ss
server: node9.example.com
port: 8388
cipher: aes-128-gcm
password: "your-password"
「prepend 进规则表头部」这一点尤其重要:规则命中即停,只有排在订阅规则之前,你的私有规则才有机会先被匹配到。字典类字段(如 dns)的合并粒度是整块替换还是逐键合并,不同客户端实现略有差异,写完务必用一条已知流量验证效果。各客户端覆写入口的位置与操作差异,客户端对比页有横向整理;Windows 端从安装到服务模式的完整流程可参考《Windows 上用 Clash Verge Rev》。
九、常见报错与配置自检清单
配置加载失败时,内核日志给出的报错通常已经点名了问题类别,先读日志再改文件,能省下大量盲试时间。几类高频报错的对号入座:yaml: line N 开头的是语法错误,回到第 N 行附近检查缩进(重点排查混入的 Tab)与冒号后的空格;proxy not found 或 proxy group ... not found 表示策略组或规则引用了一个不存在的名字,多半是节点改名后引用没同步,或名字里的空格、表情符号不完全一致;unsupport proxy type 说明配置里出现了当前内核不认识的协议,要么升级客户端要么移除该节点;bind: address already in use 是端口被占,见第二章;规则集「加载成功但从不命中」,优先怀疑第七章讲的 behavior 声明与内容不符。
另有几类问题不体现在报错里,只表现为「行为不对」,更需要方法定位。比如全部网站都打不开但节点测速正常,通常是 DNS 段配置有误或系统 DNS 缓存未刷新,而不是节点问题;又比如只有个别应用不走代理,大概率是这些应用不读系统代理设置(命令行工具、部分游戏客户端),需要改用 TUN 模式接管;再比如速度忽快忽慢、连接频繁重置,可以先把自动测速组的 tolerance 提高一些,减少线路来回切换带来的中断。定位这类问题的通用思路是「缩小变量」:每次只改一处,改完立刻用同一个测试目标复验,并把每次改动记在备注里,避免连续叠加多处改动后无法判断哪一处起了作用。
动手改配置前后的七步自检
- 改前备份:复制一份当前能正常工作的配置文件,任何改动出问题都能一步回退,这是成本最低的保险。
- 过语法关:保存后立即在客户端里重载配置,加载成功再谈效果;加载失败先按日志行号修语法,不要带着语法错误继续叠加改动。
- 查名字一致性:全文搜索被引用的节点名与组名,确认
proxies、proxy-groups、rules三处写法逐字一致,包括引号内的空格。 - 验证规则顺序:确认
MATCH在最后一条、拒绝类规则足够靠前、私有规则排在订阅规则之前(用覆写时确认走的是 prepend)。 - 验证 DNS 行为:开启 Fake-IP 后测试局域网打印机、投屏等本地服务是否正常,不正常就把对应域名加入
fake-ip-filter。 - 三模式定位:遇到「连不上」先切
direct排除本地网络,再切global排除节点,最后回rule查规则,一次只变一个变量。 - 观察一个更新周期:确认订阅自动更新之后,覆写内容仍然生效、端口与 DNS 设置没有被冲回默认值。
如果按清单走完仍未定位,回到使用指南核对上手主线是否有遗漏步骤;初次安装阶段的通用检查项可参考《Clash 第一次安装要做的 7 项初始设置》。客户端本身版本过旧也会放大各种兼容性问题,到下载页更新到当前版本后再复测,是排障流程里性价比很高的一步。