Advanced Configuration Guide · mihomo Core

Clash Advanced Configuration Guide

This page is a systematic reference for Clash Verge, breaking advanced configuration around the mihomo core into eight chapters: config layering, proxy groups, rule providers, DNS, TUN and Fake-IP, domain sniffing, local overrides, and the external controller. Each chapter follows the pattern of config section, parameter explanation, practical example, and troubleshooting branches, so you can consult it side by side while editing. If this is your first time setting up a client, finish the main path in the Getting Started guide first, then come back here to go deeper chapter by chapter.

8 chapters YAML examples mihomo core About 30 min read

Config Layering and Edit Entry Points

Before you start tweaking individual settings, it helps to know which layers make up an effective configuration. Once you understand the layering, you'll know whether your changes will be overwritten by a subscription update, and which layer your custom content belongs in.

Priority of the Four Config Layers

Clash Verge builds its runtime configuration from four layers, in ascending order:

  • Subscription config: the raw YAML pulled from your subscription URL, or a local file you imported manually. This layer is maintained by your provider or by you, and every subscription update replaces it wholesale.
  • Local config: the built-in base snippet shipped with the client, which usually only provides fields like ports and mode. It's editable but of limited use.
  • Override config: a YAML file that applies incremental changes to the subscription config, with support for prepend / append merge directives. Overrides survive subscription updates, making them the most important customization layer for long-term use.
  • Script config: a piece of JavaScript that programmatically modifies the final config after merging, suited to cases that need conditional logic or bulk generation.

Final runtime config = subscription → local → override → script, with each layer overwriting same-named keys from the layer below. When you see a change that "didn't take effect", walk this chain to check whether a higher layer has overwritten the value.

Config File Locations and Backups

Default paths by platform:

  • Windows:%APPDATA%\clash-verge\profiles\
  • macOS:~/Library/Application Support/io.github.clash-verge-rev.clash-verge-rev/profiles/
  • Linux:~/.config/clash-verge/profiles/

Each subscription has its own directory named after a UUID. Inside it, config.yaml is the raw pulled content, while merge.yaml and script.js hold the override and script respectively. To back up, just copy the whole profiles directory. When you need to make manual adjustments, open the subscription in the Profiles page and click Edit to enter the override or script, rather than editing the downloaded config.yaml directly, because the next subscription update will wipe direct edits.

Quick Reference for Common Top-Level Fields

These fields are read directly by the mihomo core and belong at the top level of any config:

Example · Common Top-Level Fields

port: 7890              # HTTP proxy port
socks-port: 7891        # SOCKS5 proxy port
allow-lan: false        # Allow LAN devices to connect
mode: rule              # rule / global / direct
log-level: info         # silent / error / warning / info / debug
ipv6: false             # Handle IPv6 traffic
external-controller: 127.0.0.1:9090
secret: ""              # Controller API access token
  • mode: rule routes by rules; global sends everything through the proxy; direct connects everything directly. Keep it on rule for daily use.
  • Setting log-level to debug makes the log show which rule each connection matched, which is very useful for troubleshooting. Remember to set it back to info when you're done.
  • With allow-lan enabled, phones and tablets on the same LAN can manually point their proxy at this computer, as long as the system firewall allows the relevant ports.

Editing and Validation

After editing YAML, click the debug button on the Profiles page, or just check the log window for parse errors. There are three common error types: indentation using tabs (spaces are required), a missing space after a colon, and an unclosed quote. mihomo reports errors with exact line numbers, so you can trace back by line. For a section-by-section breakdown of the whole file, see Clash Config File YAML Structure Explained Section by Section.

This page doesn't repeat the basics of downloading, installing, importing a subscription, or enabling the system proxy; that's the job of the Getting Started guide. This page assumes you already have a working subscription and focuses on making the config smoother and more controllable. To download the client, see the Download page.

Proxy Group Types in Practice

Proxy groups decide which node gets selected and by what logic. Rules usually point to a proxy group rather than a single node, so once your groups are well configured, the rules layer becomes much simpler.

Five Built-in Types

select: manual selection. Whatever you click in the dashboard is what gets used, ideal for groups like "main node" that you want to switch at any time.

Example · select Group

- name: Main
  type: select
  proxies:
    - Hong Kong 01
    - Japan 01
    - Direct

url-test: automatic latency testing. It sends test requests to all members on a timer and picks the node with the lowest latency. interval is the test interval in seconds, and tolerance is the tolerance in milliseconds: when the latency difference between two nodes is below the tolerance, the current node is kept to avoid flapping.

