Shadowrocketのカスタムルール優先順位|上から順に判定する仕組みとFINAL、PROXY/DIRECT/REJECT

Shadowrocketのカスタムルールは上から順に判定され、最初に一致したルールが適用されます。FINALの配置とPROXY・DIRECT・REJECTの違いを、ルール順の例とともに解説します。

この記事の概要

この記事は、Shadowrocketで接続を設定済みで、通信の振り分けを調整したい方向けです。まずGlobal RoutingがConfigになっていることを確認し、最初に一致したルールのポリシーが適用される仕組みを把握しましょう。具体的なドメイン例外、IP範囲、FINALを組み合わせ、確認しやすいルールリストを作成します。例示用のアドレスのみを使用しており、接続サービスは提供していません。サブスクリプションURLはご利用のサービス提供元から入手してください。

1. カスタムルールの優先順位:先に一致したルールが適用される

Configに基づいて通信を振り分ける場合、[Rule]内のルールは上から順に判定されます。条件に一致した時点で、そのルールに指定されたポリシーが適用され、それより下にある「より具体的な」ルールや後続のルールは判定されません。そのため、優先順位はドメイン名の長さやルールの種類で自動的に決まるのではなく、リスト内の位置で決まります。

リクエストがトンネルに入る 現在の設定を読み込む ルールを上から順に判定する 一致したルールのポリシーを適用する 外向きの接続を確立する

たとえば、DOMAIN-SUFFIX,example.com,PROXYはexample.comとそのサブドメインに一致します。そのうちfiles.example.comだけをDIRECTで接続したい場合は、DOMAIN,files.example.com,DIRECTをこのサフィックスルールより前に置きます。逆の順序では、サフィックスルールが先にサブドメインを処理するため、後ろにある例外ルールはそのリクエストの判定に使われません。

2. Global RoutingとPROXY、DIRECT、REJECTの違い

まずHome → Global Routingで現在のモードを確認します。現在の設定ルールを検証するにはConfigを選択してください。ProxyとDirectはGlobal Routingの全体設定であり、個別のカスタムルールが一致したかどうかの確認には使えません。Sceneを使っている場合は、シーンで実際に適用されている設定も確認してください。Configエディタのルールだけから、現在の結果を判断することはできません。

3種類
この記事で使うルールポリシー:PROXY / DIRECT / REJECT
4項目
Global Routing:Proxy / Direct / Config / Scene
1つ
この記事のルール例では、末尾にFINALを1つだけ置きます
ルールポリシー一致した場合の処理確認ポイント
PROXYプロキシ経由でリクエストを処理します。現在選択されているプロキシを確認します。ポリシーグループを使っている場合は、グループ内で実際に選択されている出力先も確認してください。
DIRECT現在のネットワークから宛先に直接接続します。DIRECTでも、ローカルネットワーク、宛先への到達性、DNSの結果に依存します。接続の成功が保証されるわけではありません。
REJECT一致したリクエストを拒否します。宛先に関連する機能が読み込めなくなる場合があります。まず一致範囲を確認してから、拒否範囲を広げてください。

確認の順序:まずモードを確認し、次にルールを調べる

ルールを変更しても反映されない場合は、まずHomeに戻ってGlobal RoutingがConfigになっていることを確認します。次にConfigで、編集したファイルが選択されていることを確かめてください。ルール順を判断するために、プロキシを何度も切り替えるのは避けましょう。

PROXYはルール内のポリシー識別子で、ProxyはGlobal Routingの画面上の選択肢です。役割が異なります。ルールはどのリクエストにどの出力先を使うかを決め、Shadowsocks、VMess、VLESS、Trojan、Hysteria2、WireGuardなどのプロトコルは接続方法を決めます。ルールの順序を変えても、プロトコル設定のポート、鍵、認証情報の誤りは解消されません。

3. DOMAIN-SUFFIX、GEOIP、IP-CIDR、FINALの書き方

一般的なルールは「ルールタイプ、マッチ条件、ポリシー」の形式です。FINALにはマッチ条件が不要なため、ルールキーワードとポリシーの2項目だけで構成されます。以下の表は構文の説明用です。example.comと192.0.2.0/24はドキュメント用の例であり、実際のサービスのアドレスではありません。

