開発環境 / macOS · · 読了まで約 19 分

Homebrew が止まる?brew と GHCR・Bottle CDN を Clash 分流で安定:macOS 実測(2026)

macOS の開発者向けパッケージマネージャである Homebrew は、brew updatebrew install の内部で公式の formula 索引・git 取得・Bottle(バイナリ配布)・GitHub 上の成果物をまたぐことが多く、接続先が一つに見えないままタイムアウトが出ることがあります。典型例はghcr.io(GitHub Container Registry)github.com 系ホスト、さらに Vercel 上の公式補助ドメインや各種 CDNへの分割ダウンロードです。本稿では、ターミナルの HTTP(S) を本機の Clash(mihomo)の mixed-port 等へ寄せDOMAIN 分流で formula/bottle/GHCR を同じ策略グループに揃える手順と、DNS(fake-ip)やログで名前と出口の食い違いを潰す観点を、コピーしやすい例と切り分けの手順でまとめます。

1. brew が触るホスト:formula・Bottle・GHCR のつながり

多くの読者は 「brew が動けば全部同じサイトから取っているはず」と思いがちですが、実際の取得は 索引とバイナリと git 履歴に分かれます。brew update は公式の更新フローを辿り、brew install は formula 定義に沿って 事前ビルド済みの Bottle があればその URL から、なければソースからビルドします。Bottle のホスト名として ghcr.io が頻出し、GitHub Container Registry(GHCR)経由の取得がボトルネックになりやすいのは、この分割構造が理由です。また formulae.brew.sh などメタ情報参照GitHub 上の tarball・release アセット、大きな依存を引くと オブジェクトストレージや CDN の別ドメインがログに現れます。片方だけ代理に乗り、もう片方が直連や遅い経路に落ちると、解像度の高いタイムアウトが残ります。

Python 系のパッケージ取得と同様、インデックスと実体ファイルが別ホストという考え方はそのまま転用できます。内部リンクとして pip と PyPI を Clash 分流する記事や、Node 向けの npm/pnpm とプロキシ環境変数の整理と思考の骨格は共通です。Git 作業全般は Git/GitHub CLI と HTTPS プロキシの記事も併読すると、git と curl の経路がズレないように整えやすいです。

2. ターミナル側:HTTP_PROXY と brew の出口を一本化

macOS のシステムプロキシだけに頼ると、Homebrew が起動するシェルや launchd 経由の子プロセスが別経路になることがあります。確実に揃えるには、開発用ターミナルの HTTP_PROXYHTTPS_PROXYhttp://127.0.0.1:(mixed-port) の形で Clash が応答する HTTP プロキシへ明示します(ポートは環境に合わせて読み替え)。brew 本体が内部で呼ぶ curl/gitもこの環境変数を継承しやすく、挙動の再現性が上がります。

企業環境で上流のパケットインスペクションがある場合、証明書エラーと単純なソケットタイムアウトは別物です。Clash 側のルールだけをいじっても直らないときは、OS の truststore や社内 CA の有無を先に確認してください。一時的な切り分けとして ALL_PROXY を併記する運用もありますが、socks と http の二重指定で逆に混乱することもあるので、まずは HTTP プロキシ一本から試すのが無難です。

# Example: zsh — adjust port to your mixed-port
export HTTP_PROXY=http://127.0.0.1:7890
export HTTPS_PROXY=http://127.0.0.1:7890

GUI の Clash クライアントでは macOS の Clash Verge Rev 初回セットアップを参照し、システムプロキシと TUN のどちらを主に使うかを決めると、ターミナルとブラウザの差異を減らせます。ただし brew はターミナル起点が支配的なので、環境変数ベースの方がブレにくい場面が多いです。

3. Clash 分流:ghcr.io・github.com・配布 CDN

環境変数でトラフィックを Clash に入れたうえで、rules の前段で Homebrew 関連ドメインを明示します。下例の PROXY_GROUP は手元の proxy-groups 名に置き換えてください。要点は ghcr.iogithub.com を同じ策略へ載せ、ログに出た objects.githubusercontent.com や release 系ホスト、formulae 参照先もまとめて追記することです。実運用では 広すぎる DOMAIN-SUFFIX だけに頼らず、verbose ログの実ホストを足すループが安定しやすいです。

# Mihomo / Clash Meta style — illustrative only
rules:
  - DOMAIN,github.com,PROXY_GROUP
  - DOMAIN-SUFFIX,githubusercontent.com,PROXY_GROUP
  - DOMAIN,ghcr.io,PROXY_GROUP
  - DOMAIN,formulae.brew.sh,PROXY_GROUP
  - DOMAIN-SUFFIX,brew.sh,PROXY_GROUP

大規模な購読ルールを併用すると、カスタム行が下流に追いやられ意図しない経路へ落ちることがあります。まずは十数行の DOMAIN 足場で挙動を固め、接続ログで伸びたホストを rule-providers へ昇格させると安全です。Bottle が大きい formula では 細いノードを避け、切断に強い出口を選ぶほうがトータルで速いこともあり、レイテンシ表示だけに惑わされない判断が効きます。

