速度測定の失敗と実際の接続失敗を切り分ける

Clashクライアントに表示される「タイムアウト」は、指定したテスト先へのリクエストが制限時間内に完了しなかったことを示します。ノードサーバーが必ず停止しているという意味ではなく、この結果だけでサブスクリプションが無効と判断することもできません。テスト先、DNS、ノードとのハンドシェイク、接続先サイトの応答のどこで止まっても、速度測定はタイムアウトになります。

この記事では「ローカルネットワーク → システム時刻 → コアとポート → 通信経路 → DNS → プロトコル設定 → サーバー」の順に確認します。オリジナル版Clashの設定の考え方と、Clash Meta(現mihomo)コアを採用したクライアントが対象です。各設定項目の対応状況は、実際に動作しているコアの仕様を確認してください。

症状優先して確認する項目次に確認する証拠
速度測定はタイムアウトするが、Webページは開けるテスト先と制限時間Webページへの通信が該当ノードを経由しており、直接接続ではないことを確認
すべてのノードで失敗するローカルネットワーク、コア、DNS同じ時間帯に記録された最初のエラーを確認
特定のノードだけ失敗するノード設定とサーバーの状態同じサブスクリプション内の正常なノードと比較
速度測定は正常だが、アプリは接続できないシステムプロキシ、ルール、TUN接続画面で実際の通信経路を確認
Webは見られるが、ゲームや通話ができないUDP対応と通信の取り込みTCPのテストと実際のUDP通信を切り分ける

手順1:ローカルネットワークとシステム時刻を確認

まず、プロキシを使わない状態を基準にする

  1. 現在の設定を記録してから、クライアントのシステムプロキシとTUNをオフにします。スマートフォンでは、対応するVPN接続が切断されていることも確認してください。画面を閉じただけでは、トンネルが動作し続けている場合があります。
  2. 普段プロキシなしでアクセスできるWebサイトを開きます。ホテル、学校、公共のWi-Fiで認証ページが表示される場合は、先にログインしてください。Wi-Fiアイコンが表示されていても、インターネットに接続できているとは限りません。
  3. スマートフォンのテザリングでも同じテストを行います。デバイス、設定、ノードはそのままにして、接続先のネットワークだけを切り替えてください。

プロキシをオフにしても直接接続できない場合は、まずローカルネットワークを確認します。自宅の回線では失敗し、テザリングでは正常な場合、接続ネットワークのDNS、ルーティング、UDP制限などが原因として考えられます。ただし、ログで確認するまでは断定できず、サーバー側のブロックとも限りません。OSのネットワーク診断は特定の確認先に依存することがあるため、「インターネットなし」という表示だけを根拠にしないでください。

証明書エラーが出たら、まず時刻を合わせる

TLS証明書の検証にはシステム時刻が使われます。Windows 11では「設定」→「時刻と言語」→「日付と時刻」を開き、自動時刻設定を有効にして同期します。macOSでは「システム設定」→「一般」→「日付と時刻」を確認してください。タイムゾーンだけでなく、日付、年、分単位の時刻も確認します。

ログに certificate has expired or is not yet valid と表示された場合は、端末の時刻とサーバー証明書の有効期間を確認します。証明書検証の無効化を万能な対処法として使わないでください。サーバーの本人確認が弱まり、パスワードの誤り、ポートへの接続不可、プロトコルの不一致も解決しません。

手順2:コアの動作とローカルポートを確認

GUIが起動していても、プロキシコアが設定を正常に読み込んでいるとは限りません。クライアントのログで設定の解析エラー、コアの異常終了の繰り返し、address already in use がないか確認します。設定が読み込まれていないと、ノード一覧にキャッシュが表示されたままでも、ローカルのプロキシポートは待ち受けていないことがあります。

プロキシポートとコントロールポートを区別する

  • port:HTTPプロキシポート。
  • socks-port:SOCKSプロキシポート。
  • mixed-port:HTTPとSOCKSの両方のプロキシリクエストを受け付けるポート。
  • external-controller:コントロールAPIの待ち受けアドレス。ブラウザーのプロキシ設定には入力しません。

現在有効な設定で mixed-port: 7890 を使っている場合は、次のコマンドで待ち受けプロセスを確認できます。WindowsではPowerShell、macOSではターミナルを使います。何も表示されない場合は、ノードを次々に切り替えるのではなく、コアのログを確認してください。

# Windows PowerShell
Get-NetTCPConnection -LocalPort 7890 -State Listen |
  Select-Object LocalAddress, LocalPort, OwningProcess

# macOS
lsof -nP -iTCP:7890 -sTCP:LISTEN

Windowsでは Get-Process -Id プロセス番号 でも実行プログラムを確認できます。「プロセス番号」は前の手順で確認した実際の数値に置き換えてください。古いクライアントがポートを使用している場合は、古いインスタンスを終了するか、ポートを変更し、システムプロキシの設定も合わせて変更します。出所が分からないシステムプロセスを終了したり、TUNで通信を取り込むクライアントを複数同時に動かしたりしないでください。

