Clash 多裝置設定同步:訂閱連結、代管設定與手動匯出三種方案

手機、電腦與平板如何讓設定保持一致?本文比較訂閱連結自動同步、自架設定代管與手動匯出匯入三種方案的適用情境、維護成本與衝突處理方式。

先釐清要同步的是哪幾類資料

多裝置之間「設定對不上」,多數時候不是客戶端的問題,而是把幾類性質不同的資料混在一起管理了。它們存放的位置、更新方式、能否自動同步都不一樣,先分清楚再談方案。

資料存放位置能否自動同步
訂閱連結各客戶端的設定儲存區否,每台裝置各填一次
設定本體 config.yaml客戶端設定目錄或代管 URL是,抓取訂閱時整份取代
節點與規則集 providers./providers./ruleset 快取是,依 interval 定時抓取
目前選取的節點、運作模式客戶端運作狀態否,各裝置獨立

真正需要統一的是設定本體和 providers 快取:前者決定連接埠、DNS、TUN 與規則,後者決定節點清單。至於目前選取的是哪個節點、mode 停在 rule 還是 global,本來就該依裝置分別設定,不必強求一致。

一個常見誤判:訂閱相同不等於設定相同

訂閱只決定節點來源。mixed-portdnstunrules 這些欄位由各客戶端在本機維護,換訂閱不會同步連接埠,也不會同步本機規則。所以「三台裝置填了同一個連結」和「三台裝置行為一致」是兩件事,後者要靠下面的方案來保證。

方案一:訂閱連結自動同步

三台裝置填同一個訂閱位址,客戶端依固定間隔自動抓取。桌面、Android、iOS 都支援,是涵蓋面最廣的做法,也是維護成本最低的一種。

新增訂閱

「訂閱」→「新增」,貼上訂閱位址後儲存,先不要急著開代理。

調整自動更新間隔

在訂閱卡片上按右鍵 →「編輯」,把自動更新間隔從預設的 1440 分鐘改成 360~720 分鐘。

手動更新一次

在訂閱卡片上按右鍵 →「更新」,確認能抓出完整節點清單,而不是只剩一個設定名稱。

依裝置決定代理入口

「設定」→「系統代理」視需要開啟;TUN 模式在「設定」→「TUN 模式」另外打開,行動端由客戶端的 VPN 服務接管,不需要額外設定。

其餘裝置重複以上步驟

Android 端在「設定檔」清單裡長按設定檔可看到更新入口,iOS 端在設定檔詳細頁面下拉重新整理。

訂閱更新會整份取代設定本體 訂閱檔案裡如果帶 rulesmixed-portdns 區段,更新後這些欄位會被訂閱裡的值覆蓋。把自建規則直接寫進訂閱設定,是「更新一次就丟一次」最常見的原因。

連接埠被改寫之後的表現

訂閱把 mixed-port 從 7890 改成 7891 之後,系統代理和瀏覽器外掛裡寫死的 7890 仍然指向舊連接埠,表現是客戶端顯示已連線、但網頁全部打不開。核對辦法是打開 external-controller 面板(預設監聽 127.0.0.1:9090)看實際生效的連接埠。

# 查看目前生效的連接埠、模式與 DNS 設定
curl -s http://127.0.0.1:9090/configs

不方便用命令列的人,直接看桌面客戶端「設定」頁顯示的連接埠,和瀏覽器外掛裡的值對一下即可。

適用範圍

  • 適合:裝置數 1~3 台,規則完全跟隨訂閱,不想額外維護檔案。
  • 不適合:有自建規則、需要依裝置區分連接埠、訂閱結構經常調整。

方案二:自架設定代管,一份 YAML 管所有裝置

把設定本體放到一個能直連下載的位址(私有物件儲存、自架 nginx、私有儲存庫的 raw 連結都可以),各裝置把這個位址當作訂閱匯入。之後改規則只改這一份檔案,各端下次抓取時自動生效。