ルール例マッチ条件順序の注意点
DOMAIN,files.example.com,DIRECTこの完全一致のドメインにマッチします。このルールを適用範囲に含むDOMAIN-SUFFIXより前に置きます。
DOMAIN-SUFFIX,example.com,PROXYこのドメインとそのサブドメインにマッチします。任意の文字列を含むかどうかの判定ではありません。単一ドメインの例外より後に置き、残りのサブドメインを処理できます。
IP-CIDR,192.0.2.0/24,DIRECT,no-resolve例示用のIPv4範囲にマッチします。no-resolveを指定すると、このIPルールのためにドメイン名を積極的に解決することを避けられます。Config全体のDNSを無効にする指定ではなく、すでに判明している宛先IPのマッチ条件も変更しません。
GEOIP,CN,DIRECT宛先IPを地域データベースの分類に基づいて判定します。ドメインサフィックスによる判定ではありません。結果は宛先IPとデータベースによって決まります。
FINAL,PROXYそれ以前のルールに一致しなかったリクエストをPROXYに渡します。ルールリストの末尾に置きます。

ドメインルールがマッチするかどうかは、接続で利用可能な宛先ドメイン情報があるかどうかにも左右されます。IPアドレスを直接指定してリクエストした場合、DOMAIN-SUFFIXに自動で一致するとは限りません。また、1つのウェブページがメインサイト、画像、認証API、コンテンツ配信ドメインへ同時にリクエストを送ることがあります。メインサイトがDIRECTに一致しても、ページ内のすべての接続に同じポリシーが適用されるとは限りません。

4. ルール順の調整例:サブドメインの例外とFINAL

次のような設定を考えます。files.example.comはDIRECT、ads.example.comはREJECT、それ以外のexample.comのドメインはプロキシ経由にします。下の2つの設定例ではルールの内容は同じで、並び順だけが異なります。「例外を記述した」だけでは「例外が必ず適用される」とは限らないことがわかります。

調整前:広範囲のルールが先

1番目のルール
DOMAIN-SUFFIX,example.com,PROXY
2番目のルール
DOMAIN,files.example.com,DIRECT
3番目のルール
DOMAIN,ads.example.com,REJECT
4番目のルール
FINAL,PROXY

2つの特定のサブドメインはいずれも先に1番目のルールに一致するため、後続の例外は意図どおりに適用されません。

調整後:明示的な例外を先に

1番目のルール
DOMAIN,files.example.com,DIRECT
2番目のルール
DOMAIN,ads.example.com,REJECT
3番目のルール
DOMAIN-SUFFIX,example.com,PROXY
4番目のルール
FINAL,PROXY

まず単一ドメインの例外を処理し、次にドメイン全体を処理して、最後に残りのリクエストを処理します。

IP範囲や地域に基づく振り分けも必要なら、次のような構成にできます。ここでのGEOIP,CN,DIRECTは地域ルールの配置例であり、すべてのユーザーに適した設定という意味ではありません。実際のポリシーは、利用中のネットワークとアクセス要件に合わせてください。

[Rule]
DOMAIN,files.example.com,DIRECT
DOMAIN,ads.example.com,REJECT
DOMAIN-SUFFIX,example.com,PROXY
IP-CIDR,192.0.2.0/24,DIRECT,no-resolve
GEOIP,CN,DIRECT
FINAL,PROXY

この例では、example.com配下のドメインは先にドメインルールで処理されます。解決されたIPがGEOIPでCNに分類されても、DIRECTには切り替わりません。上記のドメインルールに一致しないリクエストは、後続のIPルールで判定されます。「より具体的に見えるルール」よりもリスト内の位置が重要なのはこのためです。

調整の基本:具体的な例外を先に、分類ルールを後に

必ずDIRECTまたはREJECTにしたい宛先は、その宛先を含むルールより前に移動します。関連するルールを一組ずつ移動し、末尾のFINALは残してください。動作が変わった理由を把握しやすくなります。

5. Configの編集から新しい接続の検証まで

