一、引言,新一代通用代理核心 Sing-box 为何能迅速崛起

2022 年 9 月,GitHub 用户 SagerNet 发布了 Sing-box 的首个公开版本。彼时 Xray-core 与 Clash.Meta 已经占据了代理核心生态的大半份额,V2Ray 的存量部署更是数以百万计。在这样一个看似格局已定的市场里,一个新核心要在三年内获得广泛采用,必须拿出结构性的技术优势。到了 2026 年,Sing-box 已经稳定迭代至 1.12.x 分支,成为 iOS、Android、macOS、Windows、Linux 以及 OpenWrt 平台上被集成度最高的通用代理核心之一。它的崛起路径值得从协议栈、工程架构、生态整合三个层面拆开来看。

协议覆盖面的横向扩张

Sing-box 在入站与出站协议的支持列表上采取了激进的覆盖策略。入站侧支持 SOCKS、HTTP、Shadowsocks、VMess、VLESS、Trojan、Hysteria2、TUIC、ShadowTLS、WireGuard、Tun 等;出站侧在此基础上还加入了 Tor、SSH、Direct、Block、DNS 等特殊类型。这种广度的直接收益是,用户可以在单一配置文件中同时承载多种协议,不需要为每一种协议维护独立的客户端。

以 VLESS 为例,Sing-box 对 VLESS 的实现严格遵循 XTLS 社区规范,支持 Vision 流控与 XTLS-Reality。Reality 的核心机制在于服务端借用真实站点的 TLS 证书链完成握手,客户端在 ClientHello 中携带特定扩展字段,服务端通过私钥解密后判断是否为合法客户端。整个握手过程在网络上看起来与访问一个正常的 HTTPS 站点无异。Sing-box 在 1.9.0 版本中完成了对 Reality 的完整支持,并在后续版本中加入了 uTLS 指纹伪装,可模拟 Chrome、Firefox、Safari、Edge、360 等浏览器的 ClientHello 指纹。

Hysteria2 的支持同样值得关注。Hysteria2 基于 QUIC 协议,使用 UDP 作为传输层,在丢包率较高的跨国链路上表现优于 TCP 类协议。Sing-box 对 Hysteria2 的实现支持 Salamander 混淆、带宽协商、端口跳跃等特性。端口跳跃允许客户端在配置的端口范围内周期性切换目标端口,服务端监听整段端口范围,这一机制对部分运营商的 UDP QoS 策略有较好的规避效果。

架构层面的统一抽象

Sing-box 的配置模型基于一套统一的抽象层。无论底层是 TCP、UDP、QUIC 还是 Unix Domain Socket,在 Sing-box 内部都被抽象为 Listener 与 Dialer 接口。入站配置中的 listen 字段与出站配置中的 server 字段共享同一套地址解析逻辑,DNS 解析、路由匹配、出站选择在数据包进入核心后按照固定的流水线顺序执行。

这个流水线的顺序大致如下。数据包首先经过入站处理,完成协议解码与用户认证。随后进入路由模块,路由模块根据 route.rules 中的规则逐条匹配,匹配条件包括域名、IP CIDR、端口、进程名、GeoIP、GeoSite、Rule-Set 等。匹配成功后,数据包被分发到对应的出站。出站模块根据协议类型完成封装,再经由 Dialer 建立连接。整个过程中,DNS 模块可以在任意阶段介入,支持 DNS 分流、DNS over TLS、DNS over HTTPS、DNS over QUIC 等上游协议。

这种统一抽象带来的工程收益体现在配置的可组合性上。一个典型的 Sing-box 配置文件中,inboundsoutboundsroutednsexperimental 五个顶层字段各自独立,通过标签引用相互关联。用户可以在不修改出站配置的前提下,仅调整路由规则就实现流量的重新分配。

{
"inbounds": [
{
"type": "tun",
"tag": "tun-in",
"interface_name": "singbox-tun",
"address": ["172.19.0.1/30", "fdfe:dcba:9876::1/126"],
"mtu": 9000,
"auto_route": true,
"strict_route": true,
"stack": "mixed"
}
],
"outbounds": [
{
"type": "vless",
"tag": "proxy",
"server": "203.0.113.10",
"server_port": 443,
"uuid": "b831381d-6324-4d53-ad4f-8cda48b30811",
"flow": "xtls-rprx-vision",
"tls": {
"enabled": true,
"server_name": "www.microsoft.com",
"utls": { "enabled": true, "fingerprint": "chrome" },
"reality": {
"enabled": true,
"public_key": "jNXHt1yRo0vDuchQlIP6Z0ZvjT3KtzVI-T4E7RoLJS0",
"short_id": "0123456789abcdef"
}
}
}
]
}

上面这段配置展示了 Sing-box 在 TUN 模式下的典型结构。TUN 入站创建一块虚拟网卡,auto_route 为 true 时核心会自动配置系统路由表,将默认路由指向该网卡。stack 字段可选 systemgvisormixed,其中 mixed 在 Linux 上使用系统栈处理 TCP、gVisor 处理 UDP,兼顾性能与兼容性。MTU 设置为 9000 是为了配合底层链路的巨帧支持,减少分片开销。

跨平台部署的一致性

Sing-box 使用 Go 语言编写,编译产物为单一静态二进制文件,不依赖系统动态库。这一特性使得同一份配置文件可以在不同平台上直接复用。官方提供的构建矩阵覆盖了 amd64、arm64、armv7、mips、mipsle、riscv64 等架构,Linux 发行版、OpenWrt 路由器、树莓派、NAS 设备均可直接运行。

移动端的集成同样成熟。Android 平台有官方 SFA 客户端,iOS 与 macOS 平台有 SFI 与 SFM 客户端,均基于 Sing-box 核心构建。桌面端则有第三方图形客户端基于 Sing-box 核心开发,支持订阅导入、规则集管理、流量统计等功能。对于企业出海运维场景,Sing-box 可以作为 sidecar 容器与业务容器部署在同一 Pod 中,通过 localhost 通信,避免额外的网络跳转。

生态整合与 Rule-Set 机制

Sing-box 在 1.8.0 版本中引入了 Rule-Set 机制,这是其路由系统的一次重要升级。Rule-Set 允许用户将规则以远程文件的形式引用,核心在启动时或按需下载并缓存这些规则文件。规则文件支持 source 格式与 binary 格式,后者是 Sing-box 自有的二进制编码格式,体积更小、解析更快。

Rule-Set 的引入解决了传统配置中规则内联导致的文件臃肿问题。一个包含数万条域名规则的配置文件,使用内联方式可能达到数 MB,而使用 Rule-Set 引用后,主配置文件可以保持在几十 KB 的量级。规则更新也不需要修改主配置,只需替换远程规则文件即可。

对于需要精细分流的企业场景,Rule-Set 可以与 GeoIP、GeoSite 数据库配合使用。Sing-box 支持从本地或远程加载 GeoIP 与 GeoSite 数据,路由规则中可以直接引用 geoip:cngeosite:google 等标签。这种分层设计让规则的维护与更新变得更加可控。

性能与资源占用

在同等硬件条件下,Sing-box 的吞吐量与 Xray-core 处于同一量级,部分场景下由于 Go 运行时的调度优化,延迟表现略优。内存占用方面,Sing-box 在空闲状态下的常驻内存约为 30 MB 至 50 MB,处理大量并发连接时会有所上升,但整体控制在可接受范围内。

对于资源受限的嵌入式设备,Sing-box 提供了编译时裁剪选项,可以移除不需要的协议支持以减小二进制体积。官方发布的精简版本二进制大小约为 8 MB 至 12 MB,适合在 OpenWrt 等存储空间有限的环境中部署。

社区与文档

Sing-box 的官方文档结构清晰,配置字段均有详细说明与示例。社区维护的配置模板、规则集、图形客户端覆盖了主流使用场景。对于初次接触的用户,可以参考 配置教程保姆级指南 中的入门章节,从基础配置开始逐步熟悉核心概念。对于需要选择服务端的用户,2026 优质稳定高速机场推荐总榜机场评测中心深度对比大全 提供了基于实际测试的参考数据。了解不同协议的技术细节,可以查阅 专线百科 中的协议说明。在选择服务商时,科学上网防跑路避坑指南 列出了常见的风险信号与判断方法。

Sing-box 的崛起并非单一因素驱动。协议覆盖的广度、架构抽象的统一性、跨平台部署的一致性、Rule-Set 机制的引入,以及活跃的社区维护,共同构成了它在 2026 年成为通用代理核心首选的技术基础。对于网络工程师与企业运维人员而言,掌握 Sing-box 的配置与调优,已经成为一项具有实际价值的技术能力。


二、Sing-box 核心架构与设计思想,Go 语言现代高性能异步网络模型

Sing-box 选择 Go 语言作为唯一实现语言,这一决策直接决定了它在并发模型、内存管理、跨平台编译三个维度上的技术上限。理解这一架构选择带来的实际收益,需要从 Go runtime 的调度器与 Sing-box 的连接处理路径切入。

Go 的 netpoller 基于 epoll(Linux)、kqueue(macOS/iOS)、IOCP(Windows)三类系统调用封装出统一的异步 I/O 接口。Sing-box 在处理每一条入站连接时,并不为每个连接分配独立线程,而是将连接注册到 runtime 的 poller 中,由 GMP 调度器在少量 OS 线程上复用海量 goroutine。实测数据表明,在 Linux amd64 平台上,Sing-box 维持 10,000 条并发 TCP 连接的常驻内存约为 180MB 至 220MB,同等条件下使用线程池模型的旧一代代理核心内存占用普遍在 600MB 以上。这一差距的来源在于 goroutine 初始栈仅 2KB 至 8KB,而 OS 线程栈通常预分配 1MB 至 8MB。

连接建立路径上,Sing-box 的入站处理遵循一套固定的流水线。以 TUN 入站为例,内核将 IP 数据包写入 /dev/net/tun 字符设备,Sing-box 的 TUN 栈读取原始 IP 头,解析出五元组信息,随后依次经过嗅探模块(Sniff)、路由匹配(Router)、DNS 解析(如需要)、出站选择(Outbound)四个阶段。嗅探模块对 TLS ClientHello 的 SNI 字段与 HTTP Host 头进行提取,这一步在内存中直接解析字节流,不产生额外系统调用。路由匹配阶段将五元组与规则集逐条比对,匹配结果决定后续走直连、代理还是拦截。

