跳到主要內容

首頁 / 部落格 / 部署實戰

用 Mihomo 做家庭閘道:軟路由 / NAS 上的透明代理部署

部署實戰2026-06-052253 字約 5 分鐘
用 Mihomo 做家庭閘道:軟路由 / NAS 上的透明代理部署

給每台設備裝用戶端太麻煩,電視、投影儀、IoT 設備根本裝不了。把 Mihomo 部署在軟路由或 NAS 上,全家設備接入 Wi-Fi 就自動生效。

三種接入方式

三種方案的取舍旁路由 + 手動指閘道在需要的設備風險最低,出問題只影響那台設備需要逐台設定新手推薦TProxy 透明代理在閘道上用 i設備零設定設定複雜,出錯全家斷網TUN + auto-route閘道上開 TU設定簡單效能開銷大,軟路由 CPU 可能吃不消
先用旁路由手動指定的方式跑通,再考慮要不要上透明代理

本文以 旁路由 + TProxy 為主線,這是家庭場景最實用的組合。

一、安裝 Mihomo

以 Linux amd64 軟路由 / NAS 為例:

# 下載並解壓縮(架構按實际情況選)
gunzip mihomo-linux-amd64-v1.19.29.gz
chmod +x mihomo-linux-amd64-v1.19.29
sudo mv mihomo-linux-amd64-v1.19.29 /usr/local/bin/mihomo
mihomo -v

# 準備工作目錄
sudo mkdir -p /etc/mihomo

ARM 設備(樹莓派、ARM NAS)用 linux-arm64 版本,uname -m 輸出 aarch64 就是它。

二、設定檔

/etc/mihomo/config.yaml

# ===== 基礎 =====
mixed-port: 7890
tproxy-port: 7895          # TProxy 用
redir-port: 7892           # REDIRECT 用(可选)
allow-lan: true
bind-address: "*"
mode: rule
log-level: info
ipv6: false
unified-delay: true
tcp-concurrent: true

external-controller: 0.0.0.0:9090
secret: "改成一个足够长的随机密码"
external-ui: /etc/mihomo/ui

# ===== DNS =====
dns:
  enable: true
  listen: 0.0.0.0:1053
  ipv6: false
  enhanced-mode: fake-ip
  fake-ip-range: 198.18.0.1/16
  fake-ip-filter:
    - "*.lan"
    - "*.local"
    - "+.home.arpa"
    - "+.pool.ntp.org"
    - "time.*.com"
    - "+.msftconnecttest.com"
    - "+.msftncsi.com"
    - "captive.apple.com"
  default-nameserver: [223.5.5.5, 119.29.29.29]
  nameserver:
    - https://doh.pub/dns-query
    - https://dns.alidns.com/dns-query
  fallback:
    - https://1.1.1.1/dns-query
  fallback-filter:
    geoip: true
    geoip-code: CN

# ===== 節點來源 =====
proxy-providers:
  main:
    type: http
    url: "你的订阅链接"
    interval: 3600
    path: ./providers/main.yaml
    header:
      User-Agent: ["clash.meta"]
    exclude-filter: "(?i)剩余|到期|官网|流量"
    health-check:
      enable: true
      url: http://www.gstatic.com/generate_204
      interval: 300
      lazy: true

# ===== 策略組 =====
proxy-groups:
  - name: "PROXY"
    type: select
    proxies: ["AUTO", "HK", "JP", "SG", DIRECT]
  - name: "AUTO"
    type: url-test
    use: [main]
    url: http://www.gstatic.com/generate_204
    interval: 300
    tolerance: 50
    lazy: true
  - name: "HK"
    type: url-test
    use: [main]
    filter: "(?i)香港|HK|Hong ?Kong"
    interval: 300
    tolerance: 50
  - name: "JP"
    type: url-test
    use: [main]
    filter: "(?i)日本|JP|Japan"
    interval: 300
    tolerance: 50
  - name: "SG"
    type: url-test
    use: [main]
    filter: "(?i)新加坡|狮城|SG|Singapore"
    interval: 300
    tolerance: 50
  - name: "FINAL"
    type: select
    proxies: ["PROXY", DIRECT]

# ===== 規則 =====
rules:
  - IP-CIDR,127.0.0.0/8,DIRECT,no-resolve
  - IP-CIDR,192.168.0.0/16,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,100.64.0.0/10,DIRECT,no-resolve
  - DOMAIN-SUFFIX,lan,DIRECT
  - DOMAIN-SUFFIX,local,DIRECT
  # 按設備分流(示例)
  - SRC-IP-CIDR,192.168.1.50/32,DIRECT          # 老人的手机全直连
  - SRC-IP-CIDR,192.168.1.60/32,PROXY           # 电视全走代理
  # 常規分流
  - GEOIP,CN,DIRECT
  - MATCH,FINAL