fallback: uses nodes in list order and automatically switches to the next one when the current node becomes unavailable. Good for scenarios where you prefer one line and only want to switch when it actually fails.

load-balance: spreads connections across multiple nodes. strategy supports consistent-hashing (the same domain always goes to the same node, best compatibility), round-robin (take turns), and sticky (session stickiness). Use this group for downloads and high-traffic scenarios to saturate multiple lines.

relay: chained proxying. Traffic passes through each hop in group order, commonly used for "exit" combinations. Relay has limited protocol support, and some provider nodes don't support chained forwarding, so verify each hop in the dashboard before enabling it.

Special Groups and Nesting

DIRECT and REJECT aren't proxy groups, but they can appear in the proxies list to mean direct connection and rejection respectively. Proxy groups can be nested: an outer group references an inner group, and rules only need to point at the outermost group. mihomo also supports include-all: true to automatically include every node in the config, and include-other-group to reference members of other groups. When subscription nodes change often, these two parameters save a lot of maintenance.

A Practical Template Set

Example · Streaming / Gaming / Download Group Template

proxy-groups:
  - name: Streaming
    type: url-test
    proxies: [Hong Kong 01, Hong Kong 02, Japan 01]
    url: http://www.gstatic.com/generate_204
    interval: 300
    tolerance: 50
  - name: Gaming
    type: fallback
    proxies: [Hong Kong 01, Japan 01, Direct]
  - name: Download
    type: load-balance
    proxies: [Hong Kong 01, Hong Kong 02]
    strategy: consistent-hashing
  - name: Main
    type: select
    proxies: [Streaming, Gaming, Download, Direct]
  • The streaming group uses url-test to pick the fastest line automatically. Give tolerance 50ms to prevent switching on a few milliseconds of difference, which would interrupt playback.
  • The gaming group uses fallback: with url-test, a slightly higher latency on the preferred line would trigger a switch even though the line is still working; fallback only switches when the line is truly unavailable, which is friendlier to long-lived connections.
  • Use http://www.gstatic.com/generate_204 as the test URL; it returns 204 and generates no traffic. If you can't reach it, switch to http://cp.cloudflare.com/generate_204.

Common Mistakes

  • Setting tolerance to 0: a 1ms latency difference triggers a switch, which causes frequent disconnects in short-connection scenarios.
  • Piling dozens of nodes into a select group: the dashboard selection list becomes very long. Use an automatic group to hold the nodes, and have select reference the group instead.
  • Ignoring the default lazy setting: the preferred node isn't tested immediately, so the latency shown in the dashboard is a placeholder. If you need real numbers right away, trigger a test manually.
  • Inconsistent group name casing: rule references to group names are case-sensitive. A wrong case doesn't raise an error, and traffic silently falls into the fallback policy.

Managing Rule Providers as Subscriptions

Rules are the part of a config that bloats the fastest. Writing hundreds of rules into the main config makes it hard to read, and the next subscription update overwrites them. Rule providers split rules into separate files that update independently, leaving only references in the main config.

Three Rule Provider Behaviors

behavior determines how a rule provider is parsed:

  • domain: the content is a domain list, one domain per line, with + prefix meaning suffix matching. Good for self-maintained site lists.
  • ipcidr: the content is IPs or CIDR ranges, used for IP rules.
  • classical: full rule syntax, one DOMAIN,xxx,policy or IP-CIDR,1.2.3.0/24,policy per line. The most flexible option.

Remote and Local Rule Providers

Example · rule-providers with Both Source Types

rule-providers:
  geosite:
    type: http
    behavior: domain
    format: yaml
    url: "https://example.com/rules/geosite.yaml"
    path: ./rules/geosite.yaml
    interval: 86400
  my-custom:
    type: file
    behavior: classical
    format: text
    path: ./rules/custom.txt
  • type: http means remote fetching, and interval is the auto-update interval in seconds; 86400 means once a day. path is the local cache path; if fetching fails, the core keeps working with the cache.
  • type: file means a local file, suitable for rules you maintain yourself; it doesn't participate in remote updates.
  • With format: yaml, the content must be written as a YAML list; with format: text, one entry per line, closer to plain-text habits.

Referencing Providers in rules

Example · RULE-SET References

rules:
  - RULE-SET,geosite,Streaming
  - RULE-SET,my-custom,Direct
  - MATCH,Main