ルールの検証では、「編集が完了した」「現在の設定として選択されている」「新しいリクエストに新しい設定が適用された」の3段階を区別します。ブラウザやアプリは既存の接続を再利用することがあるため、ページを更新しただけでは新しい外向き接続が作られるとは限りません。テストでは、ルールの判定は正しいが接続に失敗している場合と、リクエストが対象のルールに一致していない場合も区別してください。

  1. 元の設定を保存する。Configで編集する前に、復元できるコピーを保存し、現在選択されているファイルを記録します。既存設定の他の部分を含め、例全体で置き換えないでください。
  2. [Rule]を確認する。変更するルールを探し、同じドメイン、上位サフィックス、IP範囲のルールが前にないか、またFINALが先に置かれていないかを確認します。末尾のフォールバックは明確なものを1つだけ残してください。
  3. 保存してファイルを選択する。編集後に保存を確認し、Configで実際に選択されているのが編集した設定であることを確かめてください。名前が似た別のファイルと間違えないようにします。
  4. ルーティングモードを確認する。Home → Global Routing → Configに戻ります。テスト中は現在のプロキシ選択を変えず、出力先とルールを同時に変更して混乱するのを避けてください。
  5. 接続を確立し直す。重要な作業に支障がないことを確認したうえで、接続をいったん切断してから再接続し、対象へのリクエストを再度実行します。必要に応じて対象アプリを終了して再起動し、既存接続の再利用を抑えてください。
  6. 新しいリクエストの記録を確認する。接続履歴やログで、宛先ドメイン、宛先IP、適用されたポリシーを確認します。一致したルールの情報が表示される場合は、それも確認してください。ウェブページが開くかどうかだけで、ルールが正しく動作したと判断しないでください。

記事中の例示用ドメインは、実際のテストサービスを提供するものではありません。検証には、自分がアクセスする権限を持ち、リクエスト先を確認できるアドレスを使い、テスト条件を記録してください。たとえば「ページの文字は表示されるが、画像が読み込み中のまま」の場合は、サイト全体のポリシーをすぐ変更するのではなく、画像への実際のリクエスト先ドメインを確認します。

6. FINALとカスタムルールのよくある質問

FINALを1行目に置くと、その下のルールが適用されないのはなぜですか?

FINALは、その位置まで到達した未一致のリクエストをすべて処理します。[Rule]の末尾に移動してから、その前にある個別ルールを確認してください。FINALの後ろに適用させたいドメイン例外を追加したり、最初のFINALを上書きする目的で2つ目のFINALを追加したりしないでください。

DIRECTを設定したのに、ウェブサイトが開かないのはなぜですか?

まず新しいリクエストの記録を確認し、実際にDIRECTが適用されているかを調べます。DIRECTが記録されていれば、ルールによる直接接続の判定は完了しています。次に現在のネットワークから宛先にアクセスできるか、DNSが妥当なアドレスを返しているか、宛先のサービスが応答しているかを確認してください。DIRECTは接続経路を指定するだけで、ネットワークやサーバー側の障害を解決するものではありません。

FINAL,DIRECTに変更すると、既存のルールすべてに影響しますか?

すでに一致したルールは変わりませんが、それ以外のリクエストに適用されるデフォルトの出力先は変わります。変更前に、現在のフォールバックに依存しているリクエストを確認してください。特定のドメインだけをDIRECTにしたい場合は、フォールバック全体の適用範囲を広げず、DOMAINまたはDOMAIN-SUFFIXの例外を前方に追加します。

サブスクリプションを更新すると、カスタムルールは上書きされますか?

まず、Homeで更新する接続サブスクリプションと、Configで更新するリモート設定を区別してください。これらは別のものです。リモート設定を更新すると、該当する設定内容が置き換わる場合があります。更新前にコピーを保存し、更新後に現在選択されているファイルと[Rule]を確認してください。ローカルの変更が必ず保持されるとは限りません。サブスクリプションURLはご利用のサービス提供元から入手してください。

REJECTのあと、ページの一部のボタンが使えません。どう確認すればよいですか?

まずボタンを押したときに追加されたリクエストを確認し、認証、API、またはリソースのドメインが拒否されていないか調べます。疑わしいルールを一時的に無効にして再テストしてください。依存関係を確認したら、REJECTの範囲を狭めるか、その前に明示的な例外を追加します。すべてのリクエストを一律に許可する設定は避けてください。

App Storeで正規版をダウンロードデベロッパ名とアプリIDを確認