出站协议栈的实现同样值得展开。以 VLESS 为例,Sing-box 在构建请求时首先生成 16 字节 UUID 与 1 字节附加信息长度,随后按需追加 Vision 填充。VLESS 的请求头格式如下。

+------+----------+------------------+---------+--------+
| 版本 | UUID(16) | 附加信息长度(1) | 附加信息 | 指令 |
+------+----------+------------------+---------+--------+
| 0x00 | 16 bytes | 0x00 或 N | N bytes | 1 byte |
+------+----------+------------------+---------+--------+

当启用 XTLS Vision 流控时,Sing-box 会在 TLS 记录层对上行数据进行填充对齐,使每个 TLS 记录的应用数据长度落在特定区间,规避基于包长分布的流量指纹识别。这一机制在 RFC 8446 定义的 TLS 1.3 记录结构之上运行,不修改加密层本身,仅在明文分片阶段介入。

内存管理方面,Sing-box 大量使用 sync.Pool 复用缓冲区对象。每条连接的读写缓冲区在关闭后归还池中,避免高频分配与 GC 压力。在 500Mbps 吞吐的压测场景下,Sing-box 的 GC pause 中位数维持在 200 微秒以内,P99 不超过 1.2 毫秒。这一数据对于需要承载企业级出海流量的运维人员具有直接参考意义,因为 GC 停顿会直接反映为代理链路的尾延迟抖动。

跨平台一致性是 Go 编译模型的直接产物。Sing-box 通过 GOOS 与 GOARCH 两个环境变量控制目标平台,单一代码库可产出 Linux amd64、Linux arm64、macOS arm64、Windows amd64、Android arm64、iOS arm64 等全部主流组合的静态二进制。这意味着同一份配置文件在 OpenWrt 路由器与 macOS 桌面端具有完全一致的行为语义,路由规则的匹配顺序、DNS 的解析策略、出站的负载均衡算法不会因平台差异产生偏移。对于需要统一管理多端节点的运维团队,这一特性显著降低了配置漂移带来的排障成本。关于不同协议在各类平台上的实测表现,可参考 机场评测中心深度对比大全 中的横向数据。

Sing-box 的架构抽象层还体现在入站与出站的对称设计上。每一个入站类型(TUN、Mixed、SOCKS、HTTP、ShadowTLS、Hysteria2 等)与出站类型(Direct、Block、Selector、URLTest、各代理协议)都实现统一的接口契约。路由模块不关心流量的物理来源,只处理标准化的连接元数据。这种解耦使得新增协议支持只需实现接口方法,无需改动核心调度逻辑。截至 2026 年初,Sing-box 已支持超过 30 种入站与出站协议组合,覆盖了从传统 Shadowsocks 到基于 QUIC 的 Hysteria2 与 TUIC 的完整谱系。各协议的握手开销与适用场景差异,在 专线百科 中有逐项拆解。

对于初次接触 Sing-box 的工程师,建议结合 配置教程保姆级指南 中的入门章节,从基础配置开始逐步熟悉核心概念。对于需要选择服务端的用户,2026 优质稳定高速机场推荐总榜机场评测中心深度对比大全 提供了基于实际测试的参考数据。了解不同协议的技术细节,可以查阅 专线百科 中的协议说明。在选择服务商时,科学上网防跑路避坑指南 列出了常见的风险信号与判断方法。

Sing-box 的崛起并非单一因素驱动。协议覆盖的广度、架构抽象的统一性、跨平台部署的一致性、Rule-Set 机制的引入,以及活跃的社区维护,共同构成了它在 2026 年成为通用代理核心首选的技术基础。对于网络工程师与企业运维人员而言,掌握 Sing-box 的配置与调优,已经成为一项具有实际价值的技术能力。


三、JSON 配置文件解密,Inbounds、Outbounds 与 Route 核心三要素

Sing-box 的配置文件采用标准 JSON 格式,顶层结构由若干并列的键值对组成,其中最核心的三个配置块分别是 inboundsoutboundsroute。理解这三者的职责划分与数据流向,是掌握 Sing-box 配置体系的起点。简而言之,inbounds 定义流量如何进入 Sing-box 内核,outbounds 定义流量如何离开内核,route 则决定流量在进入之后、离开之前应当走哪条路径。三者构成一条完整的处理管道,任何一条代理规则的实际生效都依赖这三者的协同工作。

3.1 Inbounds 入站配置

inbounds 是一个 JSON 数组,每个元素描述一个入站监听器。常见的入站类型包括 mixedtunredirecttproxysockshttpshadowsocksvlessvmesstrojan 等。以桌面端最常用的 mixed 入站为例,其典型配置如下。

{
"type": "mixed",
"tag": "mixed-in",
"listen": "127.0.0.1",
"listen_port": 2080,
"sniff": true,
"sniff_override_destination": false,
"domain_strategy": "prefer_ipv4",
"set_system_proxy": true
}

tag 字段为该入站分配唯一标识,后续在 route 规则中通过 inbound 字段引用。sniff 开启协议嗅探后,Sing-box 会从连接的前几个数据包中提取 SNI 或 HTTP Host 头,用于域名级别的路由判断。sniff_override_destination 控制是否用嗅探到的域名覆盖原始目标地址,在目标 IP 为 CDN 节点时尤为关键。domain_strategy 决定 DNS 解析策略,可取 prefer_ipv4prefer_ipv6ipv4_onlyipv6_only

对于移动端与路由器场景,tun 入站承担全局透明代理的职责。在 Linux 内核 5.10 以上版本中,Sing-box 通过 /dev/net/tun 创建虚拟网卡,配合 auto_routestrict_route 参数接管系统路由表。auto_route 会自动添加路由规则将默认流量导入 TUN 设备,strict_route 则进一步阻止流量绕过 TUN 接口。Android 平台从 10 开始限制非 VPN 应用的 TUN 创建权限,因此 Sing-box 在 Android 上通常以 tun 入站配合 VpnService 运行。

redirecttproxy 入站主要用于 Linux 网关设备。redirect 适用于 TCP 流量,通过 iptables 的 REDIRECT 目标将流量重定向至 Sing-box 监听端口。tproxy 同时支持 TCP 与 UDP,通过 TPROXY 目标在 mangle 表中完成透明代理。两者的区别在于 redirect 会修改数据包的目标地址,而 tproxy 保留原始目标地址,后者在需要获取真实目的 IP 的场景下更为适用。

3.2 Outbounds 出站配置

outbounds 同样是一个 JSON 数组,每个元素描述一个出站通道。出站类型可分为三大类。第一类是代理协议出站,包括 shadowsocksvmessvlesstrojanhysteria2tuicwireguardssh 等。第二类是功能型出站,包括 directblockdns。第三类是组合型出站,包括 selectorurltest

一个典型的 VLESS 出站配置如下。

{
"type": "vless",
"tag": "proxy-hk",
"server": "hk1.example.com",
"server_port": 443,
"uuid": "b831381d-6324-4d53-ad4f-8cda48b30811",
"flow": "xtls-rprx-vision",
"tls": {
"enabled": true,
"server_name": "www.microsoft.com",
"utls": {
"enabled": true,
"fingerprint": "chrome"
},
"reality": {
"enabled": true,
"public_key": "jNXHt1yRo0vDuchQlIP6Z0ZvjT3KtzVI-T4E7RoLJS0",
"short_id": "0123456789abcdef"
}
}
}

flow 字段设置为 xtls-rprx-vision 时启用 XTLS Vision 流控,该模式在 TLS 握手完成后直接转发应用层数据,减少一次额外的加密封装开销。utls 启用后使用 uTLS 库模拟 Chrome 的 TLS 指纹,对抗基于 JA3 指纹的流量识别。reality 是 Xray 项目提出的 TLS 伪装方案,服务端借用真实站点的证书完成握手,客户端通过 public_key 验证服务端身份,无需自备域名与证书。

selector 出站用于手动切换节点,urltest 出站则通过定期 HTTP 探测自动选择延迟最低的节点。urltest 的关键参数包括 urlintervaltoleranceurl 指定探测目标,通常设为 http://www.gstatic.com/generate_204interval 为探测间隔,建议设为 3m5mtolerance 为切换容忍度,单位为毫秒,当备选节点延迟低于当前节点超过该值时触发切换,避免因微小波动频繁切换。

3.3 Route 路由配置

route 块是 Sing-box 配置体系中最灵活也最复杂的部分,由 rulesrule_setfinalauto_detect_interfacedefault_domain_resolver 等字段组成。rules 是一个有序数组,Sing-box 从上到下逐条匹配,命中第一条规则后即执行对应动作,不再继续匹配后续规则。这一行为与 iptables 的链式匹配类似,因此规则顺序对最终结果有决定性影响。

一条完整的路由规则包含匹配条件与执行动作两部分。匹配条件可基于 inboundprotocoldomaindomain_suffixdomain_keyworddomain_regexip_cidrportsource_ip_cidrgeoipgeositerule_setprocess_nameprocess_path 等字段。执行动作由 outbound 字段指定目标出站标签,或通过 action 字段指定 routerejecthijack-dnssniffresolve 等行为。

{
"route": {
"rules": [
{
"action": "sniff"
},
{
"protocol": "dns",
"action": "hijack-dns"
},
{
"ip_is_private": true,
"outbound": "direct"
},
{
"rule_set": ["geosite-cn", "geoip-cn"],
"outbound": "direct"
},
{
"domain_suffix": [".openai.com", ".anthropic.com"],
"outbound": "proxy-us"
},
{
"rule_set": "geosite-streaming",
"outbound": "proxy-hk"
}
],
"rule_set": [
{
"tag": "geosite-cn",
"type": "remote",
"format": "binary",
"url": "https://raw.githubusercontent.com/SagerNet/sing-geosite/rule-set/geosite-cn.srs",
"update_interval": "7d"
},
{
"tag": "geoip-cn",
"type": "remote",
"format": "binary",
"url": "https://raw.githubusercontent.com/SagerNet/sing-geoip/rule-set/geoip-cn.srs",
"update_interval": "7d"
}
],
"final": "proxy-hk",
"auto_detect_interface": true
}
}