4. DNS と fake-ip:名前と策略がズレるとき

mihomo 系で fake-ip を使うと、アプリケーションが解決した名前と、ルール評価で参照する情報の対応がずれてタイムアウトが残ることがあります。HTTPS では SNI を Sniffer で復元して DOMAIN 判定へ載せる、該当ドメインだけ redir-host 寄りの扱いに寄せるなど、DNS 周りは fake-ip と redir-host の比較記事と同じ教科書的手当が有効です。加えて DoH を本格的に合わせるなら Clash Meta の DoH と fake-ip の整合手順も参照してください。

ブラウザだけ Secure DNS を有効にしていると、curl とブラウザで名前解決の物語が分かれるため、triage の再現性が落ちます。brew はターミナルスタックに近いので、システム全体の名前解決を一つの筋にそろえると原因切り分けが早くなります。

5. 公式とミラー併用:例外ルールと注意点

国内向け formula ミラーや bottle 用のキャッシュを使う場合でも、索引と実ファイルでホストが分かれる典型パターンは残ります。ミラーだけを直結したいときは NO_PROXY にその FQDN を足し、Clash 側でも DOMAIN で DIRECT を明示すると、海外ノードへ無駄に迂回しません。逆に公式へ戻す場面では、ミラー用の例外を残したまま混線する事故が起きやすいので、シェルプロファイルを用途ごとに分けると安全です。

Docker と併用して開発コンテナからホストの brew を直接は触らないケースでは、Docker をホスト Clash へ通す手順と照合し、コンテナ内の 127.0.0.1 がホストを指さない点だけ注意してください。ルールと購読の入口は サブスクリプションの取り込みルールルーティングの説明も併せて読むと整理が速いです。

6. ログとコマンドで切り分け

まず brew update -vbrew install -v パッケージ で、どの URL を順に取りにいったかをログへ残します。続けて curl -v -x http://127.0.0.1:7890 https://ghcr.io/ のように、プロキシ経由で GHCR の応答が返るかを切り分けます。Clash の接続ビューでは 策略名・chains・ホストの三点で見ると、意図しない DIRECT や遅いノードへ落ちていないかが判別しやすいです。

購読取得そのものが不安定なら 購読の TLS・DNS・ログの整理を先に直す価値があります。Homebrew の問題とノード品質の問題は層が違うため、curl と brew の verbose を併記したログを一枚にまとめるとチーム内共有も楽です。

# verbose examples
brew update -v
brew install -v jq

Intel/Apple Silicon の差は主にバイナリ互換ですが、取得 URL が増えるほどルール漏れの影響が表面化しやすい点は共通です。初回導入ユーザーは Intel Mac 向け Clash Verge Rev 手順で権限や拡張まわりを先に固めると、tun/システム代理との相性確認がスムーズです。

7. よくある質問

formula は見えるのに bottle だけ失敗します。
ghcr.io やログに出た配布ホストが別策略に落ちていないか確認し、DOMAIN 行を追記してください。brew install -v の URL 列と Clash の接続表を突き合わせるのが最短です。
Git operations を SSH にしている場合は?
SSH は HTTP プロキシの話とは別レイヤです。tun モードと併用するか、HTTPS での取得に切り替えられる範囲で経路を揃える必要があります。接続ログでプロトコル別に分けて見てください。
社内プロキシと二重になりませんか?
上流でさらにプロキシを要求される構成では、brew の環境変数と Clash の上流設定の双方を確認し、ループや認証ヘッダの衝突がないかを切り分けます。mihomo のログレベルを上げると原因が見えやすいです。

8. まとめ

Homebrew のタイムアウトは、単に「プロキシをオン」では足りず、formula 索引・GitHub・GHCR・CDN に分割される取得を同一の出口とルール束で扱うことが重要です。環境変数で Clash の HTTP プロキシへ集約し、DOMAIN 行で ghcr/github 系を明示し、DNS と接続ログで名前の食い違いを潰す、この三層がそろうと brew update/brew install の再現性が大きく上がります。

同種のテーマでは、汎用 VPN 型クライアントや更新の止まった GUI ラッパーは、ホスト単位の接続ログが薄く、開発ツールチェーンのようにドメインが増え続ける作業に弱く、原因特定に時間が溶けがちです。ルールとログを素直に読める mihomo 系のデスクトップ GUI では、verbose に出た FQDN をその日のうちに追記する運用が現実的で、npm/pip/docker pull と横断するチームほど効きます。

自分の環境に合うビルドを選び、ポートと策略を確認しながら試すなら、 → 公式ページから無料で Clash をダウンロードし、分流とログを試す のが手早いでしょう。

トピックの近さで選んだ関連記事 — 同じカテゴリの Clash 実践ガイド。