Configuration Featured Clash Beginner Guide Clash vs VPN Proxy Basics

Clash TUN Setup for Developers: Route Terminal Traffic Automatically

October 10, 2026 Updated October 10, 2026 Approx. 12 min read

Why Developers Use TUN Mode

Developer tools often make network connections outside the browser. Git may contact a hosting service over HTTPS or SSH, Homebrew may fetch package metadata and files from several domains, and command-line tools may open their own sockets without consulting your desktop browser’s proxy settings. That is why a browser can work through Clash while a terminal command times out or connects from an unexpected network.

Clash TUN mode addresses this gap by creating a virtual network interface and routing eligible system traffic through the Clash core. Instead of relying on every application to understand an HTTP or SOCKS proxy, the operating system sends traffic to the TUN interface, where Clash can apply DNS handling and routing rules. For a developer, the practical goal is not necessarily to proxy everything. It is to make terminal connections follow the same deliberate routing policy as other applications, with a clear way to verify what happened.

This guide focuses on desktop clients powered by Mihomo, including Clash Verge Rev and other clients that expose TUN settings. Labels and menu locations vary by version, and some features depend on the operating system. Treat the YAML examples as configuration patterns: check your client’s documentation and validate the merged configuration before applying changes.

What You Will Set Up

A working TUN interface, predictable rules for terminal destinations, and a repeatable test that distinguishes a routing problem from an application or DNS problem.

1Prepare the Client and Check Permissions

Before enabling TUN, confirm that the active profile is usable in ordinary proxy mode. Select a working proxy group, check that the core is running, and test a website from a browser or the client’s connection test. TUN cannot repair an unavailable node, an expired subscription, or a profile that fails to parse. Keeping this baseline makes it much easier to identify whether a later failure comes from the virtual interface or from the proxy itself.

Next, confirm that the client uses a core with TUN support. In current setups, this commonly means a compatible Mihomo core. Some applications bundle their own core, while others let you choose or update it. If the client reports an unsupported TUN option, update the application or core using its official release channel rather than copying an arbitrary binary into the installation directory.

Grant the Required System Permission

Creating or configuring a virtual network interface requires operating-system permission. On Windows, the client may request administrator approval or install a service or driver. Approve only a prompt from the client you intended to install; if the interface cannot be created, close the client and relaunch it with the appropriate elevated permission, following the client’s own instructions.

On macOS, the system can ask for authorization to add a network extension or VPN configuration. Approve the request in the system settings if it matches the client and action you initiated. A macOS account password may be required. On Linux, the client may need access to TUN devices and network administration capabilities. The exact setup depends on the distribution and packaging method; avoid granting broad permanent privileges to unrelated processes just to suppress an error message.

Check for Existing Network Tools

Another VPN, security product, container network, or second proxy client may install routes or virtual adapters of its own. If TUN activation causes a sudden loss of connectivity, disable competing network tools temporarily and retest before changing DNS or firewall settings.

Find the TUN controls in the client’s settings, often under a section named TUN, Network, or Advanced. Enable TUN and any required service or stack option, then apply the change. The client may need to restart the core or request permission. Do not enable every advanced toggle at once: change one setting, apply it, and check whether the interface starts. This keeps troubleshooting focused and makes it easier to undo a problematic change.

2Configure TUN and Make Routing Intent Explicit

A minimal Mihomo TUN configuration can look like the following. It is an example, not a universal drop-in profile. If your client manages TUN through its graphical settings, use the client’s controls or its documented override mechanism instead of adding a second conflicting configuration block.

tun: enable: true stack: mixed auto-route: true auto-detect-interface: true mode: rule

enable turns on the TUN interface. stack selects the network stack used by the core; available choices and performance depend on the core build and platform. auto-route asks Mihomo to install routes for captured traffic, while auto-detect-interface helps the core select the outbound network interface. These options do not replace a valid proxy group, DNS configuration, or routing rules. When using a managed profile, check whether the client merges user overrides with subscription settings and whether a profile update can replace your edits.

Route Terminal Destinations Deliberately

TUN captures packets, but rules determine the outbound policy. In rule mode, a request can still go DIRECT, use a selected proxy group, or match another policy, depending on the profile’s rules and their order. For example, a profile may have a broad final rule that sends unmatched traffic DIRECT. Turning on TUN alone does not mean every terminal connection uses a proxy node.

For Git hosting or package registries that should use a proxy, place specific rules before broad catch-all rules. Use the policy-group name that actually exists in your profile; the name below is illustrative.

rules: - DOMAIN-SUFFIX,github.com,Proxy - DOMAIN-SUFFIX,githubusercontent.com,Proxy - DOMAIN-SUFFIX,brew.sh,Proxy - DOMAIN-SUFFIX,ghcr.io,Proxy - MATCH,DIRECT

Rules are matched from top to bottom, so earlier rules take precedence. A domain rule generally helps when the client can associate the connection with a hostname; for connections made directly to an IP address, an IP or CIDR rule may be necessary. Avoid adding large, speculative IP ranges for a service: hosting providers use shared and changing infrastructure, and a broad rule can reroute unrelated work traffic. Start with the exact domains visible in the connection log, then add only what your workflow requires.