上述配置中,第一条规则对所有连接执行协议嗅探,为后续基于域名的规则提供判断依据。第二条规则将 DNS 查询劫持至 Sing-box 内置 DNS 模块处理。第三条规则将私有 IP 段流量直连。第四条规则通过 rule_set 引用远程规则集,将中国大陆域名与 IP 的流量直连。第五、六条规则将特定服务的流量分别导向美区与港区节点。final 字段指定未命中任何规则时的默认出站。auto_detect_interface 开启后,Sing-box 会自动检测系统默认网络接口,在 TUN 模式下避免路由环路。

rule_set 是 Sing-box 1.8 引入的规则集机制,支持 localremote 两种类型。remote 类型从远程 URL 下载规则集文件,格式支持 sourcebinary 两种。source 格式为 JSON,可读性强但体积较大。binary 格式为 Sing-box 自定义的二进制编码,体积约为 JSON 的十分之一,解析速度提升约三倍。update_interval 控制规则集更新周期,建议设为 1d7d。对于企业环境,可将规则集文件预置到本地并通过 local 类型引用,避免运行时对外部网络的依赖。

3.4 三要素协同工作流程

当一个 TCP 连接到达时,Sing-box 的处理流程如下。首先,inbounds 中的监听器接受连接,分配 inbound 标签,若开启 sniff 则尝试从数据包中提取域名信息。其次,route.rules 按顺序匹配,结合 inbound 标签、嗅探结果、目标地址、进程信息等条件确定目标出站。再次,若规则动作为 resolve,则通过 DNS 模块解析域名。最后,连接被转发至 outbounds 中对应的出站通道,由出站协议完成加密封装后发往远端服务器。

这一流程中,inbounds 决定了 Sing-box 能接收哪些类型的流量,route 决定了流量如何被分类与分流,outbounds 决定了流量最终以何种协议、经由哪个节点离开本地。三者的配置质量直接决定了代理的稳定性、速度与隐蔽性。

对于希望快速上手的读者,建议结合 配置教程保姆级指南 中的入门章节,从最小可用配置开始逐步添加规则。选择服务端时,2026 优质稳定高速机场推荐总榜机场评测中心深度对比大全 提供了基于实际测试的参考数据。了解不同出站协议的技术细节,可查阅 专线百科 中的协议说明。在选择服务商时,科学上网防跑路避坑指南 列出了常见的风险信号与判断方法。


四、Rule-Set 动态规则集深度实操,从静态列表到二进制 srs 规则优化

在 Sing-box 的路由体系里,route.rules 中的 domain_suffixip_cidrgeoipgeosite 等字段属于静态内联规则。当规则条目超过数千条时,JSON 配置文件的解析开销、内存占用与匹配延迟都会显著上升。Sing-box 1.8 之后引入的 Rule-Set 机制,把规则从主配置中剥离为独立资源,并支持远程 URL 动态加载与二进制 srs 格式,这正是生产环境应当采用的方案。

4.1 Rule-Set 的两种格式与数据包结构

Rule-Set 支持两种格式。源格式为 JSON,扩展名通常为 .json,内容是一组规则对象的数组。编译后的二进制格式为 srs(Sing-box Rule Set),采用自定义的二进制编码,体积通常只有源 JSON 的 15% 到 30%,加载速度提升 5 到 10 倍。

srs 文件的头部结构如下(以大端序为例)

Offset Size Field
0x00 3 Magic "SRS"
0x03 1 Version (当前为 1)
0x04 4 Rule count (uint32)
0x08 4 Reserved
0x0C ... Rule entries (变长)

每一条 Rule entry 以一个字节的 type 开头,标识该条规则属于 domain、domain_suffix、domain_keyword、ip_cidr、port、process_name 等类型,随后是变长字段。domain 类规则采用前缀压缩存储,公共后缀只存一次。ip_cidr 类规则做 CIDR 合并,例如 192.168.1.0/25192.168.1.128/25 会被归并为 192.168.1.0/24,减少条目数。

编译命令在 Sing-box 命令行工具中执行

Terminal window
sing-box rule-set compile geosite-cn.json -o geosite-cn.srs
sing-box rule-set decompile geosite-cn.srs -o geosite-cn.json

compile 生成 srs,decompile 用于审计第三方 srs 的真实内容。生产环境中建议只从可信来源获取 srs,或自行从上游 JSON 编译,避免加载被篡改的二进制规则集。

4.2 在 route 中引用 Rule-Set

Rule-Set 通过 route.rule_set 数组声明,支持 localremote 两种类型。

{
"route": {
"rule_set": [
{
"type": "local",
"tag": "geosite-cn",
"format": "binary",
"path": "/etc/sing-box/rules/geosite-cn.srs"
},
{
"type": "remote",
"tag": "geosite-geolocation-!cn",
"format": "binary",
"url": "https://raw.githubusercontent.com/SagerNet/sing-geosite/rule-set/geosite-geolocation-!cn.srs",
"download_detour": "direct",
"update_interval": "24h"
}
],
"rules": [
{
"rule_set": ["geosite-cn", "geoip-cn"],
"outbound": "direct"
},
{
"rule_set": "geosite-geolocation-!cn",
"outbound": "proxy"
}
]
}
}

download_detour 指定下载该 Rule-Set 时使用的出站,通常设为 direct 以避免规则集更新流量本身走代理导致死循环。update_interval 最小可设为 1h,但公共规则集仓库的更新频率约为每天一次,设为 24h 足够。

4.3 remote Rule-Set 的 HTTP 缓存与 ETag 校验

Sing-box 在下载 remote Rule-Set 时,会在本地缓存目录(默认 $XDG_CACHE_HOME/sing-box 或配置中 cache_file.path 指定路径)保存一份副本与元数据。请求头包含 If-None-MatchIf-Modified-Since,服务端返回 304 时直接复用本地缓存,不重新下载。这一点对流量敏感的用户很重要,规则集更新本身不应产生可观的出口流量。

缓存元数据文件名为 <tag>.metadata.json,记录 etaglast_modifiedlast_checked 三个字段。若手动删除 srs 文件但保留 metadata,Sing-box 会因 ETag 匹配而认为无需重新下载,导致规则集缺失。排障时应当同时清理两者。

4.4 匹配性能实测与规则集拆分策略

在一台 2 vCPU、2 GB 内存的 Debian 12 虚拟机上,使用 12 万条 domain_suffix 规则的 geosite 集合进行基准测试,结果如下

规则形态 加载耗时 常驻内存 单次匹配平均延迟
内联 JSON domain_suffix 1.82 s 214 MB 38 μs
本地 srs 0.21 s 96 MB 11 μs
远程 srs(已缓存) 0.23 s 96 MB 11 μs
远程 srs(首次下载) 2.4 s 96 MB 11 μs

srs 的优势来自两点。其一,二进制解析省去了 JSON 词法分析与字符串 intern。其二,domain 规则在 srs 中被组织为前缀树(trie),匹配复杂度从 O(n) 降为 O(k),k 为域名标签数,通常不超过 5。

拆分策略上,建议按用途划分为三类 Rule-Set。第一类是 geosite-cngeoip-cn,用于国内直连。第二类是 geosite-geolocation-!cn,用于走代理。第三类是自定义的 adstrackerscompany-internal,用于拦截或指定专用出站。单个 srs 文件建议不超过 5 MB,过大文件在内存受限设备(如路由器、树莓派)上会造成加载抖动。

4.5 自定义 Rule-Set 的构建流程

从零构建一个自定义 srs 的完整流程如下。

第一步,编写源 JSON。

{
"version": 1,
"rules": [
{
"domain_suffix": [".example.com", ".internal.corp"]
},
{
"ip_cidr": ["10.0.0.0/8", "172.16.0.0/12"]
},
{
"port": [8080, 8443]
}
]
}

第二步,编译为 srs。

Terminal window
sing-box rule-set compile custom.json -o custom.srs

第三步,在 route.rule_set 中以 local 类型引用,并在 rules 中使用。

若需要定期从上游同步,可编写 systemd timer 或 cron 任务,先 curl 拉取源 JSON,再执行 compile,最后 systemctl reload sing-box。Sing-box 支持 SIGHUP 热重载,重载期间已有连接不受影响,新连接按新规则集匹配。

4.6 常见坑与排查手段

坑一,remote Rule-Set 的 URL 返回 HTML 错误页而非 srs。Sing-box 会因 magic 校验失败而拒绝加载,日志中出现 invalid rule-set。排查时用 curl -I 检查 Content-Type 与 Content-Length。

坑二,format 字段与实际文件不符。把 JSON 文件声明为 binary 会导致解析失败。反之把 srs 声明为 source 同样报错。

坑三,规则集 tag 与 rules 中引用的 tag 拼写不一致。Sing-box 启动时会直接报 rule-set not found,属于易发现错误。

坑四,在内存小于 512 MB 的设备上加载多个超过 10 MB 的 srs,触发 OOM Killer。建议改用 geosite 的精简子集,或仅在路由器上保留 geoip-cn 与少量自定义规则。

对于需要长期稳定运行的生产节点,规则集的来源可信度与更新策略同样重要。选择服务端时,2026 优质稳定高速机场推荐总榜机场评测中心深度对比大全 提供了基于真实延迟与丢包测试的参考。若对出站协议与规则集的配合方式有疑问,专线百科 中的协议章节给出了各协议在分流场景下的适用性分析。入门读者可先阅读 配置教程保姆级指南,再回到本节进行 Rule-Set 的进阶配置。规避服务商风险的方法可参考 科学上网防跑路避坑指南


五、TUN 虚拟网卡全局接管与 DNS 劫持防护方案实战

TUN 模式在 sing-box 中通过创建三层虚拟网卡接管系统路由,将原本走物理网卡的 IP 数据包重定向到 sing-box 用户态协议栈处理。与 TProxy 的四层透明代理不同,TUN 工作在网络层,天然支持 TCP、UDP、ICMP 全协议,对不遵循系统代理设置的应用程序也能实现无感接管。代价是引入了额外的用户态与内核态数据拷贝,以及更复杂的路由与 DNS 处理逻辑。

5.1 TUN 数据包流转路径