手順3:リクエストが通るルールとノードを確認

システムプロキシの設定が適用されるのは、その設定に従うアプリだけです。一部のコマンドラインツール、ゲーム、独自のネットワーク機能を持つアプリは設定を無視します。TUNは仮想ネットワークインターフェースを通じて、ルーティング条件に合う通信を取り込みますが、ルート、権限、除外設定にも左右されます。両者は同じ機能ではなく、「システムプロキシが有効」というだけでは、すべての通信がコアを通っている証拠になりません。

プロキシを明示したリクエストで比較する

クライアントでテスト対象のノードを選び、該当するポリシーグループがそのノードを指していることを確認してから、HTTPプロキシを明示したリクエストを1回実行します。以下のコマンドはローカルの7890ポートに接続し、接続タイムアウトを10秒、全体の制限時間を15秒に設定します。Windowsでは curl.exe、macOSとLinuxでは curl を使ってください。

curl.exe --proxy http://127.0.0.1:7890 --connect-timeout 10 --max-time 15 -I https://example.com/

テスト先は同じ条件でリクエストを再現するためのもので、ノードの利用可否を判定する唯一の基準ではありません。HTTPステータスが返れば、そのリクエストが少なくとも該当段階まで進んだことを示します。403 は接続先サイトによる拒否の可能性があり、プロキシ接続の失敗とは限りません。127.0.0.1:7890 に接続できない場合は、まずローカルポートの待ち受けを確認します。プロキシトンネルの確立後に失敗する場合は、ハンドシェイク、DNS、接続先からの応答を調べてください。

  1. クライアントの接続画面を開き、先ほど指定したドメインを探します。
  2. 一致したルール、ポリシーグループ、最終的に選ばれたノードを確認し、実際には DIRECT で接続していないか調べます。
  3. 接続画面にリクエストがまったく表示されない場合は、まず接続元とポートを確認します。接続記録がすぐ消えることもあるため、ログも併せて確認してください。
  4. 必要に応じて一時的にグローバルモードにし、テスト対象のノードを明示して比較します。確認後はルールモードに戻してください。

プロキシを明示したリクエストが成功し、特定のアプリだけ失敗する場合は、サブスクリプションを何度も更新するのではなく、アプリのプロキシ設定とTUNのルーティングを確認します。TUNを有効にしたときだけ失敗する場合は、TUNをオフにして明示的なプロキシ接続を残した状態でテストし、管理者権限、ほかのVPN、仮想ネットワークアダプター、ルートの競合を1つずつ調べてください。

手順4:DNSの問題を2つの名前解決経路に分ける

プロキシ接続では、少なくとも2種類のドメインが関係します。ノードサーバーのドメインと、ユーザーがアクセスする接続先ドメインです。前者の名前解決に失敗するとトンネルを確立できません。後者の名前解決に失敗すると、ノードとのハンドシェイクは成功しても一部のサイトが開けないことがあります。2つのドメインで同じDNS経路が使われるとは限りません。

ノードのドメイン:トンネル確立の前提を確認

ログに記録された失敗ドメインが、ノードの server と一致するか確認します。mihomoの proxy-server-nameserver では、ノードのドメインを解決するDNSサーバーを指定できます。default-nameserver は、DNSサーバー自身のドメインを解決するための初期設定に関係します。まだ確立していない同じプロキシ経路だけにノードの名前解決を依存させると、循環依存になるおそれがあります。

Windowsの Resolve-DnsName やmacOSの dig で、システムが取得する名前解決結果を確認できます。ただし、結果が分かるのは各ツールが使用したDNS経路に限られ、mihomo内蔵DNSでも同じ結果になるとは限りません。診断時は、有効な設定のDNS項目とコアのログも併せて確認してください。

接続先ドメイン:Fake-IP、DNSの横取り、アプリのキャッシュを確認

  • fake-ip モードでは、198.18.0.0/16 の範囲にある合成アドレスが返されることがあります。これらはWebサイトの実サーバーアドレスではありません。
  • Fake-IPアドレスは、対応するコアが通信を取り込み、ドメインに対応付ける必要があります。クライアントの切り替え後に残ったシステムやアプリのDNSキャッシュによって、リクエストが誤った経路に進む場合があります。
  • TUNのDNSハイジャックでは、設定に合うDNSリクエストを取り込めます。ただし、アプリ内蔵のDoHが通常の53番ポートを通るとは限りません。
  • nameserver-policy、nameserver、fallback は実際の設定に照らして確認してください。DNSサーバーを増やせば、必ず名前解決が速くなったり安定したりするわけではありません。

DNSモードを変更したら、設定を再読み込みし、影響を受けるアプリを再起動します。Windowsでは必要に応じて ipconfig /flushdns を実行し、システムのDNSキャッシュを消去できます。ただし、すべてのブラウザー内キャッシュが消えるわけではありません。IPv6を無効にして復旧した場合も、AAAAレコードの解決、IPv6の出口、ルーティングを引き続き確認する必要があります。すべてのIPv6環境で無効化すべきだという意味ではありません。