把節點來源和規則解耦

不要把節點直接寫進 proxies,用 proxy-providers 讓內核自己去抓節點;連接埠、DNS、規則這些屬於你自己的部分,全部寫在 base config 裡。

mixed-port: 7890
allow-lan: false
mode: rule
log-level: warning
external-controller: 127.0.0.1:9090
unified-delay: true
tcp-concurrent: true

proxy-providers:
  airport-a:
    type: http
    url: "https://sub.example.com/api/v1/client/subscribe?token=9f2c1a7b4e"
    interval: 3600
    path: ./providers/airport-a.yaml
    health-check:
      enable: true
      url: https://www.gstatic.com/generate_204
      interval: 300
      timeout: 3000

rule-providers:
  reject:
    type: http
    behavior: domain
    format: mrs
    url: "https://example.com/rules/reject.mrs"
    path: ./ruleset/reject.mrs
    interval: 86400

dns:
  enable: true
  enhanced-mode: fake-ip
  fake-ip-range: 198.18.0.1/16
  nameserver:
    - https://223.5.5.5/dns-query
  fallback:
    - https://1.1.1.1/dns-query

兩個 interval 的單位都是秒:3600 表示一小時抓一次節點,86400 表示一天抓一次規則集。節點變動頻繁就把前者調到 1800,規則集沒必要更頻繁。

兩個容易踩雷的細節 format: mrs 需要 mihomo 1.18.0 以上,舊版本改用 format: yaml 搭配 behavior: domain。另外,代管位址必須能直連下載,放在需要代理才能存取的地方,首次啟動會抓不到設定,表現是節點清單為空。

上線前先在本機跑一次語法檢查

# 只做設定檢查,不啟動代理
mihomo -t -d /etc/mihomo -f config.yaml

檢查通過再上傳到代管位址。各裝置匯入代管 URL 之後,節點由 providers 定時抓取,改規則只需要各端重新抓一次設定,不用逐台修改。

欄位與內核版本的對應關係

欄位適用版本用途
format: mrsmihomo 1.18.0 起規則集二進位格式,體積更小、載入更快
tcp-concurrentmihomo 1.16 起並行建立連線,減少握手等待
unified-delaymihomo 1.16 起統一各協定的延遲測量基準
geodata-modemihomo 1.16 起選擇內建 GEO 資料的使用方式

方案三:手動匯出匯入

只在離線裝置、路由器或臨時除錯時值得用。做法是匯出設定本體,連 providers/ruleset/ 快取目錄一起複製過去,少了快取目錄會白跑一趟。

找到設定目錄

桌面客戶端在「設定」裡點「開啟設定目錄」;mihomo 命令列版通常在 /etc/mihomo/config.yaml~/.config/mihomo/config.yaml

連快取目錄一起複製

只複製 config.yaml 時,首次啟動會因為 providers 快取缺失而顯示節點清單為空。

檔名帶上日期

例如 config-20260830.yaml,避免客戶端裡堆了好幾份同名設定互相覆蓋。

在目標裝置匯入

iOS 端先用「檔案」App 或雲端硬碟把 YAML 存到本機,再在客戶端裡選擇「匯入設定」。

匯入後立刻對照

看「代理」頁的節點數量和「規則」頁的筆數,和來源裝置一致才算匯入成功。

手動匯入是完整覆蓋 匯入沒有合併邏輯,目標裝置上原有的本機規則和連接埠設定會被匯入檔案覆蓋。匯入前先把目標裝置上的設定匯出保留一份。

以下幾種情況基本上只能走手動這條路:

  • 目標裝置連不到代管位址,例如內網或離線環境。
  • 只想臨時驗證一條規則或一組 DNS 設定,不想動代管檔案。
  • 路由器等嵌入式環境,只能透過 USB 隨身碟或 SCP 放檔案。

衝突處理:把修改分層