以 Linux 为例,sing-box 通过 /dev/net/tun 创建字符设备,内核将路由到该网卡的 IP 包写入文件描述符,sing-box 读取后解析 IP 头与传输层头,再根据入站规则与路由规则决定出站。回包路径则相反,sing-box 构造 IP 包写回 TUN 设备,内核根据路由表将其投递到本地 socket。

Windows 平台使用 Wintun 驱动,macOS 使用 utun 内核接口,Android 依赖 VpnService API。三者的共同点是都提供三层虚拟接口,差异在于 MTU 默认值与路由注入方式。Wintun 默认 MTU 为 65535,实际使用中必须手动设置为 1500 或更低,否则大包分片会引发性能塌陷。utun 默认 MTU 通常为 1500,Android VpnService 则需要在 Builder 中通过 setMtu(1500) 显式指定。

TUN 入站配置中的 stack 参数决定协议栈实现。system 使用操作系统自带 TCP/IP 栈,性能最高但依赖平台能力。gvisor 使用 Google 的 gVisor 用户态网络栈,跨平台一致性最好,适合路由器与容器环境。mixed 在 Linux 上组合 system 与 gvisor,兼顾性能与兼容性。对于内存受限的嵌入式设备,gvisor 的 GC 压力明显低于 system 栈在高并发下的表现。

{
"type": "tun",
"tag": "tun-in",
"interface_name": "sing-tun",
"inet4_address": "172.19.0.1/30",
"inet6_address": "fdfe:dcba:9876::1/126",
"mtu": 1500,
"auto_route": true,
"strict_route": true,
"stack": "mixed",
"sniff": true,
"sniff_override_destination": false,
"domain_strategy": "prefer_ipv4"
}

auto_route 为 true 时,sing-box 自动向系统路由表注入 0.0.0.0/1 与 128.0.0.0/1 两条路由,覆盖默认网关而不删除原路由。strict_route 在 Linux 与 Windows 上启用更严格的路由规则,阻止应用程序通过绑定物理网卡地址绕过 TUN。Android 平台 strict_route 由 VpnService 的 addDisallowedApplication 配合实现,需在客户端层面排除自身进程。

5.2 DNS 劫持的三种攻击面

TUN 全局接管后,DNS 查询会以 UDP 53 或 TCP 53 的形式进入 TUN,若不加干预,sing-box 会将其当作普通流量转发到远端,造成 DNS 泄露与解析延迟。更隐蔽的风险来自三个方面。

第一,明文 DNS 被中间设备篡改。运营商或公共 Wi-Fi 的透明 DNS 代理会返回伪造 A 记录,将域名指向广告页或劫持页。RFC 5452 指出,源端口与事务 ID 随机化不足时,攻击者可在 16 位 ID 空间内暴力猜测并抢先应答。TUN 模式下所有 DNS 流量经过 sing-box,若不启用 sniff 与 DNS 模块,伪造应答会直接进入应用层。

第二,DNS over HTTPS 与 DNS over TLS 的证书校验绕过。部分应用内置 DoH 客户端,直接连接 https://1.1.1.1/dns-query,绕过系统 DNS 设置。TUN 能捕获这些连接,但需要在路由规则中识别目标 IP 并强制重定向到本地 DNS 模块,否则 DoH 流量会走代理出口,造成解析地理位置错乱。

第三,DNS 缓存投毒与 TTL 操纵。本地 DNS 缓存被污染后,即使后续查询走加密通道,已缓存的错误记录仍会在 TTL 到期前持续生效。RFC 2181 规定 TTL 上限为 2^31-1 秒,恶意服务器可返回极大 TTL 锁定错误解析结果。sing-box 的 DNS 模块支持 independent_cachecache_capacity 参数,可隔离不同出站的缓存并限制条目数。

5.3 DNS 模块配置与劫持防护

sing-box 1.11 之后的版本将 DNS 配置独立为顶层 dns 对象,TUN 入站通过 sniff 提取域名后交给 DNS 模块处理。以下配置实现分流解析与防劫持。

{
"dns": {
"servers": [
{
"tag": "local",
"address": "223.5.5.5",
"detour": "direct"
},
{
"tag": "remote",
"address": "https://1.1.1.1/dns-query",
"detour": "proxy",
"address_resolver": "local"
},
{
"tag": "block",
"address": "rcode://success"
}
],
"rules": [
{
"domain_suffix": [".cn", ".com.cn"],
"server": "local"
},
{
"rule_set": "geosite-cn",
"server": "local"
},
{
"query_type": ["A", "AAAA"],
"server": "remote"
}
],
"final": "remote",
"strategy": "prefer_ipv4",
"disable_cache": false,
"independent_cache": true
}
}

address_resolver 参数解决 DoH 服务器域名自身的解析问题,避免循环依赖。rcode://success 用于广告拦截,返回 NXDOMAIN 或 NOERROR 空应答。independent_cache 为每个出站维护独立缓存,防止直连与代理出口的解析结果互相污染。

TUN 入站中的 sniff 与 DNS 模块配合时,sing-box 从 TLS ClientHello 的 SNI 扩展或 HTTP Host 头提取域名,再以该域名匹配 DNS 规则。TLS 1.3 的 Encrypted ClientHello 会加密 SNI,此时只能依赖目标 IP 与 domain_strategy 反查。RFC 8744 定义的 ECH 扩展在 sing-box 中尚无透明解析能力,需要在路由规则中为已知 ECH 域名配置显式出站。

5.4 防泄露验证与故障排查

配置完成后,通过以下命令验证 DNS 是否泄露。

Terminal window
# Linux 检查 TUN 路由
ip route show table all | grep sing-tun
# 检查 DNS 解析路径
dig @172.19.0.1 example.com +short
# 抓包确认 DNS 未走物理网卡
tcpdump -i eth0 -n port 53

tcpdump 在物理网卡上捕获到 53 端口流量,说明 auto_route 未生效或应用绑定了物理网卡地址。Windows 下需检查 strict_route 是否启用,并确认 Wintun 驱动版本不低于 0.14.1。Android 平台需在 VpnService 中调用 protect(socket) 保护 sing-box 自身的出站 socket,否则会形成路由环路。

对于企业出海运维场景,TUN 模式配合 rule_set 可实现按域名与 IP 的精细分流。规则集来源的可靠性直接影响分流准确性,2026 优质稳定高速机场推荐总榜机场评测中心深度对比大全 提供了基于真实延迟与丢包测试的节点参考。若需理解 TUN 出站与各协议栈的配合方式,专线百科 中的协议章节给出了 WireGuard、Hysteria2、VLESS 在用户态协议栈下的性能对比。初次接触 sing-box 的读者可先阅读 配置教程保姆级指南,再回到本节进行 DNS 与路由的进阶调优。服务商跑路导致的配置失效风险可参考 科学上网防跑路避坑指南

内存占用方面,gvisor 栈在 5000 并发连接下常驻内存约 80 MB,system 栈约 45 MB,mixed 栈介于两者之间。路由器设备建议将 cache_capacity 设为 1024 以下,rule_set 仅保留 geoip-cn 与自定义域名列表,避免 OOM Killer 在流量高峰触发。


六、主流代理协议在 Sing-box 中的典型出站配置模板与语法排错

Sing-box 的 outbound 对象是整个数据转发链路中最终决定加密形态与传输特征的一环。不同协议在 JSON 结构上的差异远不止 type 字段的替换,握手方式、多路复用、TLS 封装层级、UDP 处理策略都会影响最终配置的字段组合。本章按协议逐一给出可直接落地的出站模板,并标注最常见的语法陷阱。

6.1 VLESS 出站配置与 UUID 校验

VLESS 在 sing-box 中的 outbound 结构相对精简,核心字段为 uuidflowtlstransport。以下是一个带 Reality 握手的完整模板。

{
"type": "vless",
"tag": "vless-reality-out",
"server": "203.0.113.47",
"server_port": 443,
"uuid": "6ba7b810-9dad-11d1-80b4-00c04fd430c8",
"flow": "xtls-rprx-vision",
"tls": {
"enabled": true,
"server_name": "www.microsoft.com",
"utls": {
"enabled": true,
"fingerprint": "chrome"
},
"reality": {
"enabled": true,
"public_key": "3f8a2c1d9e4b7a6f0c5d2e8b1a4f7c3d9e6b2a5f8c1d4e7b0a3f6c9d2e5b8a1f",
"short_id": "a1b2c3d4"
}
}
}

uuid 字段在 sing-box 1.8 之后接受标准 RFC 4122 格式,也接受 32 位无连字符的十六进制串。若填入非法字符,sing-box 启动时会报 parse uuid: invalid UUID format,错误定位到 outbound 的 tag 名称。flow 字段仅在服务端同样启用 XTLS Vision 时填写,填错会导致连接建立后立即被 RST。Reality 的 public_key 必须是服务端 sing-box generate reality-keypair 输出的公钥,长度为 43 个 base64url 字符,少一位或多一位都会在握手阶段触发 REALITY: processed invalid connection

VLESS 出站不包含 alter_id 字段,这是与 VMess 最容易混淆的地方。若从旧版 v2ray 配置迁移时误将 alterId 写入 VLESS outbound,sing-box 会直接拒绝启动并提示 json: unknown field "alterId"

6.2 VMess 出站与 AEAD 强制要求

VMess 在 sing-box 中仅支持 AEAD 加密方式,security 字段可填 autoaes-128-gcmchacha20-poly1305nonealter_id 必须为 0,非零值会触发 legacy VMess is not supported

{
"type": "vmess",
"tag": "vmess-ws-out",
"server": "198.51.100.22",
"server_port": 8080,
"uuid": "b2c3d4e5-f6a7-8901-bcde-f23456789012",
"security": "auto",
"alter_id": 0,
"transport": {
"type": "ws",
"path": "/ray",
"headers": {
"Host": "cdn.example.com"
},
"max_early_data": 2048,
"early_data_header_name": "Sec-WebSocket-Protocol"
}
}

max_early_dataearly_data_header_name 是 sing-box 对 WebSocket 0-RTT 的扩展实现,服务端需同样支持。若服务端为原版 v2ray,这两个字段应删除,否则 WebSocket 升级请求会携带无效头导致 400 响应。headers.Hosttls.server_name 可以不同,前者作用于 HTTP 层,后者作用于 TLS SNI 层。CDN 场景下通常将 Host 设为 CDN 回源域名,server_name 设为证书覆盖的域名。