The first argument of RULE-SET is the provider name, and the second is the proxy group to match. If the provider uses classical behavior and each rule already carries its own policy, the second argument can be omitted.

Updates and Maintenance

  • Remote rule providers can be updated individually from the Subscriptions page, or you can wait for interval to expire and let them update automatically.
  • Subscription updates don't touch rule providers: they're independent files, which is exactly the core benefit of splitting rules out of the main config.
  • Don't put anything beyond the list in a rule provider file. In format: yaml mode the top level must be a list; a wrong format makes the entire provider fail to load, all its rules go dead, and traffic falls into the fallback policy.
  • To check whether a rule provider is active, search the log window for rule-provider to see load and update records; debug logs show which rule each connection matched.

Routing Strategy

A common approach is three layers: domain rule provider + IP rule provider + fallback. First REJECT ads and tracking domains, then point streaming domains at the streaming group, then direct-connect domestic domains, and finally MATCH to the main group. mihomo matches top to bottom and the first hit wins, so REJECT and direct rules must come first.

A dead rule provider URL doesn't affect the main subscription, but it silently disables the corresponding rules. When troubleshooting subscription issues, first check whether the main subscription can be fetched, then whether the rule provider URL is reachable; the two are independent. For a full self-check procedure, see Clash Subscription Failure and Parse Error Checklist.

DNS Configuration Tuning

DNS is the dividing line for routing quality. The resolution result determines whether a connection goes through the proxy or direct, and misconfiguration produces three kinds of problems: traffic that should be proxied goes direct, DNS leaks, and resolution timeouts.

Basic Structure of the dns Section

Example · Domestic DoH Primary + Foreign DoH Fallback

dns:
  enable: true
  listen: 0.0.0.0:1053
  ipv6: false
  enhanced-mode: fake-ip
  default-nameserver:
    - 223.5.5.5
    - 119.29.29.29
  nameserver:
    - https://dns.alidns.com/dns-query
    - https://doh.pub/dns-query
  fallback:
    - https://1.1.1.1/dns-query
    - https://dns.google/dns-query
  fallback-filter:
    geoip: true
    geosite: geolocation-!cn
  • default-nameserver is only used to resolve the hostnames of the DNS servers themselves, so it must contain IP addresses. Otherwise startup stalls on DNS resolution.
  • nameserver is the primary resolution channel. Domestic DoH providers (Aliyun, Tencent) are fast and resolve domestic domains accurately.
  • fallback is the backup channel, used when the primary channel's result is judged abnormal by fallback-filter. geoip: true with geosite: geolocation-!cn means: when the IP returned by nameserver is foreign and the domain isn't a domestic domain, re-resolve using fallback. This is the standard way to prevent domestic DNS pollution of foreign domain resolution.
  • With ipv6: false, mihomo only requests A records even if the system has IPv6. Turn it on only if you need an IPv6 exit.

Choosing enhanced-mode

fake-ip: domains aren't really resolved; they're mapped directly to a virtual IP in fake-ip-range (default 198.18.0.1/16). Apps connect to the virtual IP, and the core restores the domain during forwarding to do rule matching. It's fast, prevents DNS leaks, and is the recommended choice for TUN mode.

redir-host: resolves for real and returns the result, with rule matching using the real IP. Compatibility is more stable, but every connection has to wait for resolution to finish, and the result can be polluted.

Hijacking and Caching

dns-hijack is configured in the tun section; it hijacks DNS requests sent to port 53 and redirects them to the core's own DNS service:

Example · DNS Hijacking and Caching

tun:
  dns-hijack:
    - any:53

cache:
  enabled: true
  size: 4096
  ttl: 300

The cache section caches resolution results to reduce repeated queries. ttl is the cache duration in seconds: too short and caching is pointless, too long and latency increases after a domain changes IP. 300 seconds is a common value.

Troubleshooting Branches

  • Web pages often take several seconds to load: check whether nameserver uses DoH and whether the network can reach the DoH server directly. In some network environments, foreign DoH is unreliable, so add backup DoH servers to the nameserver list.
  • Domestic sites resolving to foreign IPs: the geosite rule in fallback-filter isn't taking effect. Confirm the core can fetch the geosite data source, or specify geox-url manually.
  • The dns section from the subscription conflicts with your override: overwrite the entire dns key in the override instead of merging field by field.