三、systemd 服務

/etc/systemd/system/mihomo.service

[Unit]
Description=Mihomo Daemon
After=network-online.target
Wants=network-online.target

[Service]
Type=simple
User=root
LimitNOFILE=1000000
CapabilityBoundingSet=CAP_NET_ADMIN CAP_NET_RAW CAP_NET_BIND_SERVICE CAP_SYS_TIME CAP_SYS_PTRACE CAP_DAC_READ_SEARCH
AmbientCapabilities=CAP_NET_ADMIN CAP_NET_RAW CAP_NET_BIND_SERVICE CAP_SYS_TIME CAP_SYS_PTRACE CAP_DAC_READ_SEARCH
Restart=always
RestartSec=5
ExecStartPre=/usr/local/bin/mihomo -t -d /etc/mihomo
ExecStart=/usr/local/bin/mihomo -d /etc/mihomo

[Install]
WantedBy=multi-user.target

ExecStartPre 裡的 -t 是設定檢查——設定寫錯時服務不會帶著壞設定啟動,這個細節能省掉很多麻煩。

sudo systemctl daemon-reload
sudo systemctl enable --now mihomo
sudo systemctl status mihomo
journalctl -u mihomo -f

四、方式 A:手動指定閘道(推薦先用這個)

不動任何防火牆規則,在需要代理的設備上手動改:

  • 閘道:改成軟路由的 IP(比如 192.168.1.2
  • DNS:同樣改成 192.168.1.2
旁路由的位置設備閘道指向旁路由旁路由 Mihomo按規則處理主路由負責撥號上網外網不改設定的設備走原路,完全不受影響
最大的好處:出問題時其他設備照常上網

這種方式的優點是容錯性極好——Mihomo 掛了只影響手動改過設定的設備,家裡其他人無感。

五、方式 B:TProxy 透明代理

設備零設定,但需要在閘道上配防火牆規則。

開啟核心轉發

sudo tee /etc/sysctl.d/99-mihomo.conf > /dev/null <<'EOF'
net.ipv4.ip_forward = 1
net.ipv4.conf.all.route_localnet = 1
EOF
sudo sysctl --system

iptables 規則

#!/bin/bash
# /etc/mihomo/tproxy.sh
TPROXY_PORT=7895
ROUTE_TABLE=100
FWMARK=1

# 策略路由:打了標記的包走本地
ip rule add fwmark $FWMARK table $ROUTE_TABLE 2>/dev/null
ip route add local default dev lo table $ROUTE_TABLE 2>/dev/null

# 自定義鏈
iptables -t mangle -N MIHOMO 2>/dev/null
iptables -t mangle -F MIHOMO

# 內網與保留地址直接放行
for net in 0.0.0.0/8 10.0.0.0/8 127.0.0.0/8 169.254.0.0/16 \
           172.16.0.0/12 192.168.0.0/16 224.0.0.0/4 240.0.0.0/4; do
  iptables -t mangle -A MIHOMO -d $net -j RETURN
done

# 其餘 TCP/UDP 打標記並轉給 TProxy 連接埠
iptables -t mangle -A MIHOMO -p tcp -j TPROXY --on-port $TPROXY_PORT --tproxy-mark $FWMARK
iptables -t mangle -A MIHOMO -p udp -j TPROXY --on-port $TPROXY_PORT --tproxy-mark $FWMARK

# 應用到轉發流量(來自其他設備)
iptables -t mangle -A PREROUTING -j MIHOMO

# DNS 劫持:把設備發出的 53 連接埠查詢轉給 Mihomo
iptables -t nat -A PREROUTING -p udp --dport 53 -j REDIRECT --to-ports 1053
iptables -t nat -A PREROUTING -p tcp --dport 53 -j REDIRECT --to-ports 1053

清理腳本:

#!/bin/bash
# /etc/mihomo/tproxy-clear.sh
iptables -t mangle -D PREROUTING -j MIHOMO 2>/dev/null
iptables -t mangle -F MIHOMO 2>/dev/null
iptables -t mangle -X MIHOMO 2>/dev/null
iptables -t nat -F PREROUTING 2>/dev/null
ip rule del fwmark 1 table 100 2>/dev/null
ip route del local default dev lo table 100 2>/dev/null

把規則掛到 systemd 上,隨服務啟停:

[Service]
ExecStartPost=/etc/mihomo/tproxy.sh
ExecStopPost=/etc/mihomo/tproxy-clear.sh

讓設備用上它

主路由的 DHCP 設定裡,把「預設閘道」和「DNS 伺服器」都改成軟路由的 IP。設備重新連一次 Wi-Fi 即可生效。

六、容錯設計:別讓家人罵你

這是家庭部署最重要的一節。

必做的容錯措施systemd 加 Restart=always,行程掛了自動拉起ExecStartPre 用 -t 檢查設定,壞設定不啟動訂閱更新腳本先下載到臨時檔案、校驗通過再替換保留一台不經過旁路由的設備,出問題時能上網查資料主路由 DHCP 裡配兩個 DNS:旁路由 + 公共 DNS 作為備份重要設備(老人手機、工作電腦)用 SRC-IP-CIDR 規則設為 DIRECT

安全的訂閱更新腳本

#!/bin/bash
# /usr/local/bin/update-mihomo.sh
set -euo pipefail
CONF=/etc/mihomo/config.yaml
TMP=$(mktemp)
trap 'rm -f "$TMP"' EXIT

curl -fsSL --max-time 30 -A "clash.meta" -o "$TMP" "你的订阅链接"

# 基本校驗
grep -q "^proxies:\|^proxy-providers:" "$TMP" || { echo "订阅内容异常"; exit 1; }

# 讓 mihomo 自己驗一遍
cp "$CONF" "${CONF}.bak"
cp "$TMP" "$CONF"
if mihomo -t -d /etc/mihomo; then
  systemctl restart mihomo
  echo "更新成功"
else
  cp "${CONF}.bak" "$CONF"
  echo "配置校验失败,已回滚"
  exit 1
fi

加到 cron:

0 4 * * * /usr/local/bin/update-mihomo.sh >> /var/log/mihomo-update.log 2>&1

用 proxy-provider 的話其實不需要這個腳本——核心會自己定期拉取節點,主設定不用動。這是推薦 provider 而不是整份訂閱的重要原因

七、Web 面板

external-ui: /etc/mihomo/ui
external-ui-name: metacubexd

把面板檔案放進 /etc/mihomo/ui,然後瀏覽器訪問 http://软路由IP:9090/ui,輸入 secret 就能在網頁上切換節點、看連接、查日誌。

家裡其他人也能用這個頁面自己切節點,不用找你。

八、效能與資源

不同硬體的大致承載能力(參考量級)樹莓派 4B百兆級別,家庭夠用J4125 軟路由千兆基本跑滿N100 軟路由千兆無壓力老舊單核設備規則集大時會明顯吃力實际取決於規則集規模、連接數與協議類型,僅作選型參考

效能吃緊時的最佳化順序:

  1. 精簡規則集(刪掉用不到的串流媒體、廣告列表)
  2. 規則集換成 mrs 二進位格式
  3. log-level 設為 warning,別用 debug
  4. 減少 health-check 的頻率
  5. TProxy 比 TUN 省資源,優先用 TProxy

九、排查

# 服務狀態
systemctl status mihomo
journalctl -u mihomo -n 100 --no-pager

# 連接埠監聽
ss -tulnp | grep mihomo

# API 是否回應
curl -H "Authorization: Bearer 你的secret" http://127.0.0.1:9090/version

# 從另一台設備測試代理連接埠
curl -x http://192.168.1.2:7890 -I https://www.google.com

# 看 iptables 規則命中計數
iptables -t mangle -L MIHOMO -v -n

小結

  • 先用「旁路由 + 手動指閘道」跑通,確認穩定了再上 TProxy
  • secret 必須設0.0.0.0:9090 是對整個區域網路開放的
  • 用 proxy-provider 而不是整份訂閱,核心自己更新,主設定永遠不動
  • ExecStartPre 加 -t 檢查設定,壞設定不會頂掉正在執行的服務
  • 給重要設備配 SRC-IP-CIDR 直連規則,別讓家人受影響
  • 改 TProxy 前先設一個自動清理的定時任務,給自己留後路

相關:外部控制 API 與面板多訂閱管理


相關文件

讓 Docker 和 WSL2 用上宿主機的 Clash 代理
部署實戰 讓 Docker 和 WSL2 用上宿主機的 Clash 代理

容器裡的 127.0.0.1 不是宿主機。這篇給出 Docker 構建期、執行期、daemon 拉取鏡像三種場景的設定方法,以及 WSL2 網路模式差異下的兩套方案。

2026-06-141716 字約 4 分鐘