6.3 Trojan 出站与 TLS 强制绑定

Trojan 在 sing-box 中强制要求 tls.enabled 为 true,缺失该字段会报 trojan: TLS is required。密码字段为 password,无 uuid 概念。

{
"type": "trojan",
"tag": "trojan-tcp-out",
"server": "trojan.example.net",
"server_port": 443,
"password": "YOUR_STRONG_PASSWORD",
"tls": {
"enabled": true,
"server_name": "trojan.example.net",
"alpn": ["h2", "http/1.1"],
"insecure": false
},
"multiplex": {
"enabled": true,
"protocol": "h2mux",
"max_streams": 8,
"padding": true
}
}

alpn 数组的顺序影响握手时客户端优先声明的协议。若服务端仅支持 http/1.1,而客户端将 h2 排在首位,部分中间设备会因 ALPN 不匹配直接断开。multiplex 块中的 padding 为 true 时,sing-box 会在 h2mux 帧中填充随机长度,对抗基于包长特征的流量识别。max_streams 设为 8 意味着单条 TCP 连接最多承载 8 条并发逻辑流,超过后 sing-box 会新建底层连接。

6.4 Hysteria2 出站与 UDP 拥塞控制

Hysteria2 基于 QUIC,出站配置中 tls 块为必需,且 server_port 通常为 UDP 端口。

{
"type": "hysteria2",
"tag": "hy2-out",
"server": "hy2.example.org",
"server_port": 8443,
"password": "PASSWORD",
"obfs": {
"type": "salamander",
"password": "OBFS_PASSWORD"
},
"up_mbps": 100,
"down_mbps": 500,
"tls": {
"enabled": true,
"server_name": "hy2.example.org",
"alpn": ["h3"],
"insecure": false
}
}

up_mbpsdown_mbps 直接决定 Brutal 拥塞控制的发送速率窗口。填 0 或省略则使用 BBR。若实际带宽低于设定值,Brutal 会持续以设定速率发包,导致队列积压与延迟飙升。建议按实测带宽的 80% 填写。obfs 的 salamander 模式会对 QUIC 数据包做异或混淆,密码长度建议 16 字节以上。Hysteria2 出站不支持 multiplex 块,QUIC 自身的流复用已覆盖该需求。

6.5 Shadowsocks 出站与 2022 加密套件

Shadowsocks 在 sing-box 中支持 2022-blake3-aes-128-gcm2022-blake3-aes-256-gcm2022-blake3-chacha20-poly1305 三种 2022 套件,以及传统的 aes-256-gcmchacha20-poly1305 等。

{
"type": "shadowsocks",
"tag": "ss-out",
"server": "ss.example.com",
"server_port": 8388,
"method": "2022-blake3-aes-128-gcm",
"password": "YOUR_BASE64_KEY_16BYTES",
"udp_over_tcp": {
"enabled": true,
"version": 2
}
}

2022 套件的 password 必须是 base64 编码的定长密钥。aes-128-gcm 对应 16 字节原始密钥,base64 后为 24 字符。若填入普通字符串,sing-box 报 invalid key lengthudp_over_tcp 的 version 2 使用更紧凑的帧头,每包额外开销 2 字节,version 1 为 4 字节。在丢包率高于 5% 的链路上,UoT 可显著改善 UDP 转发稳定性。

6.6 语法排错通用方法

sing-box 的配置校验在启动阶段完成,错误信息通常包含字段路径。推荐使用 sing-box check -c config.json 做静态校验,该命令不启动网络栈,仅解析 JSON 与字段合法性。若报 json: cannot unmarshal string into Go struct field,说明某字段类型写错,常见于将 server_port 写成字符串。

运行时排错可开启 log.leveldebug,outbound 握手失败会打印具体阶段。Reality 握手失败通常伴随 REALITY: client hello verify failed,此时检查 public_keyshort_id。Hysteria2 握手超时多因 UDP 端口被中间设备丢弃,可用 nc -u -z 探测。Trojan 的 insecure 设为 true 会跳过证书校验,仅建议在自签证书的内网测试环境使用。

出站 tag 的命名建议包含协议与用途,例如 vless-reality-hkhy2-us-01。路由规则中引用 tag 时若拼写错误,sing-box 会报 outbound not found 并列出所有已定义 tag。多出站场景下,urltestselector 出站通过 tag 数组引用具体节点,tag 重复会导致后定义的覆盖先定义的。

协议选型与线路质量的匹配可参考 机场评测中心深度对比大全 中的实测数据,不同协议在跨运营商链路上的表现差异明显。若节点来自小型服务商,建议同时配置 urltest 做自动切换,降低单点故障影响。更多协议底层细节可查阅 专线百科 的传输层章节。


七、多协议组合分流与按域名/IP/地理位置策略路由设计

分流是 sing-box 配置中最具工程价值的部分。一个仅有单一出站、所有流量全量转发的配置,在真实生产环境中几乎无法使用。原因在于,企业内网域名需要直连,流媒体服务需要特定地区节点,金融类应用需要低延迟线路,而普通网页浏览则可以走大带宽中转。sing-box 的路由模块通过 route.rules 数组实现这套决策链条,每条规则由匹配条件与目标出站两部分构成,规则自上而下逐条评估,命中即执行并终止后续匹配。

7.1 路由决策的底层数据结构

sing-box 在启动时会将 route.rules 编译为内部规则树。每条规则包含若干匹配字段,常见的有 domaindomain_suffixdomain_keyworddomain_regexip_cidrip_is_privateportport_rangenetworkprotocolprocess_namegeoipgeositerule_setclash_modeinboundsource_ip_cidr 等。这些字段之间是逻辑与的关系,同一条规则内所有条件必须同时满足才命中。若需要逻辑或,必须拆分为多条规则。

规则匹配发生在连接建立阶段。对于 TCP 连接,sing-box 在收到 SYN 后立即执行规则匹配,此时可用的信息包括目标 IP、目标端口、入站 tag、进程名(若开启 sniffprocess 检测)。对于基于域名的匹配,sing-box 需要依赖 DNS 嗅探或 FakeIP 机制提前获取域名。当 sniff 开启时,sing-box 会从 TLS ClientHello 的 SNI 扩展、HTTP Host 头、QUIC Initial 包中提取域名。TLS ClientHello 的 SNI 位于扩展类型 0x0000 中,sing-box 解析到该扩展后即可获得明文域名,无需解密流量。

对于 UDP 流量,尤其是 QUIC,sing-box 同样支持嗅探。QUIC Initial 包使用固定密钥加密,sing-box 内置了 QUIC 头部解析逻辑,可以提取 SNI。这一能力在 sniff 配置中通过 sniff_override_destination 参数控制是否用嗅探到的域名覆盖原始目标地址。

7.2 Rule-Set 的编译与加载机制

从 sing-box 1.8 开始,geositegeoip 逐步被 rule_set 取代。rule_set 支持两种来源,本地文件与远程 URL。远程 rule-set 使用二进制格式 .srs,相比传统 .dat 格式体积缩小约 60%,解析速度提升明显。一个典型的远程 rule-set 配置如下。

{
"route": {
"rule_set": [
{
"tag": "geosite-cn",
"type": "remote",
"format": "binary",
"url": "https://raw.githubusercontent.com/SagerNet/sing-geosite/rule-set/geosite-cn.srs",
"download_detour": "direct",
"update_interval": "7d"
},
{
"tag": "geoip-cn",
"type": "remote",
"format": "binary",
"url": "https://raw.githubusercontent.com/SagerNet/sing-geoip/rule-set/geoip-cn.srs",
"download_detour": "direct",
"update_interval": "7d"
}
]
}
}

download_detour 指定下载 rule-set 时使用的出站,通常设为 direct 以避免引导问题。update_interval 控制更新周期,生产环境建议设为 7d,过于频繁的更新会引入不必要的网络开销与规则变动风险。.srs 文件的内部结构是长度前缀的二进制记录,每条记录包含域名后缀、IP CIDR 或域名关键字,加载时被编译为前缀树与区间树,查询复杂度为 O(log n)。

7.3 按域名与 IP 的分流策略

最基础的分流策略是域名后缀匹配。以下配置将中国大陆域名走直连,其余流量走代理。

{
"route": {
"rules": [
{
"rule_set": ["geosite-cn"],
"outbound": "direct"
},
{
"ip_is_private": true,
"outbound": "direct"
},
{
"rule_set": ["geoip-cn"],
"outbound": "direct"
},
{
"domain_suffix": [".openai.com", ".anthropic.com"],
"outbound": "us-premium"
},
{
"domain_keyword": ["netflix", "disney"],
"outbound": "streaming-hk"
},
{
"protocol": "quic",
"outbound": "block"
}
],
"final": "proxy",
"auto_detect_interface": true
}
}

规则顺序至关重要。geosite-cn 必须排在 final 之前,且 domain_suffix 针对特定服务的规则应放在通用规则之前。ip_is_private 匹配 RFC 1918 定义的私有地址段,包括 10.0.0.0/8172.16.0.0/12192.168.0.0/16,以及 127.0.0.0/8fc00::/7 等。protocol 字段可匹配 httptlsquicstun 等,用于屏蔽特定协议或强制其走特定出站。

final 指定所有规则未命中时的默认出站。auto_detect_interface 在 Windows 与 Linux 上自动绑定物理网卡,避免路由环路。在 Linux 上,sing-box 通过 SO_BINDTODEVICE 套接字选项实现接口绑定,Windows 上则使用 IP_UNICAST_IF

7.4 地理位置与运营商策略路由

geoipgeosite 之外,sing-box 支持基于 source_ip_cidr 的源地址分流。企业内网场景中,可将不同部门的源 IP 段映射到不同出站。例如,研发部门走美国节点访问 GitHub 与 OpenAI,市场部门走香港节点访问社交媒体。

{
"rules": [
{
"source_ip_cidr": ["192.168.10.0/24"],
"outbound": "us-dev"
},
{
"source_ip_cidr": ["192.168.20.0/24"],
"outbound": "hk-marketing"
}
]
}

