确认卡在哪一段

用 Homebrew 自带命令把问题拆开:

brew update --verbose
brew doctor
brew config
brew install --display-times <formula>
brew fetch --retry <formula>
brew fetch --force-bottle <formula>
brew --cache <formula>

Homebrew 官方 Troubleshooting 建议先跑 brew updatebrew doctor,并在反馈问题时提供 brew configbrew doctorbrew gist-logs。这不是形式主义:没有这些输出,很难判断是网络、权限、旧依赖还是 formula 本身。

Bottle、GitHub 和 DNS 的排查方法

Bottle 下载慢,常见表现是进度条长时间不动;源码编译慢,则通常能看到编译输出,看基础连通性:

nslookup github.com
curl -I -L https://github.com --connect-timeout 10 -m 20
curl -I -L https://ghcr.io --connect-timeout 10 -m 20

Homebrew 的下载对象可能来自 GitHub、GitHub Container Registry 或项目自己的 release 地址。brew fetch --retry 能有限重试失败下载;--force-bottle 能帮助确认是否有可用 Bottle。若没有 Bottle,慢点可能是本机编译能力和依赖树,不是网络。

代理和环境变量设置

查看当前 shell:

env | grep -i '_proxy'
scutil --dns | grep nameserver | head

临时排查可以只对当前命令生效:

HTTPS_PROXY=http://127.0.0.1:7890 brew fetch --retry <formula>
NO_PROXY=localhost,127.0.0.1 brew install <formula>

不要把个人代理写入团队 Brewfile 或安装脚本。Brewfile 应表达「需要哪些工具」,不应该绑定某个人的网络出口。多人团队可以写一个 bootstrap 文档,说明哪些变量只允许本机设置,哪些依赖必须固定版本。

Mac 开发机和 CI 的限制

本机 Mac 追求可用和可维护,CI 追求可复现。CI 里不要每次无脑 brew upgrade,否则一个 formula 更新就能改变构建结果。建议:

brew bundle check || brew bundle install
brew install --display-times <formula>
brew cleanup -n

团队 Mac 则要记录芯片架构、macOS 版本、Homebrew 前缀和核心工具版本。Apple Silicon 与 Intel 的路径不同,/opt/homebrew/usr/local 混用会让 PATH 问题看起来像安装慢。

如果你经常在酒店、共享办公和跨境网络之间切换,Homebrew、GitHub、Docker、Vercel 的下载路径会一起抖动。可以准备独立开发者出海稳定专线作为开发环境基线,但仍要保留 brew config 和命令日志,方便复盘。

问题仍未解决时的排查方向

把问题缩小到一个 formula,贴出:brew configbrew doctorbrew fetch --retry -vcurl 结果、macOS 版本和芯片架构。不要把整个环境重装作为第一选择。重装能抹掉证据,也会把 PATH、证书和权限问题带到下一轮。

相关阅读

中文长尾问题写入开发者 SOP

开发者搜索经常是故障式长尾,比如「GitHub clone 很慢」「Docker pull 超时」「npm install 卡住」「Stripe 后台打不开」「Cloudflare 登录验证」。这些词要保留,但正文要把它们落到 DNS、代理变量、认证、CI runner、浏览器会话和团队权限上。

中文长尾说法工程化排查项团队记录字段
GitHub clone 慢DNS、HTTPS、SSH、仓库体积协议、耗时、错误日志
Docker pull 超时registry、镜像层、代理变量镜像名、runner、出口网络
npm / pnpm 卡住registry、lockfile、缓存、代理包管理器、版本、失败阶段
Stripe / Cloudflare 验证设备、浏览器、IP、2FA登录设备、角色、时间

这样写能覆盖中文长尾,同时保留开发者文章的证据链和可复用 SOP,而不是只给一个“换网络”的泛化建议。