Some profiles use rule providers or policy groups with different names, and a subscription may place its own rules ahead of your local rules. Confirm the effective rule order in the client or the generated configuration. If your intention is to send all unmatched traffic through a proxy, change the final policy only after considering local networks, company resources, and services that should remain direct.

Keep Rules Narrow

A targeted domain rule is easier to audit than forcing every process through one node. Preserve DIRECT access for private networks and internal development services unless your organization specifically requires otherwise.

3Verify Git, SSH, and Package Manager Traffic

Test one destination at a time and keep the Clash connection log open. A useful test has three parts: confirm that the command can connect, inspect the route or rule reported by the client, and compare the observed public address with the expected result. A successful command by itself does not prove that it used the intended proxy; it may have matched DIRECT or used an application-level proxy setting instead.

Check for Old Shell Proxy Settings

Before testing TUN, inspect the current terminal session for proxy environment variables. These can direct command-line applications through an HTTP or SOCKS proxy independently of TUN and may hide a broken TUN route.

# macOS / Linux shells env | grep -i proxy # Remove common variables from this shell for a clean TUN test unset http_proxy https_proxy all_proxy unset HTTP_PROXY HTTPS_PROXY ALL_PROXY

On PowerShell, inspect the environment with Get-ChildItem Env:*proxy*. To clear a variable for the current session, use Remove-Item Env:HTTP_PROXY and repeat for the other variables that are set. These commands affect only the current shell session; they do not remove proxy settings stored in a shell profile or application configuration. Reopen a clean terminal if you are unsure which settings are active.

Test HTTP and Git

First make a simple HTTPS request to a destination covered by your rules. Replace the hostname with one relevant to your workflow.

curl -I --connect-timeout 10 https://github.com curl -sS --connect-timeout 10 https://api.ipify.org

The first command checks whether an HTTPS connection completes; the second prints the public IP address seen by that service. Compare the result with the expected egress for your selected route, and verify the matching destination in Clash’s connection log. Public IP lookup services reveal network information to the service you contact, so use an endpoint you trust and do not include sensitive data in a diagnostic request.

Then test Git without changing its configuration:

git ls-remote https://github.com/OWNER/REPOSITORY.git

Use a repository you are authorized to access. If this command works while the browser works but no matching connection appears in Clash, check whether Git has an explicit proxy configured. Inspect the relevant setting with git config --show-origin --get-regexp 'http\..*proxy|http.proxy'. Git settings can be global, local to a repository, or inherited from a system configuration. Remove or update a setting only if you understand why it was added; otherwise it can make results differ between projects.

Test SSH and Homebrew

SSH is not HTTP. It usually connects to a hostname and port directly, so an HTTP proxy variable does not automatically configure SSH. Test the actual SSH route with a verbose connection attempt:

Read the output for the resolved hostname, selected address, and connection result. A successful network connection may still end with an authentication message because the hosting service does not provide an interactive shell; distinguish that from a timeout or refused connection. If the destination is not routed as expected, inspect the Clash log and your SSH configuration. A deliberate SSH proxy command can be useful in special environments, but it is a separate per-client setup and should not be added as a substitute for diagnosing TUN.

For Homebrew, use a read-only or low-impact operation first, such as brew update, and watch the connection log while it runs. Package managers may contact several hosts, including mirrors, code hosting sites, and release storage domains. If one request fails, identify its actual hostname in the terminal output or client log rather than assuming all Homebrew traffic uses a single domain. Avoid running a full installation as the first connectivity test.

4Troubleshoot Common Failures and Keep the Setup Reliable

If every command fails immediately after TUN is enabled, first turn TUN off and confirm ordinary connectivity. Then enable it again and check the client’s status, permission prompts, core log, and operating-system network interface. A missing or stopped interface points toward startup, privilege, or driver setup; a running interface with failed requests points more often toward routing, DNS, or an unreachable proxy node.

If the browser works but Git or Homebrew does not, check whether the terminal has stale proxy variables, whether the application has its own proxy setting, and whether its destination matches a rule that sends traffic somewhere unexpected. Review the connection log during the command, not several minutes afterward. A connection shown as DIRECT may be behaving exactly as the rules specify even when you expected a proxy.

If a domain resolves but the connection times out, distinguish DNS resolution from the subsequent TCP or UDP connection. Check whether the rule uses the hostname you expected, whether the selected group has a healthy node, and whether the destination port is permitted. If DNS fails, review the profile’s DNS settings and the client’s TUN DNS handling. Do not add multiple unrelated DNS overrides at once; make one controlled change and repeat the same test.

For a failure that appears only on one network, check for a captive portal, restrictive firewall, corporate endpoint policy, or another VPN. On managed work devices, routing changes may be restricted by organizational policy. Do not bypass those controls without authorization. In split-tunnel environments, preserve routes to local printers, private development servers, and internal company networks as required by your organization.

When testing is complete, keep a short record of the working state: client and core versions, TUN settings, the relevant rule names, and the exact command used for verification. Back up a profile before editing it, and validate YAML indentation after each change. If the client supports configuration parsing or profile validation, run it before applying an override. A small, documented change is easier to maintain than a large collection of copied rules.

TUN is most useful when it complements a clear routing policy. Use the connection log to understand individual decisions, avoid duplicate application-level proxy settings unless they are intentional, and retest after core or profile updates. This approach makes terminal traffic predictable without turning every shell command into a special case.

Download Clash for Free – Get Started Now →