1. Choose Your Routing Criteria: Domains, Destination IPs, and a Fallback
Routing traffic inside and outside mainland China isn't based on a webpage's language or a company's place of registration. Clash's rule engine uses information available for each connection, such as its domain and destination IP, and checks rules in order. This guide aims to send explicitly listed domains direct, try a direct connection for known mainland China IPs, and send all other connections to a proxy group.
This is a maintainable routing strategy, not a precise geographic classification of every website. International services may use mainland China CDNs, while services based in mainland China may call APIs hosted elsewhere. Domain rules express routing intent; GEOIP adds IP location data. Neither replaces the other.
| Rule | What it checks | Use case |
|---|---|---|
DOMAIN | Full domain | Exact exception for a single hostname |
DOMAIN-SUFFIX | Domain suffix | A domain and its subdomains |
GEOIP | Database location of the destination IP | Connections not covered by the supplemental domain list |
MATCH | No preceding rule matched | Fallback for all remaining connections |
Three requirements for the configuration to work
- The client must be in
rulemode. Global mode does not select an outbound based on the rule list in this guide. - The target app's traffic must pass through the client. The system proxy only covers apps that honor proxy settings; TUN depends on virtual network adapter, routing, and permissions being configured.
- The proxy group referenced by the rules must exist. This guide uses
境外代理as the group name; replace it with the exact name in your current configuration.
2. Put DOMAIN-SUFFIX Before GEOIP
DOMAIN-SUFFIX,qq.com,DIRECT matches qq.com and mail.qq.com, but not notqq.com. Suffix matching respects domain-label boundaries, so there's no need to write *.qq.com. Don't include https://, a port, or a URL path in the domain field.
Standard rule lists use first-match-wins order from top to bottom; the engine doesn't automatically pick the most specific rule. For exceptions within a site, put the exact domain first, followed by the broader suffix rule. Once a suffix rule matches, a later GEOIP rule won't change the result.
Basic rules
mode: rule
rules:
- DOMAIN,localhost,DIRECT
- IP-CIDR,127.0.0.0/8,DIRECT,no-resolve
- IP-CIDR,10.0.0.0/8,DIRECT,no-resolve
- IP-CIDR,172.16.0.0/12,DIRECT,no-resolve
- IP-CIDR,192.168.0.0/16,DIRECT,no-resolve
- IP-CIDR6,::1/128,DIRECT,no-resolve
- IP-CIDR6,fc00::/7,DIRECT,no-resolve
- DOMAIN-SUFFIX,qq.com,DIRECT
- DOMAIN-SUFFIX,taobao.com,DIRECT
- GEOIP,CN,DIRECT,no-resolve
- MATCH,Overseas Proxy
This snippet keeps common private network addresses, IPv6 unique-local addresses, and loopback addresses on a direct connection, then handles two explicitly listed domain suffixes. It isn't a complete list of special-use addresses. If your network uses IPv6 link-local addresses, multicast, or custom corporate routes, add rules to complement your existing LAN configuration; don't simply remove related entries from the original config.
DIRECTis a built-in routing policy. It doesn't mean traffic bypasses the client; the client establishes the outbound connection directly.境外代理is a custom proxy group name. Its name in the rules must exactly match the name underproxy-groups.- Put
MATCHlast. If it appears earlier, no subsequent rules will get a chance to match.
To proxy a specific subdomain while keeping the rest of the parent domain direct, add DOMAIN,exact.hostname.to.match,Overseas Proxy before the suffix rule. Don't switch an entire large service's suffix to proxy just to handle one API endpoint; that broadens the change and makes it harder to verify.
3. GEOIP and no-resolve: Should the Rule Trigger DNS Resolution?
GEOIP,CN,DIRECT checks an IP database; it doesn't look up a website's country online. If a connection only has a domain name, the rule engine may need to resolve it before checking the IP. The exact behavior also depends on the core, DNS mode, and metadata already available for the connection.
Adding no-resolve means the IP rule won't initiate a DNS lookup just for the purpose of matching. If the connection already has a destination IP that can be checked, the rule can still match; if no usable IP is available, evaluation continues to the next rule. This doesn't disable DNS or block DNS requests.
| Rule syntax | When only a domain is available | Trade-off |
|---|---|---|
GEOIP,CN,DIRECT | May trigger resolution to check the IP | More chances to route by IP location, at the cost of depending on DNS resolution |
GEOIP,CN,DIRECT,no-resolve | Don't resolve specifically for this rule | Avoids extra resolution during matching; some domain-based connections will fall through |
Choosing an approach
- If you maintain a comprehensive list of domains that should connect directly and want all remaining domains to go to the proxy group, consider using
no-resolve. - If you rely on IP location to catch many unlisted domains hosted in mainland China, consider omitting the parameter, but check that DNS is available and returns the expected results.
- If an app connects directly to an IP address, the destination is already available;
no-resolveusually won't prevent the rule from matching it.
GEOIP accuracy also depends on the local database. IP range transfers, delayed database updates, and CDN routing can all cause discrepancies. mihomo's geographic data settings also affect which data files it reads. If startup logs report a missing database or a read error, fix the data-loading issue first rather than repeatedly changing rule order.
4. rule-providers: Keep Direct-Connect Domains in a Separate File
When domain exceptions grow from a handful to dozens, keeping them all in the main config makes duplicates and typos more likely. mihomo lets you declare providers with rule-providers and reference them using RULE-SET. A provider stores match conditions; the rule that references it in the main config determines which policy to use.
Main config: declare a local domain rule set
rule-providers:
domestic-domains:
type: file
behavior: domain
format: yaml
path: ./rules/domestic-domains.yaml
rules:
- DOMAIN,localhost,DIRECT
- IP-CIDR,127.0.0.0/8,DIRECT,no-resolve
- IP-CIDR,10.0.0.0/8,DIRECT,no-resolve
- IP-CIDR,172.16.0.0/12,DIRECT,no-resolve
- IP-CIDR,192.168.0.0/16,DIRECT,no-resolve
- IP-CIDR6,::1/128,DIRECT,no-resolve
- IP-CIDR6,fc00::/7,DIRECT,no-resolve
- RULE-SET,domestic-domains,DIRECT
- GEOIP,CN,DIRECT,no-resolve
- MATCH,Overseas Proxy
Rule file: rules/domestic-domains.yaml
payload:
- '+.qq.com'
- '+.taobao.com'
- '+.jd.com'
For a mihomo rule set with domain behavior, +.qq.com matches the domain and its subdomains. Single quotes preserve the domain pattern as written. Don't use DOMAIN-SUFFIX,qq.com,DIRECT here; that isn't the expected format for entries in this file.
behavior: domain: Stores domain match patterns, suitable for lists of domains to route directly or through a proxy.behavior: ipcidr: Stores IP ranges; don't mix in domain entries.behavior: classical: Stores rule expressions such asDOMAIN-SUFFIX,qq.com. In most cases, don't add a policy name at the end of each entry.
Interpret relative paths based on the core's working directory and the client's file-access restrictions; they aren't necessarily relative to the subscription file you're editing. Mobile clients may also restrict file imports and storage locations. After saving, make sure the rule set loads successfully and the number of entries looks right, then reconnect to test. Local type: file sources aren't downloaded from the internet and don't need an interval for remote updates.
If you switch to a remote rule set, first check the source file's behavior and format. A plain-text domain list can't be read as a YAML file, and a binary file made for another core can't be used directly by a version that doesn't support that format.
5. DNS, System Proxy, and TUN: What Information Can the Rules See?
A rule failing to match doesn't necessarily mean its syntax is wrong. Start by checking what information the client receives when the connection arrives. HTTP proxy requests can usually provide the destination hostname; some SOCKS apps resolve locally and send only the IP to the client. Even when both connect to the same site, the latter may not match a domain-suffix rule directly.
Three common limitations
- Local DNS resolution happens before the proxy. When an app sends only the destination IP, domain rules have no hostname to match. Cores with sniffing support may recover the domain for some protocols, but can't guarantee the hostname can be identified for every connection.
- DNS interception is incomplete. TUN DNS hijacking doesn't mean all encrypted DNS can be identified. An app's built-in DoH uses HTTPS and can't be treated as an ordinary UDP port 53 query.
- IPv4 and IPv6 may take different routes. A domain can return both A and AAAA records, and the two connections may use different addresses. Testing IPv4 alone doesn't prove that an IPv6 connection will use the same policy.
TUN captures IP traffic that meets the routing conditions; it doesn't automatically fix an incorrect rule list. If both the system proxy and TUN are enabled, check which entry point the test app actually uses. Corporate VPNs, container networks, and virtual machine networks can also change routing. If an intranet site is unreachable, check for overlapping IP ranges before adding a direct-connect rule.
Test DNS and outbound connectivity separately: a successful lookup only confirms that an address was returned, not that the destination port is reachable. A DIRECT match doesn't prove the direct route is available either. If a domain resolves to an IP outside mainland China and GEOIP excludes it, that's the result of applying the current data; it doesn't necessarily indicate a rule-engine failure.
6. Troubleshooting Rule Matches and Test Cases
Change one variable at a time. Record the failed connection's domain, destination IP, port, matched rule, and actual policy before deciding whether to change the domain list or the IP rule. The table below shows expected matches, not measured connection speeds; verify each result with your current config and network.
| Test case | Expected match | What to check |
|---|---|---|
192.168.1.1:80 | Private IP rule → DIRECT | Test only if this address is your local gateway |
www.qq.com:443 | Domain suffix or rule set → DIRECT | Whether the connection log includes the domain |
| CN IP not in the domain list | GEOIP → DIRECT | Whether the connection has a matchable IP |
| Other new connections | MATCH → Overseas Proxy | Node or policy actually selected in the group |
Find the cause in six steps—don't reinstall the client first
- Check the active config and mode. Confirm the current config name, make sure the client is in rule mode, and inspect the running rule list—not just the file open in the editor.
- Confirm the connection reaches the client. Look for the request in the connection panel. If there's no record at all, check the system proxy, TUN routing, or the app's own proxy settings first.
- Check the first matching rule. If a broad domain rule matches too early, move the more specific exception above it. If an earlier MATCH rule catches the connection, fix its position first.
- Check DNS results and the database. Review the destination IP, whether it's IPv4 or IPv6, and the geodata loading logs. With
no-resolve, check whether the rule missed because no usable IP was available. - Check that the rule set loaded. An incorrect path, bad indentation, or format mismatch can make a provider unavailable. First confirm the file is readable and its entries load, then check the position of RULE-SET.
- Reconnect. Close the target app's existing session or disconnect the relevant connection in the client, then try again. Existing long-lived connections usually won't switch to a different outbound automatically when the rule file changes.
Once you've confirmed the match, check what the proxy group actually selected. A rule matching “Overseas Proxy” only means the connection was handed to that group; if the group selected DIRECT, the connection still goes direct. Conversely, if a direct rule matches but the page won't load, the issue may be DNS, the destination service, or your local network—not necessarily a routing failure.