手順5:プロトコル設定とコアの対応状況を確認

ローカルポートが正常で、リクエストが対象ノードに届き、ノードのドメインも解決できることを確認してから、プロトコルの項目を1つずつ確認します。YAMLパーサーで設定を読み込めても、構文が正しいことしか分かりません。現在のコアが項目に対応していない、認証情報が期限切れ、サーバーの待ち受け方式が変更された、といった原因でも接続に失敗します。

設定項目確認する内容よくある誤解
サーバーアドレスserver、portサブスクリプション更新後も古いポートを使用している
認証と暗号化UUID、パスワード、暗号化方式コピー時に空白が混入、または古い認証情報を使用
TLSSNI、証明書、ALPNノードの表示名をSNIとして使っている
トランスポート層WebSocketのパス、Host、gRPCのサービス名サーバーとパスワードだけをコピーし、トランスポート設定を見落としている
Reality公開鍵、short-id、サーバー名別のノードの設定値を混ぜて使用している
UDPプロトコルコアの対応状況、ネットワークでの許可、サーバーの待ち受けTCPポートのテストだけでUDPも正常と判断する

たとえばHysteria2やTUICなどUDPベースの接続は、UDPが制限されたネットワークでは失敗しても、同じネットワークのTCPノードは正常に動作する場合があります。TCPポートへの接続テストでは、この種のプロトコルのハンドシェイク全体を検証できません。反対に、通常のHTTP遅延テストに成功しても、ゲームや音声通話に必要なUDP転送に対応しているとは限りません。

クライアントのバージョンと実際のコアのバージョンを記録してください。両者のバージョン番号は異なります。オリジナル版Clashとmihomoでは対応するプロトコルが異なり、古いコアでは新しい設定項目を認識できない場合もあります。unsupported proxy type や設定項目の解析エラーが出た場合は、速度測定の制限時間を延ばすのではなく、設定形式とコアの対応状況を確認してください。

手順6:ノード、テスト先、サーバーの状態を切り分ける

条件を絞って比較する

  1. 同じ端末・同じネットワークでノードを変更:特定のノードだけ失敗する場合は、まず設定、利用可能量、サーバーのメンテナンス状況を確認します。
  2. 同じ端末・同じノードでネットワークを変更:テザリングでは正常で固定回線では失敗する場合は、接続ネットワークの経路とプロトコル制限を調べます。
  3. 同じネットワーク・同じノードで端末を変更:別の端末で正常なら、問題の端末のオーバーライド、コア、プロキシの接続先、キャッシュを確認します。
  4. 同じノードで接続先サイトを変更:特定のテスト先だけ失敗する場合は、接続先の制限やテストURLを確認します。単一サイトの障害をノード全体の停止と判断しないでください。

速度測定の制限時間も診断項目として変更できます。たとえば5秒から一時的に10秒へ延ばし、接続確立に時間がかかっているだけかを確認します。この操作で認証エラー、期限切れの証明書、接続を拒否されたポートは直りません。制限時間を延ばしたときだけ時々成功する場合も、パケットロス、輻輳、ハンドシェイクのログを確認してください。

サブスクリプションの更新成功が示すのは設定を取得できたことだけで、すべてのノードが稼働中とは限りません。プロバイダーのアカウント状態、通信量の上限、メンテナンスのお知らせを確認してください。更新後は、現在有効な設定、ノードの項目、更新日時が実際に変わったかを確認します。高頻度で連続して速度測定を行うのは避けてください。時刻を記録した少数のリクエストのほうが、原因を特定しやすくなります。

ログの確認:エラー発生段階を残し、認証情報は隠す

ログレベルを一時的に debug に変更して障害を1回再現し、時刻を記録したら、通常のログレベルに戻します。デバッグログにはアクセス先ドメインや接続の詳細が含まれる場合があります。共有するときは、該当する時間帯の部分だけを抜き出してください。

  • connection refused:通常、接続が明示的に拒否されたことを示します。エラーの接続先がローカルのプロキシポートか、リモートのノードポートかを確認してください。
  • i/o timeout、context deadline exceeded:いずれかの段階が制限時間を超えたことを示します。前後のログを確認し、名前解決、接続開始、リクエストのどこで発生したかを特定します。
  • no such host:名前解決に失敗したドメインと、使用されたDNS経路を優先して特定します。
  • authentication failed:認証情報とアカウントの状態を優先して確認します。通常、クライアントを再インストールしてもサーバー側の認証結果は変わりません。
  • EOF、接続リセット:接続が途中で閉じられたことを示します。この1行だけでは原因を特定できないため、ハンドシェイクの段階とサーバー側の記録も確認してください。

確認が終わったら、ルールモード、ログレベル、一時的な変更を元に戻し、再現できる記録を残します。次に「速度測定がタイムアウト」したときは、検証済みのネットワーク、ポート、DNSの状態から確認を続けられ、最初から再インストールする必要はありません。プロキシの接続先や設定のインポート方法はクイックスタートを、よくある設定の疑問はヘルプセンターを参照してください。