For complete field explanations of nameserver and fallback, the filtering logic of fallback-filter, and why DNS hijacking only works together with Fake-IP, there's a dedicated article: Clash DNS Configuration Explained: How to Fill In nameserver, fallback, and DNS Hijacking. You can read it alongside this chapter.

TUN Mode and Fake-IP

System proxy only takes over apps that actively read proxy settings; command-line tools, games, and UDP traffic often bypass it. TUN mode creates a virtual network interface in the system and pulls all IP traffic into the core, which is the real answer to "global takeover". Fake-IP is the DNS and rule-matching partner for TUN mode.

System Proxy vs. TUN

System proxy works by modifying system settings to tell apps "send traffic to 127.0.0.1:7890". Apps that don't read this setting simply bypass it. TUN mode works at the IP layer: the virtual interface receives all outbound IP packets and doesn't depend on app cooperation. The differences show up directly in:

  • Command-line tools, curl, and git don't read the system proxy by default. In TUN mode you don't need to export anything one by one.
  • For games and UDP apps, system proxy is basically useless; TUN can take them over.
  • TUN takes over IP packets. Apps send DNS queries first and then establish TCP connections, so TUN must be paired with DNS hijacking. Otherwise domain resolution still goes through the system DNS and rule matching never sees the domain.

Complete tun Section Configuration

Example · tun Section

tun:
  enable: true
  stack: mixed
  auto-route: true
  auto-detect-interface: true
  dns-hijack:
    - any:53
  strict-route: true
  • stack: the packet processing stack. system has the best compatibility but average performance; gvisor performs well with low resource usage but isn't compatible with some older systems; mixed lets the core choose automatically per platform, and is recommended for new setups.
  • auto-route: automatically adds routes so the virtual interface takes over the default route. It must stay enabled.
  • auto-detect-interface: automatically detects the outbound interface. Recommended in multi-NIC environments (wired + wireless + VMs), otherwise the core may pick the wrong interface and cut off your network.
  • strict-route: on Windows, enabling it strictly takes over the routing table, which prevents some traffic from leaking out, but it also conflicts more easily with VPNs and virtual adapters. When troubleshooting, try turning it off first.

How Fake-IP Works

With enhanced-mode: fake-ip enabled, when the core receives a domain resolution request it doesn't query a real DNS server. Instead it returns a virtual IP from fake-ip-range (default 198.18.0.1/16) and records the domain-to-virtual-IP mapping in memory. When an app connects to the virtual IP, the core restores the domain from the mapping and runs rule matching. Two benefits: connections no longer wait for a real DNS round trip, so they establish faster; and rule matching is always based on the domain, so IP pollution can't steer it astray.

fake-ip-filter excludes domains that don't need virtual IPs, typically local services and sites that need real IP direct connections:

Example · fake-ip Range and Filter

dns:
  fake-ip-range: 198.18.0.1/16
  fake-ip-filter:
    - "*.lan"
    - "*.local"
    - "stun.*"

Platform-Specific Notes

  • Windows: the core needs to run in service mode. Check "Install service" during installation, or enable service mode later in settings; the system firewall must allow the core process.
  • macOS: enabling TUN requires administrator authorization, and the first enable will show a password prompt. System updates may invalidate the authorization; just toggle TUN off and on again.
  • Linux: requires cap_net_admin capability. When running as a regular user, make sure the binary has the corresponding capability, or start it via a systemd service.
  • Android: clients like Clash Meta for Android also support TUN. They need the system VPN permission, and TUN is mutually exclusive with the system proxy as two working modes.

Troubleshooting Branches

  • Complete network loss after enabling TUN: first turn off strict-route, then switch to stack: system, and check whether auto-detect-interface selected the correct interface.
  • Domestic sites work but foreign sites time out: the TUN and DNS hijacking combination is broken. Confirm the tun section has dns-hijack: [any:53] and dns.enable is true.
  • Some apps get their connections reset: the app may be validating the destination IP. Add that domain to fake-ip-filter so it uses real resolution.

For the full differences between the two modes in terms of traffic takeover layer, and which scenarios each suits, read TUN Mode vs. System Proxy: At Which Layer Is Traffic Taken Over.

Domain Sniffing

TUN mode takes over IP packets. When an app connects directly to an IP, or connects to an already-resolved address, the core never sees the domain and rule matching can only rely on IP. Domain sniffing recognizes the domain from the connection content, filling this gap.

