Clashを開いてもブラウザは直結?システムプロキシが効かないブラウザ・端末の切り分け調査
システムプロキシのスイッチはオンになっているのに、通信がプロキシを経由しない――このような問題は多くの場合Clash自体の不具合ではなく、ブラウザと端末それぞれが独自のプロキシ判定ロジックを持っているために起こる。本記事ではレジストリ/ネットワーク設定、ブラウザ拡張機能の競合、端末の環境変数の3方向に分けて順に原因を特定し、最後に単一のスイッチに依存しないTUNモードの代替策を紹介する。
システムプロキシのスイッチは何を変更しているのか
Clashクライアント画面上の「システムプロキシ」スイッチは、本質的にはOSレベルでHTTP/HTTPSプロキシ設定を書き込むものだ――WindowsではレジストリのProxyServerキー値、macOSではネットワークサービスのプロキシ設定、Linuxのデスクトップ環境ではGSettingsまたは環境変数に書き込まれる。この設定は**システムプロキシ設定に従うプログラム**にのみ有効で、「従うかどうか」は完全にアプリケーション側の判断に委ねられており、OSが強制的に全てのアウトバウンド通信をこの設定に従わせるわけではない。
つまり、システムプロキシは一種の「提案」であり、強制転送ではない。主要ブラウザ(Chrome、Edge、Firefoxのデフォルトモード)はこの提案を読み取るが、多くのコマンドラインツールや一部の古いソフトウェアは完全に無視し、自身のネットワークライブラリで直接接続を確立する。これが、同じPC上でブラウザは既にプロキシ経由になっているのに、端末でcurlを実行すると直結で失敗したり、直結のまま成功したりする理由だ。
1つ目の経路:システムレベルのレジストリとネットワーク設定
これが最も基本的な層であり、ここが正しく設定されていなければ、後続のブラウザや端末の問題を議論することすらできない。
Windows:インターネットオプションとレジストリを確認する
システムプロキシのスイッチをオンにすると、Clashは現在のユーザーのHKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Internet Settingsに書き込む。重要なフィールドはProxyEnable(1であるべき)とProxyServer(Clashのリスニングアドレスとポート、通常は127.0.0.1:7890を指すべき)だ。「設定 → ネットワークとインターネット → プロキシ」を開き、手動プロキシ設定がClashのHTTPポートと一致しているか確認できる。
- ここに表示されているアドレスやポートが空、あるいは別のソフトウェアが書き込んだ古い値になっている場合、システムプロキシがClashに正しく引き継がれていないことを示す。Clash側でシステムプロキシのスイッチをもう一度オンにし直す必要がある。
- アドレスとポートが正しくても依然として直結している場合、問題はシステム層にはない可能性が高く、個別のプログラムを調べる必要がある。
- 企業のドメインポリシーや一部のセキュリティソフトはプロキシ設定を強制ロックし、再起動ごとに空にリセットすることがある。この場合は管理者に該当レジストリ項目の書き込み権限を開放してもらうか、直接TUNモードを使って回避する。
macOS:ネットワークサービスのプロキシ設定を確認する
macOSのプロキシ設定は各ネットワークサービス(Wi-Fi、イーサネットなど)ごとに紐づいており、全体で1つだけというわけではない。「システム設定 → ネットワーク → 使用中のサービス → 詳細 → プロキシ」を開き、「Webプロキシ(HTTP)」と「セキュアWebプロキシ(HTTPS)」の両方にチェックが入り、アドレスとポートがClashのローカルリスニングポートを指しているか確認する。複数のネットワークインターフェースやサービスがある場合、どれか1つにチェックを入れ忘れやすい。特に有線ネットワークとWi-Fiを同時に使っている場合、片方のサービスだけ設定してももう一方には反映されない。
2つ目の経路:ブラウザがシステムプロキシに従わない理由
ブラウザがプロキシを経由しない場合、以下の4つのケースが多く、優先順位順に並べる:
- ブラウザ自体が独立したプロキシモードを設定している。 Firefoxはデフォルトではシステムプロキシに従わず、自身の「ネットワーク設定」内の手動設定を使用する。
about:preferencesで「システムプロキシ設定を使用する」を手動で選択しない限り、Clashをどう設定しても無関係だ。 - プロキシ管理系の拡張機能をインストールしている。 SwitchyOmegaなどの拡張機能はブラウザのプロキシ判定を横取りする。システムプロキシがすでにClashを指していても、拡張機能側で「直接接続」や別のアドレスが設定されている場合、ブラウザが実際に使うのは拡張機能の設定であり、システムの設定ではない。これは最も見落とされやすい競合パターンで、調査時はまず全てのプロキシ系拡張機能を一時的に無効化し、プロキシが効くかどうかを確認した上で、拡張機能側で個別に設定するかどうかを決めるのがよい。
- ブラウザ内蔵のVPNや「セキュアブラウジング」的なネットワーク高速化機能。 一部のブラウザ(特に一部の国産ブラウザ)に内蔵されているネットワーク高速化スイッチは、システムプロキシを回避して直接接続を確立することがある。どう設定しても効かない場合、まずブラウザ自身の設定内でこの類の機能をオフにしてみる。
- PACスクリプトモードの設定ミス。 Clashが固定HTTPプロキシではなく自動設定スクリプト(PAC)を使用している場合、ブラウザがこのPACファイルを正常に取得できる必要がある。ブラウザで直接PACのアドレス(通常
http://127.0.0.1:<ポート>/proxy.pac)にアクセスしてみて、開けない場合はPACサービスが起動していないことを示すので、固定HTTPプロキシモードに切り替えた方が安定する。
調査の順序としては、まずブラウザ自身の「ネットワーク診断」を使うか、あるいは規則にヒットすることが分かっているドメインに直接アクセスし、Clashクライアントの接続パネルにこのレコードが表示されるかを確認する。表示されているが直結と表示されている場合は規則やポリシーグループの問題であり、全く表示されていない場合はブラウザがそもそもリクエストをClashに送っていないことを示すので、上記の4項目に戻って調査する。
3つ目の経路:端末がシステムプロキシに従わない理由
端末環境は最も誤解されやすい部分だ――多くの人はシステムプロキシをオンにすればコマンドラインツールも自動的に追従すると考えているが、Linux・macOSの端末ツールチェーンの大半はGUIのプロキシ設定を読み取らず、**環境変数**を参照している。
標準的な環境変数一覧
Unixの慣習に従う多くのコマンドラインツール(curl、wget、git、パッケージマネージャーなど)は以下の環境変数を読み取る:
export http_proxy="http://127.0.0.1:7890"
export https_proxy="http://127.0.0.1:7890"
export all_proxy="socks5://127.0.0.1:7891"
export no_proxy="localhost,127.0.0.1,.local"
この数行は現在の端末セッションでのみ有効で、ウィンドウを閉じると消える。長期的に有効にしたい場合は、~/.zshrc、~/.bashrcなど対応するシェルの起動スクリプトに書き込み、sourceして即時反映させる必要がある。WindowsのコマンドプロンプトやPowerShellも同様で、$env:HTTP_PROXY、$env:HTTPS_PROXYで現在のセッションに設定するか、システム環境変数に長期的に書き込むことができる。
よくある落とし穴
- 大文字小文字の不一致。 一部のプログラムは大文字の
HTTP_PROXYだけを読み取り、別のプログラムは小文字のhttp_proxyだけを読み取る。確実な方法は大文字小文字それぞれ1組ずつ書いておくことだ。 - SOCKSとHTTPポートの混同。 Clashは通常HTTPポートとSOCKS5ポートを同時にリスンしている(ミックスポートモードでは同一ポート)。環境変数のプロトコルヘッダと実際のポート種別を対応させる必要があり、プロトコルヘッダを間違えるとプロキシを迂回するのではなく接続失敗になる。
- Dockerコンテナ、SSHセッション内の環境変数は独立している。 ホスト側でプロキシを設定していても、コンテナ内部やリモートSSHセッションはデフォルトで継承しない。コンテナ・リモート環境内で個別に設定するか、
-eパラメータで明示的に渡す必要がある。 - パッケージマネージャーは独自の設定ファイルを持つ。 例えばnpmは
npm config set proxyで個別設定が必要、gitはgit config --global http.proxyが必要だ。これらのツールは環境変数を設定しても、自身の設定ファイルに別の値が書かれていると環境変数が上書きされてしまう場合がある。
| ツール | 環境変数を読むか | 追加設定の必要性 |
|---|---|---|
| curl / wget | 読む | なし |
| git | 読まない(デフォルト) | http.proxy 設定項目 |
| npm / yarn | 読まない(デフォルト) | proxy / https-proxy 設定項目 |
| docker CLI | 読む(コンテナ内は個別設定が必要) | コンテナ環境変数または daemon.json |
| Python requests | 読む | なし(標準環境変数に従う) |
TUNモード:単一スイッチに依存しない代替策
上記3方向を順に確認してもなお一部のプログラムがどうしてもプロキシを経由しない場合や、もう環境変数やブラウザ拡張機能を1つずつ設定したくない場合は、より根本的な方法としてTUNモードへの切り替えがある。TUNモードはシステム内に仮想ネットワークカードを作成し、ネットワーク層で全てのアウトバウンド通信をハイジャックする。アプリケーション層がシステムプロキシ設定や環境変数を読み取るかどうかに依存せず、理論上はバックグラウンドサービスやゲームクライアントを含むほぼ全てのネットワークリクエストをカバーできる。
TUNモードを有効にするには一般的に、クライアントを管理者/root権限で実行し、設定内でtunフィールドを有効化し、stack(gvisorまたはsystemなど)が自分のネットワーク環境と互換性があるか確認する必要がある。有効化後はシステムプロキシのスイッチをオフのままにしておいて問題ない。通信はすでにより下位の層でハイジャックされているためで、両方を同時に有効化しても通常は競合しないが、重ねて使う必要は特にない。
tun:
enable: true
stack: gvisor
auto-route: true
auto-detect-interface: true
調査フローのまとめ
「システムプロキシはオンにしたのに効かない」という状況に遭遇したら、あちこち手当たり次第に試すのではなく、以下の順序で確認することを推奨する:
- まずClashクライアントの接続パネルを見て、対応するリクエストが表示されているか確認する――表示されていない場合、通信がそもそもClashに送られていないので、まずシステムプロキシ設定が正しく書き込まれているか確認する。
- ブラウザの問題は、まずプロキシ管理系拡張機能とブラウザ内蔵のネットワーク高速化機能を優先的に調査する。この2つが最も見落とされやすい。
- 端末の問題は、まず環境変数が現在のセッションで有効になっているか確認し、次に具体的なツールが環境変数に従うのか、それとも独立した設定ファイルが必要なのかを確認する。
- 1つずつ調査するコストが高すぎる場合、または標準的なプロキシロジックに従わないプログラムが多数存在する場合は、直接TUNモードに切り替えて一括対応し、個別対応にこだわる必要はない。
システムプロキシ、ブラウザ拡張機能、環境変数、TUNモードは、本質的には互いに独立しつつも重ね合わせ可能な4種類の通信ハイジャック方式だ。現在の問題がどの層にあるかを明確にすれば、闇雲にクライアントを再起動するよりも調査効率がはるかに高くなる。