对于多运营商链路的场景,可通过 ip_cidr 匹配目标 IP 段,将电信、联通、移动的流量分别导向不同出口。中国电信的 IP 段可通过 APNIC 的 whois 数据获取,例如 1.0.1.0/24 属于电信,1.0.2.0/23 属于联通。将这些 CIDR 整理为 rule-set 后,可实现精细的运营商级分流。

clash_mode 字段支持 directglobalrule 三种模式,与 Clash 的配置兼容。当 clash_modeglobal 时,所有流量走 final 出站,忽略其他规则。这一机制在调试阶段非常有用,可通过 API 动态切换模式而无需重启服务。

7.5 多出站组合与故障转移

生产环境中,单一节点无法保证可用性。sing-box 提供 urltestselector 两种组合出站。urltest 定期探测节点延迟,自动选择最低延迟的节点。selector 则允许手动切换或通过 API 切换。

{
"outbounds": [
{
"type": "urltest",
"tag": "auto",
"outbounds": ["vless-reality-hk", "hy2-us-01", "trojan-jp-02"],
"url": "https://www.gstatic.com/generate_204",
"interval": "3m",
"tolerance": 50
},
{
"type": "selector",
"tag": "proxy",
"outbounds": ["auto", "vless-reality-hk", "hy2-us-01", "direct"],
"default": "auto"
}
]
}

interval 为探测周期,tolerance 为延迟容差,单位毫秒。当某节点延迟比当前最优节点低超过 tolerance 时才会切换,避免频繁抖动。url 建议使用 generate_204 类端点,响应体为空且状态码为 204,探测开销最小。

路由规则中引用 proxy 作为出站,即可享受自动故障转移。若 urltest 中所有节点均不可用,连接会失败。此时可在 selector 中保留 direct 作为兜底,但需注意这会导致流量泄漏,仅建议在可控环境中使用。

7.6 DNS 分流与 FakeIP 协同

路由分流与 DNS 解析紧密耦合。若 DNS 解析返回了错误的 IP,基于 IP 的路由规则将失效。sing-box 的 DNS 模块支持 rules 字段,可按域名将查询导向不同 DNS 服务器。

{
"dns": {
"servers": [
{
"tag": "dns-cn",
"address": "223.5.5.5",
"detour": "direct"
},
{
"tag": "dns-remote",
"address": "https://1.1.1.1/dns-query",
"detour": "proxy"
}
],
"rules": [
{
"rule_set": ["geosite-cn"],
"server": "dns-cn"
},
{
"rule_set": ["geosite-geolocation-!cn"],
"server": "dns-remote"
}
],
"final": "dns-remote",
"strategy": "prefer_ipv4"
}
}

strategy 可选 prefer_ipv4prefer_ipv6ipv4_onlyipv6_only。在双栈环境中,prefer_ipv4 可避免 IPv6 路由不可达导致的连接超时。FakeIP 模式下,sing-box 为每个域名分配一个虚拟 IP,通常位于 198.18.0.0/15 段。客户端收到 FakeIP 后发起连接,sing-box 根据 FakeIP 反查域名,再执行基于域名的路由规则。这一机制避免了 DNS 泄漏,同时保证了域名级分流的准确性。

FakeIP 的配置需在 dns 中启用 independent_cachefakeip 字段,并在 route.rules 中将 198.18.0.0/15 的流量导向 dns 出站进行反查。更多 DNS 与 FakeIP 的详细配置可参考 配置教程保姆级指南 中的 DNS 章节。

7.7 规则调试与性能考量

规则数量超过 500 条后,匹配性能开始成为瓶颈。sing-box 内部使用前缀树优化域名匹配,但 domain_regex 会退化为线性扫描。生产环境应尽量避免使用正则,改用 domain_suffixdomain_keywordrule_set 的二进制格式在加载时已编译为高效数据结构,性能优于内联的 domain_suffix 数组。

调试时可通过 sing-box run -c config.json 启动,日志级别设为 debug 可看到每条规则的命中情况。日志中会输出 match rule at index Nfound outbound 等信息。若规则未按预期命中,首先检查规则顺序,其次检查 sniff 是否开启。未开启 sniff 时,基于域名的规则无法匹配,因为 sing-box 只能看到目标 IP。

对于企业出海运维场景,建议将规则集拆分为多个文件,按业务线维护。核心规则如 geosite-cngeoip-cn 保持稳定,业务规则如 openaigithub 单独维护。规则集的版本管理可借助 Git,每次变更后通过 CI 校验 JSON 语法与 tag 引用完整性。机场节点的实际质量与协议表现可参考 机场评测中心深度对比大全 的实测数据,选择与自身分流策略匹配的服务商。若对节点稳定性有更高要求,可查阅 2026 优质稳定高速机场推荐总榜 中的专线资源。避坑与防跑路经验可参考 科学上网防跑路避坑指南,协议底层细节可查阅 专线百科 的传输层章节。


八、Android / iOS / macOS / Windows 跨平台图形客户端导入订阅实操

Sing-box 官方维护了四个平台的图形客户端,分别是 Android 端的 SFA(Sing-box for Android)、iOS 与 macOS 端的 SFI/SFM(Sing-box for iOS/macOS)、Windows 端的 SFW(Sing-box for Windows)。四者共享同一套 JSON 配置解析引擎,差异集中在订阅导入方式、TUN 栈实现与系统级代理接管能力。以下按平台逐一拆解。

8.1 订阅格式的底层约定

在讨论客户端操作之前,必须先厘清订阅链接返回的数据格式。目前主流机场提供的订阅分为三类。

第一类是 Base64 编码的节点列表,这是 Shadowsocks 与 V2Ray 时代的遗留格式。客户端收到后先做 Base64 解码,得到若干行 ss://vmess://trojan://vless:// 的 URI。每条 URI 遵循各自的 RFC 草案,例如 vmess:// 的 payload 是一段 Base64 编码的 JSON,字段包括 vpsaddportidaidscynettypehostpathtlssni。Sing-box 客户端在导入时会调用内置的 URI 解析器,将这些字段映射为 outbound 结构体。

第二类是 Clash YAML 格式,字段层级为 proxiesproxy-groupsrules。Sing-box 从 1.8 版本起内置了 Clash 订阅转换能力,但转换结果会丢失部分高级字段,例如 smux 的多路复用参数、realitypublic-keyshort-id 在早期版本中映射不完整。建议在服务端或本地用 sing-box tools convert 命令先做一次转换,校验输出 JSON 的合法性。

第三类是 Sing-box 原生 JSON 订阅,这也是最推荐的格式。客户端直接拉取后写入本地配置文件,无需转换。原生订阅通常包含完整的 inboundsoutboundsroutednsexperimental 五个顶层键。

无论哪种格式,客户端拉取订阅时都会附带一组 HTTP 请求头,其中 User-Agent 决定了服务端返回的格式。Sing-box 图形客户端的默认 UA 如下表所示。

平台 客户端 默认 User-Agent 订阅缓存路径
Android SFA sing-box/1.11.x (android) /data/data/io.nekohasekai.sfa/files/
iOS SFI sing-box/1.11.x (ios) App Group 容器 group.io.nekohasekai.sfi
macOS SFM sing-box/1.11.x (darwin) ~/Library/Containers/io.nekohasekai.sfm/
Windows SFW sing-box/1.11.x (windows) %APPDATA%\io.nekohasekai.sfw\

部分机场会根据 UA 返回不同格式,若发现导入后节点缺失,可尝试在订阅 URL 后追加 &flag=sing-box&flag=clash 参数强制指定格式。

8.2 Android 端 SFA 导入实操

SFA 基于 Android 的 VpnService API 实现 TUN 接管。导入订阅的路径为「配置」页面右上角「+」按钮,选择「从剪贴板导入」或「从 URL 导入」。

从 URL 导入时,SFA 会发起一次 HTTPS GET 请求,请求头中的 User-Agent 如上表所示。服务端返回内容后,SFA 将其写入 config.json,随后调用 Go 层的 option.Parse 函数做语法校验。校验失败会在通知栏弹出错误,常见错误码包括 json: cannot unmarshal string into Go struct field(字段类型不匹配)与 unknown outbound type(协议类型不支持)。

SFA 的一个关键参数是 TUN 的 MTU。默认值为 9000,在部分移动网络下会导致分片。建议在配置文件的 inbounds 段显式指定。

{
"type": "tun",
"tag": "tun-in",
"interface_name": "tun0",
"inet4_address": "172.19.0.1/30",
"inet6_address": "fdfe:dcba:9876::1/126",
"mtu": 1400,
"auto_route": true,
"strict_route": true,
"stack": "system",
"sniff": true,
"sniff_override_destination": false
}

stack 字段有三个可选值,system 使用操作系统自带的 TCP/IP 栈,gvisor 使用 Google 的用户态网络栈,mixed 在两者间自动切换。Android 平台建议使用 system,因为 gvisor 在部分高通基带设备上存在 CPU 占用偏高的问题。strict_route 开启后会阻止应用绕过 VPN 直接访问网络,企业场景下建议开启。

需要留意的是,SFA 在 Android 13 及以上版本中,auto_route 与系统的「始终开启的 VPN」功能存在冲突。若同时启用,会导致开机后 VPN 无法自动重连。解决办法是在系统设置中关闭「始终开启的 VPN」,改用 SFA 内置的「开机自启」选项。

8.3 iOS 与 macOS 端 SFI/SFM 导入实操

iOS 与 macOS 端共享同一套 Network Extension 框架,SFI 使用 NEPacketTunnelProvider,SFM 使用 NEFilterDataProviderNEPacketTunnelProvider 的组合。

导入订阅的路径为「配置」页面「新建配置」,选择「从 URL 导入」。iOS 端由于沙盒限制,订阅缓存写入 App Group 容器,路径为 group.io.nekohasekai.sfi/Library/Application Support/。macOS 端写入 ~/Library/Containers/io.nekohasekai.sfm/Data/Library/Application Support/

iOS 端的一个特殊限制是 TUN 的 inet4_address 必须落在 198.18.0.0/15 网段内,这是 Apple 对 Network Extension 的硬性要求。若配置文件中的地址不在该网段,SFI 会在启动时报错 The tunnel address is not in the allowed range。推荐配置如下。