三種方案混用時,衝突基本上來自同一個原因——同一個欄位被兩處修改。解決辦法是把修改分層:訂閱或代管檔案只放共用部分,裝置差異放在合併層。

合併層只寫差異

# Merge 設定:不複製整份 config.yaml,只寫要改的部分
prepend-rules:
  - DOMAIN-SUFFIX,intranet.example.com,DIRECT
prepend-proxy-groups:
  - name: 手動選擇
    type: select
    proxies: [自動選擇, DIRECT]

規則用 prepend-rules 插到最前面,匹配優先順序高於訂閱自帶的規則;代理群組用 prepend-proxy-groups 放到清單最上方,方便在介面上直接選。訂閱更新時,合併層的內容不會被覆蓋,這是它比「直接改訂閱設定」可靠的地方。

一致性檢查清單

檢查項目位置預期結果
生效連接埠「設定」→「連接埠」,或 GET /configs各裝置同為 7890
節點數量「代理」頁同一個 provider 抓取的節點數一致
規則筆數「規則」頁與代管檔案裡的 rules 筆數一致
provider 更新時間GET /providers/proxies落在 interval 之內
運作模式系統匣選單或首頁平時保持 rule,需要診斷時才切 global
# 查看 provider 最近一次抓取時間與節點數量
curl -s http://127.0.0.1:9090/providers/proxies

一條經驗法則:同一個欄位只允許一個地方定義。連接埠、DNS、TUN 寫在 base config;節點來源寫在 proxy-providers;裝置差異寫在合併層;選取節點和運作模式交給各裝置自己。做到這一點,三台裝置之間的差異就只剩「目前選了哪個節點」。

區域網路裡的兩個注意事項

  • external-controller 預設只監聽 127.0.0.1,要讓其他裝置存取面板,需要明確改成 0.0.0.0:9090 並設定 secret
  • 多台裝置同時開 allow-lan 不會互相衝突,但其他裝置要指向正確的裝置 IP,連接埠保持 7890 即可。

三種方案怎麼選

方案適用情境維護成本衝突處理
訂閱連結自動同步1~3 台裝置,規則跟隨訂閱各自覆蓋,本機修改會遺失
自架設定代管3 台以上,有自建規則合併層分層,衝突可預期
手動匯出匯入離線裝置、路由器、臨時除錯完整覆蓋,需人工檢查

最常見的組合是:主要裝置用代管 URL 加合併層,手機和備用機直接填訂閱連結,路由器這類不方便連網更新的裝置手動放檔案。三套並存時,只要確保同一個欄位只有一個定義處,就不會互相打架。

常見問題

手機和電腦填了同一個訂閱,節點數量卻不一樣
先在兩台裝置上各手動更新一次再比對。仍不一致時檢查訂閱位址是否完全相同——部分訂閱會依客戶端類型回傳不同格式,複製時漏掉結尾的 &flag=clash 這類參數,結果就會不同。
訂閱更新後本機規則不見了,該怎麼保留
不要把規則寫進訂閱本體。桌面端把本機規則放進合併鏈的 prepend-rules;不支援合併鏈的客戶端,改用自架代管 URL,把規則寫進 base config 的 rules 區段。
同一份設定在 macOS 上正常,Android 上啟動就報錯
平台相關欄位不同。tunredir-porttproxy-port 屬於桌面和 Linux 側的寫法,Android 由客戶端自己的 VPN 服務接管;external-controller 寫成 0.0.0.0:9090 又沒設定 secret 時,部分客戶端會直接拒絕啟動。把這些欄位從 base config 移出,放進各端的合併層即可。
多台裝置同時開 TUN 模式會衝突嗎
不會,每台裝置的 TUN 只在本機生效。同一個區域網路裡如果都開了 allow-lan,注意讓其他裝置指向正確的裝置 IP;面板連接埠預設只監聽本機,跨裝置存取要明確開放並設定 secret
下載 Clash 客戶端