When Do You Need Sniffing

  • Apps with built-in DNS resolution (some game clients, some apps that connect directly to IPs): when traffic reaches TUN, there's only an IP, no domain.
  • QUIC / HTTP3 connections: UDP traffic has no traditional DNS query to hijack.
  • Connection reuse: subsequent requests on the same TCP connection don't send another DNS query, so rules can only match by IP.

Example

Example · sniffing Section

sniffing:
  enable: true
  override-destination: false
  force-doman: true
  parse-pure-ip: true
  skip-dest-address:
    - 192.168.0.0/16
    - 198.18.0.1/16
  • enable: master switch.
  • override-destination: whether to rewrite the connection destination to the domain after sniffing. Enabling it makes rule matching more accurate, but some protocols (like QUIC) don't support rewriting. It's recommended to keep it false and let the core rewrite only when it can do so safely.
  • force-doman: forces rule matching to use the sniffed domain even if the config contains IP rules.
  • parse-pure-ip: also tries to extract a domain from pure IP connections (via TLS SNI and similar fields).
  • skip-dest-address: skips destination subnets that don't need sniffing. Usually you exclude private subnets and the fake-ip-range to avoid pointless sniffing of virtual IPs.

Order of Sniffing and Rule Matching

When a connection arrives, the matching order is: first check whether the connection hits a Fake-IP mapping (if so, use the domain directly), then check whether it's skipped, then try sniffing. After a domain is sniffed out, matching proceeds in the order domain rules → IP rules → fallback. So DOMAIN rules cover a wider range once sniffing is enabled; IP rules still work but come after domain rules.

Notes

  • Sniffing only reads the first few packets of a connection, so the performance impact is tiny. However, with override-destination enabled, some apps may error out because the destination address was rewritten. When you hit "this app can't connect with TUN on", turn this option off first.
  • Plaintext non-TLS HTTP traffic can be sniffed via the Host header; TLS traffic via SNI; QUIC traffic via the SNI in CHLO. But UDP sessions have no stable "connection" concept, and some implementations limit the sniffing scope.
  • Relationship with Fake-IP: Fake-IP already gets the domain at the DNS layer, so sniffing mainly covers traffic that didn't go through DNS hijacking. Running both isn't duplicate work; they cover different entry points.

Sniffing isn't a cure-all: encrypted traffic that carries no domain (some P2P, encrypted tunnels) can't be sniffed. Such traffic can only be handled by IP rules or the fallback policy. In these cases, writing the destination IP ranges into IP rules is more reliable.

Local Overrides and Multi-Subscription Merging

If you edit the config pulled by a subscription directly, one update wipes everything. Overrides (merge) are the incremental modification layer Clash Verge provides: after a subscription update, the changes in the override are automatically reapplied. When multiple subscriptions coexist, overrides can also merge nodes from different subscriptions into the same proxy group.

Override Syntax

The override file is itself YAML and supports two kinds of directives:

  • Key overwrite: write the target key and value directly to replace the same-named key in the subscription. Use overwrites for whole-section rewrites like DNS or TUN.
  • Append directives: keys prefixed with prepend- and append- insert content before or after the corresponding list in the subscription. Supported forms include prepend-proxies, append-proxies, prepend-proxy-groups, append-proxy-groups, prepend-rules, and append-rules.

Example · Append Directives

prepend-rules:
  - DOMAIN-SUFFIX,company.com,Direct
append-rules:
  - GEOIP,CN,Direct
  - MATCH,Main
prepend-proxy-groups:
  - name: Work
    type: select
    proxies:
      - Company Leased Line
      - Main

A Complete Override Example

Example · Merge Nodes + Custom Rules + Fixed DNS

# Override: merge nodes from two subscriptions, append custom rules, fix DNS
prepend-proxy-groups:
  - name: All Nodes
    type: select
    proxies:
      - Subscription A Nodes
      - Subscription B Nodes
      - Direct
prepend-rules:
  - DOMAIN-SUFFIX,corp.example.com,Direct
  - RULE-SET,my-custom,Main
append-rules:
  - MATCH,All Nodes
dns:
  enable: true
  enhanced-mode: fake-ip
  nameserver:
    - https://dns.alidns.com/dns-query

Note: writing a dns key in the override replaces the subscription's entire dns section. If you want to keep the subscription's DNS and change just one part, either copy the subscription's full dns section over and modify it, or use prepend-dns/append-dns to append to lists. But the dns section's fields are nested objects and append directives only work on lists, so overwriting the whole section is the safest approach.