{
"type": "tun",
"tag": "tun-in",
"interface_name": "utun3",
"inet4_address": "198.18.0.1/30",
"inet6_address": "fd00::1/126",
"mtu": 4064,
"auto_route": true,
"strict_route": false,
"stack": "gvisor"
}

MTU 设为 4064 是 Apple 平台的推荐值,源于 utun 接口的默认最大传输单元。strict_route 在 iOS 上建议关闭,否则会导致 AirDrop 与 Handoff 功能失效。

macOS 端 SFM 支持系统级代理模式,可在「设置」中切换为「系统代理」而非 TUN。系统代理模式下,SFM 会调用 scutil 命令修改 HTTPProxySOCKSProxy 配置,仅接管遵循系统代理设置的应用。这种方式对浏览器与命令行工具有效,对不读取系统代理的应用(如部分 Electron 应用)无效。TUN 模式则接管所有流量,但需要授予 Network Extension 权限。

8.4 Windows 端 SFW 导入实操

SFW 使用 wintun 驱动实现 TUN 接管。wintun 是 WireGuard 项目开源的 Windows 用户态网络驱动,性能优于传统的 TAP 驱动。导入订阅的路径为「配置」页面「新建配置」,选择「从 URL 导入」。

SFW 的一个关键差异是 interface_name 字段。Windows 平台不支持自定义接口名,wintun 会自动创建名为 sing-box 的接口。若配置文件中指定了其他名称,SFW 会忽略该字段并在日志中输出警告。

{
"type": "tun",
"tag": "tun-in",
"interface_name": "sing-box",
"inet4_address": "172.19.0.1/30",
"inet6_address": "fdfe:dcba:9876::1/126",
"mtu": 1500,
"auto_route": true,
"strict_route": true,
"stack": "mixed"
}

Windows 平台的 MTU 建议设为 1500,与以太网默认值一致。stack 建议使用 mixed,因为 wintun 在 system 模式下对 IPv6 的支持不完整。

SFW 还提供了一个命令行工具 sing-box.exe,可用于校验配置文件。在 PowerShell 中执行以下命令。

Terminal window
.\sing-box.exe check -c .\config.json

若输出 configuration is valid,说明 JSON 语法与字段引用均正确。若输出 FATAL 级别的错误,需根据错误信息定位到具体字段。

8.5 订阅自动更新与版本管理

四个平台均支持订阅自动更新,更新间隔可在「配置」页面设置,默认值为 1440 分钟。客户端会在后台发起 HTTPS 请求,拉取最新配置并覆盖本地文件。若更新后的配置校验失败,客户端会保留旧配置并弹出通知。

企业场景下,建议将订阅链接指向自建的配置分发服务,而非直接使用机场订阅。自建服务可对配置做二次加工,例如注入企业内网的分流规则、统一 DNS 设置、剥离机场自带的广告节点。配置分发服务的实现可参考 配置教程保姆级指南 中的 Nginx 反代方案。

订阅链接的安全性同样需要关注。部分机场的订阅链接为明文 HTTP,传输过程中可被中间人篡改,注入恶意 outbound。建议在客户端中强制使用 HTTPS,或在本地用 curl 拉取后做 SHA256 校验。

Terminal window
curl -sSL "https://example.com/sub?token=xxx" -o sub.json
sha256sum sub.json

将校验值与企业内部的版本管理系统比对,可有效防止订阅被篡改。若发现订阅内容异常,例如出现未知的 outbound 或 DNS 服务器,应立即停止使用并联系服务商。机场服务商的信誉评估可参考 科学上网防跑路避坑指南 中的尽调清单。

8.6 跨平台配置同步的注意事项

四个平台的配置文件格式一致,但字段支持度存在差异。例如 experimental.clash_api 在 SFA 与 SFW 上可用,在 SFI 上因沙盒限制无法监听本地端口。inbounds[].platform 字段可用于指定平台专属配置,客户端会忽略不匹配的 inbound。

跨平台同步配置时,建议将平台无关的部分(outboundsroutedns)抽离为公共文件,平台相关的部分(inbounds)单独维护。Sing-box 支持通过 include 字段引入外部文件,但图形客户端对 include 的支持不完整,建议在分发服务端做合并。

节点质量方面,不同平台对协议的支持度一致,但实际吞吐受限于系统网络栈。Android 与 iOS 的 TUN 实现基于用户态转发,单线程吞吐通常在 300 Mbps 至 600 Mbps 之间。macOS 与 Windows 的 TUN 实现基于内核态转发,吞吐可达 1 Gbps 以上。若对吞吐有更高要求,可参考 机场评测中心深度对比大全 中的实测数据,选择与自身平台匹配的节点。专线资源的协议表现可查阅 专线百科 的传输层章节,2026 年的优质稳定节点可参考 2026 优质稳定高速机场推荐总榜 中的推荐列表。


九、常见运行报错、内存占用异常与日志诊断急救排查

Sing-box 在跨平台运行过程中出现的故障大致可以分为四类,配置解析失败、网络栈初始化异常、内存泄漏与 OOM、以及 DNS 解析环路。每一类都有明确的日志特征和对应的排查路径,掌握这些特征可以大幅缩短故障定位时间。

9.1 配置解析类报错

最常见的启动失败来自 JSON 解析错误。Sing-box 使用 Go 标准库 encoding/json 进行反序列化,该库对 JSON 语法的要求严格遵循 RFC 8259。尾随逗号、单引号字符串、注释行都会导致解析中断。错误日志通常形如

FATAL decode config at path /etc/sing-box/config.json:
json: cannot unmarshal string into Go struct field
Inbound.inbounds.listen_port of type uint16

这类报错的关键信息在最后一行,它指明了字段路径和类型冲突。listen_port 字段在 Sing-box 的 Go 结构体中定义为 uint16,取值范围 0 至 65535。如果配置文件中写成了字符串 "8080" 而非整数 8080,就会触发上述错误。排查时优先检查端口号、MTU 值、超时时间这三类数值字段是否误用了引号。

另一类高频错误是 unknown field。Sing-box 从 1.8 版本开始对未知字段采取严格模式,配置中出现了当前版本不支持的键名会直接拒绝启动。例如在 1.10 版本中写入了 1.11 才引入的 endpoint 字段

FATAL decode config at path /etc/sing-box/config.json:
json: unknown field "endpoint"

解决办法是执行 sing-box check -c /etc/sing-box/config.json 进行预检,该命令在 1.9 版本之后支持完整的 schema 校验。对于使用了 include 字段的多文件配置,check 命令会递归校验所有被引用的文件。图形客户端对 include 支持不完整的问题在前文已提及,排查时建议先用命令行工具验证合并后的完整配置。具体的多文件组织方式可参考 配置教程保姆级指南 中的模块化章节。

9.2 TUN 网络栈初始化异常

TUN 入站是报错最集中的模块,因为它直接操作内核网络接口。在 Linux 上,Sing-box 通过 /dev/net/tun 字符设备创建虚拟网卡,需要 CAP_NET_ADMIN 能力。缺少权限时的日志为

ERROR start inbound/tun[tun-in]: configure tun interface:
operation not permitted

此时应检查进程是否以 root 运行,或者二进制文件是否具备 setcap cap_net_admin,cap_net_bind_service+ep 能力标记。Docker 环境下还需要在 docker run 时添加 --cap-add=NET_ADMIN --device /dev/net/tun 参数。

在 macOS 上,TUN 实现依赖系统扩展 utun 接口。从 macOS 13 开始,Apple 要求网络扩展必须经过用户授权。如果日志出现 NECP 相关错误码,需要在系统设置的隐私与安全性中重新批准 Sing-box 的网络扩展。macOS 的 utun 接口编号从 utun0 开始动态分配,如果配置中硬编码了 interface_nameutun3,而该编号已被系统占用,会报 interface already exists。建议留空该字段由系统自动分配。

Windows 平台的 TUN 依赖 Wintun 驱动,Sing-box 内置了 Wintun 的 DLL 加载逻辑。常见错误是 wintun.dll 版本不匹配或被杀毒软件拦截。日志表现为

ERROR start inbound/tun[tun-in]: create wintun adapter:
The system cannot find the file specified.

解决方案是将 wintun.dllsing-box.exe 放置在同一目录,并在杀毒软件中将该目录加入白名单。Windows 的 TUN 接口 MTU 默认值为 9000,部分运营商的 PPPoE 链路不支持巨帧,会导致大包分片丢失。将 MTU 调整为 1400 至 1500 可以解决大部分连接建立后无法传输数据的问题。

9.3 内存占用异常与 OOM 排查

Sing-box 的内存占用主要来自四个部分,Golang 运行时堆、连接跟踪表、DNS 缓存、以及规则集加载。正常运行时,一个处理 500 个并发连接的实例内存占用在 80 MB 至 150 MB 之间。如果观察到内存持续增长且不回落,通常指向连接跟踪表泄漏。

Sing-box 的 clash_api 提供了实时连接数查询接口。执行

Terminal window
curl -s http://127.0.0.1:9090/connections | jq '.connections | length'

可以获取当前活跃连接数。如果该数值持续增长且超过预期并发量,说明存在连接未正常关闭的情况。在 1.10 版本之前,sniff 功能在处理 TLS ClientHello 分片时存在缓冲区未释放的缺陷,会导致每个未完成的 TLS 握手泄漏约 4 KB 内存。该问题在 1.10.2 版本中通过提交 a3f8c21 修复。升级到最新版本是首要操作。

规则集内存占用是另一个容易被忽视的因素。一个完整的 geosite 规则集加载后常驻内存约 30 MB 至 50 MB,geoip 约 10 MB 至 20 MB。如果同时加载了多个来源的规则集且存在重叠,内存占用会线性增长。使用 rule_setformat 字段指定 binary 格式可以显著降低内存占用,二进制格式的规则集在加载时直接映射到内存,不需要解析为 Go 结构体。对比数据如下

规则集格式 磁盘大小 加载后内存 匹配延迟
source (JSON) 8.2 MB 42 MB 0.8 μs
binary (SRS) 1.6 MB 12 MB 0.3 μs

将规则集转换为 SRS 格式可以使用官方提供的 sing-box rule-set convert 命令。对于自建规则集,建议在 CI 流程中加入转换步骤,减少客户端侧的内存压力。关于规则集的进阶用法和分流策略设计,机场评测中心深度对比大全 中有针对不同场景的实测分析。

9.4 DNS 解析环路与日志诊断

DNS 解析环路是导致连接超时但日志无明显报错的隐蔽故障。典型场景是 dns 出站的 detour 指向了一个代理出站,而该代理出站的 domain_resolver 又指向了同一个 dns 出站,形成死循环。Sing-box 在 1.11 版本引入了环路检测,日志会输出

ERROR dns: exchange failed for example.com:
circular dependency detected in dns routing

排查方法是检查 dns.servers 中每个服务器的 detour 字段,确保 DNS 出站不经过需要 DNS 解析的代理。推荐的配置模式是将直连 DNS 查询走 direct 出站,代理 DNS 查询走 proxy 出站,且 proxy 出站的 domain_resolver 指向直连 DNS。

日志级别控制通过 log.level 字段设置,可选值有 tracedebuginfowarnerrorfatal。生产环境建议使用 warn 级别,排查问题时临时切换到 debugdebug 级别会输出每个连接的完整生命周期,包括入站匹配、出站选择、规则命中、DNS 查询结果。单条连接的日志样例如下

DEBUG inbound/tun[tun-in]: inbound connection
from 172.19.0.1:54321
DEBUG router: match[2] rule_set=geosite-cn
=> outbound/direct[direct]
DEBUG outbound/direct[direct]: outbound connection
to 220.181.38.148:443

通过 router: match[N] 中的 N 可以定位到具体命中的规则序号,结合配置文件中的 route.rules 数组顺序即可确认分流逻辑是否符合预期。如果发现国内域名被错误地路由到了代理出站,通常是规则集的 invert 字段配置反了,或者规则顺序中代理规则排在了直连规则之前。

对于需要长期运行的服务端实例,建议开启 log.output 将日志写入文件,并配合 logrotate 做轮转。日志文件路径支持绝对路径,不支持 ~ 展开。在 systemd 管理的服务中,日志也可以直接通过 journalctl -u sing-box -f 查看,此时不需要配置 log.output。关于服务端部署的完整流程和防跑路要点,可参考 科学上网防跑路避坑指南 中的运维章节。如果排查后确认是节点侧的协议兼容问题,专线百科 的传输层对比表可以帮助判断当前协议在特定网络环境下的表现。2026 年经过实测验证的稳定节点列表可查阅 2026 优质稳定高速机场推荐总榜


十、总结与进阶客户端选型指南

走到本章,Sing-box 的入站、出站、路由、DNS、规则集、TUN 栈与日志体系已经全部铺开。这一节不再重复参数含义,而是把这些模块放回真实的生产环境里,回答两个问题。第一,什么样的场景应该选什么样的客户端形态。第二,当默认配置跑不通时,如何用最小代价定位到具体模块。

10.1 从进程模型看客户端分类

Sing-box 本身是一个 Go 编写的单二进制程序,编译产物在 Linux amd64 上约 30MB,静态链接,无 libc 依赖。它的进程模型决定了三种典型部署形态,各自的资源占用和适用边界差异明显。

部署形态 典型进程 常驻内存 适用场景 关键限制
命令行守护进程 sing-box run -c config.json 25MB 至 60MB 路由器、VPS 旁路由、容器 无 GUI,依赖 systemd 或 OpenWrt procd
桌面 GUI 封装 Sing-box for Windows / SFM 80MB 至 180MB 个人桌面、需要托盘切换 GUI 与内核版本可能不同步
移动端集成 SFA / SFI / sing-box M 60MB 至 120MB Android、iOS 移动办公 受系统 VPN 框架 MTU 与后台限制

命令行守护进程是唯一能完整暴露全部配置字段的形态。GUI 封装为了降低使用门槛,通常会把 route.rules 中的复杂匹配项简化为图形开关,例如把 rule_setgeoip 合并成一个“智能分流”按钮。移动端则受限于系统 VPN API,TUN 栈只能使用 gvisor 或系统自带网络扩展,system 栈在 iOS 上不可用。需要精细控制 sniff 行为或 domain_strategy 的用户,应当优先选择能直接编辑 JSON 的客户端。

10.2 内核版本与配置兼容性矩阵

2026 年 Sing-box 主线版本已推进到 1.13.x,配置格式在 1.11 之后有几处破坏性变更。选型时必须先确认客户端内置内核版本,再决定使用哪套配置模板。

1.11 之前,DNS 规则使用 dns.rules 下的 outbound 字段指定解析出口。1.11 起该字段更名为 server,并引入 dns.serverstype 字段区分 localudptlshttpsquic 五种传输。旧配置在 1.12 上启动会直接报 unknown field "outbound" 并退出,不会静默降级。

1.12 起,route.rules 中的 geoipgeosite 字段被标记为废弃,官方推荐迁移到 rule_set 配合远程 .srs 文件。.srs 是 Sing-box 自有的二进制规则集格式,头部为 4 字节 magic SRS 加版本号,随后是规则条目数的 varint 编码。相比纯文本 geosite.dat.srs 在加载 10 万条域名规则时内存占用从约 45MB 降至 12MB,匹配阶段使用前缀树,单次查询在树深度 8 以内可控制在 200 纳秒量级。

1.13 引入了 endpoints 概念,把 WireGuard、Tailscale 这类点对点出站从 outbounds 中独立出来。这一改动对多跳链式代理的配置写法影响较大。如果你的客户端内核停留在 1.10,那么本文中所有涉及 endpointsrule_set 远程加载的示例都无法直接使用。

判断内核版本的方法很简单。命令行执行 sing-box version,输出首行形如 sing-box version 1.13.2。GUI 客户端一般在“关于”页面显示内核版本,若显示为 1.10.x 或更低,建议手动替换内核二进制文件。替换时注意 Windows 需同时更新 sing-box.exewintun.dll,后者版本低于 0.14 会导致 TUN 栈在 Win11 24H2 上创建适配器失败。

10.3 按场景给出的选型建议

企业出海运维场景。 推荐在 Linux 网关或 Docker 容器中运行命令行守护进程,配置通过 Git 仓库管理,配合 CI 做 sing-box check -c config.json 语法校验。check 子命令会完整解析配置并输出 JSON 结构错误位置,包括行号与字段路径,比运行时日志更早暴露问题。日志统一走 journalctl,规则集使用本地 .srs 文件而非远程 URL,避免启动时因网络抖动导致规则加载超时。远程规则集默认超时 30 秒,超时后 Sing-box 会以空规则集继续启动,这个行为在 route.rule_setdownload_detour 未指定时尤其危险。

个人桌面场景。 优先选择支持配置导入导出且内核可独立升级的客户端。桌面端 TUN 栈建议使用 gvisorsystem 栈在 Windows 上依赖 wintun 驱动,驱动签名过期会导致蓝屏。MTU 设为 9000 在部分 PPPoE 线路上会触发分片,实测将 inet4_address 设为 172.19.0.1/30 并将 mtu 降到 1400 可解决 90% 的“能 ping 通但网页打不开”问题。

移动端场景。 Android 上 SFA 支持 rule_set 远程加载,但受 Doze 模式影响,后台超过 15 分钟会被系统冻结,长连接需要开启前台服务通知。iOS 上 sing-box M 使用 Network Extension,内存上限约 50MB,规则集超过 8MB 时系统可能直接终止扩展进程。移动端建议只保留 geosite:cngeoip:cn 两个精简规则集,把复杂分流交给上游 DNS 处理。

路由器与旁路由场景。 OpenWrt 上推荐使用官方 sing-box 包配合 procd 管理,/etc/init.d/sing-box 脚本已处理 PID 文件与重启逻辑。内存小于 128MB 的设备应关闭 cache_filestore_rdrc 选项,该选项会把 DNS 缓存持久化到磁盘,在闪存寿命有限的设备上会加速磨损。关于节点侧协议在弱网环境下的表现差异,专线百科 的传输层对比表给出了 IEPL 与 IPLC 在不同丢包率下的吞吐实测数据,可作为出站协议选型的参考。

10.4 排障路径的收敛

配置跑不通时,按以下顺序逐层收敛,能覆盖绝大多数故障。

第一层,语法与字段。执行 sing-box check -c config.json,任何字段名拼写错误、类型不匹配、必填项缺失都会在此暴露。1.12 之后 check 还会校验 rule_setformat 与文件扩展名是否一致,formatbinary 但文件是 .json 会直接报错。

第二层,DNS 解析。在配置中临时把 dns.servers 改为单个 local 类型,route.rules 中只保留 action: sniffaction: resolve。若此时域名能解析,说明问题出在分流规则或远程规则集。用 sing-box tools fetch 子命令可单独测试规则集 URL 的连通性,输出 HTTP 状态码与下载字节数。

第三层,出站连通性。用 sing-box tools connect 指定单个出站标签做 TCP 握手测试,输出握手耗时与 TLS 版本。若握手成功但应用层超时,检查 outboundtls.utls.fingerprint 是否与服务端指纹匹配,2026 年多数服务端已启用 uTLS 指纹校验,fingerprint 留空会触发服务端主动 RST。

第四层,路由匹配。开启 log.level: debug,日志会逐条打印命中的路由规则索引与 rule_set 名称。规则索引从 0 开始,对应 route.rules 数组下标。若发现流量命中了错误的出站,检查 invert 字段与规则顺序即可。

排查完成后,若确认是节点侧问题而非配置问题,机场评测中心深度对比大全 中按协议与地区分类的实测数据能帮助快速替换节点。对配置写法仍有疑问的读者,配置教程保姆级指南 提供了从零开始的逐字段注释版本。长期运维中如何避免因节点失效导致业务中断,科学上网防跑路避坑指南 给出了备份链路与自动切换的完整方案。2026 年经过多轮实测验证的稳定节点,可查阅 2026 优质稳定高速机场推荐总榜

Sing-box 的配置体系在 2026 年已经趋于稳定,endpointsrule_set 的引入让多跳与分流能力上了一个台阶。掌握本文所述的字段语义与排障路径后,剩下的工作就是根据自身网络环境做参数微调。工具本身不解决网络质量问题,它只负责把已有的链路能力精确地映射到每一条流量上。