Merging Multiple Subscriptions

  • Add multiple subscriptions on the Profiles page; each one updates independently without interfering with the others.
  • Use a group like "All Nodes" to collect nodes from multiple subscriptions, via include-all or by referencing group names in the override's proxies.
  • When you switch subscriptions, the currently active profile switches wholesale, and overrides and scripts always stack on top of the current subscription. So when an override references node names, make sure every subscription contains a node with that name; otherwise the group will reference empty members.
  • Script mode (script.js) suits more complex merge logic, such as auto-grouping by subscription name prefix or filtering out nodes whose names contain "expired". The script runs after the override, receives the config object, and returns the modified object.

Maintenance Tips

  • Organize override content by purpose with comments marking "Rules", "Proxy Groups", and "DNS", so it's still readable six months later.
  • After each subscription update, check the log for merge failure messages to confirm the override syntax isn't conflicting with the subscription content.
  • Prefer rule providers for rules; keep only a few personalized rules in the override so it doesn't balloon into a second main config.

If the subscription itself fails to fetch or has invalid formatting, overrides won't take effect. The troubleshooting order for subscription issues is: link reachability → response format → YAML syntax → core field compatibility. See Clash Subscription Failure and Parse Error Checklist for details.

External Controller Dashboard

For daily node switching and connection viewing, the client UI is enough. But for batch operations, checking rule hits, and remote management, you need mihomo's external controller API. The dashboard talks to the core over HTTP; once external-controller is configured, it's ready to use.

Basic Configuration

Example · External Controller Listen Address and Token

external-controller: 127.0.0.1:9090
secret: "your-long-random-token"
  • The external-controller format is "address:port". For local-only access, use 127.0.0.1:9090. To access from the LAN, change it to 0.0.0.0:9090 and set up the firewall, but don't expose it directly to the public internet: the dashboard can switch proxies and read connection info, so an exposed port is effectively handing proxy control to anyone.
  • secret is the access token; the dashboard and API requests must all carry it. Use a sufficiently long random string; Verge's settings page can also generate and save a secret.
  • After changing external-controller or secret, you need to restart the core for it to take effect.

Common Dashboards

The mihomo official repository provides dashboards like Yacd and MetaXD. After building, place them in the ui folder next to the core binary, and visit http://127.0.0.1:9090/ui in a browser to open them. On first open, the dashboard asks for the backend address and secret. Verge's Settings → External Control also has a dashboard entry that works out of the box.

Common REST API Endpoints

Method Path Purpose
GET/proxiesRead all proxies and proxy group states
PUT/proxies/{name}Switch the selected node of a proxy group
GET/rulesRead the rules list and hit counts
GET/connectionsView current connections and their matched rules
DELETE/connectionsClose all connections
GET/configsRead runtime config
PUT/configsModify runtime config, such as mode
GET/providers/proxiesRead subscription and provider status

Example · curl Read and Switch

curl -H "Authorization: Bearer your-long-random-token" \
  http://127.0.0.1:9090/proxies

curl -X PUT -H "Authorization: Bearer your-long-random-token" \
  -d '{"name":"Hong Kong 01"}' \
  http://127.0.0.1:9090/proxies/Main
  • Use GET /connections to troubleshoot "why did this connection go direct": the response includes rule and rulePayload fields that show exactly which rule was matched.
  • PUT /configs is handy for quickly switching modes: {"mode":"global"} gives temporary global proxying; switch back to rule when done.
  • All endpoints require an Authorization header in the format Bearer <secret>.

Security Recommendations

  • Have the dashboard and API listen only on loopback, or access machines outside the LAN through an SSH tunnel.
  • Don't put the secret in notes that get synced, and don't let it appear in plaintext repeatedly in shell history. Use environment variables or the client's built-in secret management.
  • Periodically check mode with GET /configs. If you find mode changed to global and it wasn't you, suspect port exposure first, then rotate the secret.

The external controller API is provided by the core and is independent of the frontend client; both desktop and mobile clients that support the mihomo core can enable it. For the package list and top picks, see the Download page. On desktop, Clash Plus is the top recommendation; on mobile, Clash Plus is also the priority.

Next: Continue by Scenario

When you hit a specific error, start with FAQ and look it up by category. Windows installation pitfalls are collected in Clash Verge Windows Installation and Setup Guide. More practical articles are in Tech Notes. To download a client, go to the Clash Client Download page.