Mac硬盘扩容之后,最折腾的不是把数据倒回来,而是把开发环境重新支起来。尤其是git和node这两个工具,平时安安静静,一到换盘、迁移、重装系统就各种闹脾气:git命令敲下去还能跑,但推送时密钥对不上;node版本看着是对的,npm一装全局包就报路径错、权限错。这篇文章就来聊一个很实际的问题——Mac硬盘扩容后,如何重装git和node,而且尽量装得干净,把该留的配置留住,把不该留的残留全部清掉。适合正在换硬盘、刚重装完系统、或者被开发环境折腾得想砸电脑的朋友参考。
1. 为什么硬盘扩容后要重新搭开发环境
1.1 扩容最常见的几种场景,跟开发环境的恩怨
Mac用户说要扩容,一般跑不掉这几种情况:一是把内置硬盘换成容量更大的型号,比如从256GB换到1TB;二是硬盘空间不够,干脆格式化重装系统顺便换个环境;三是用外置硬盘或者网络存储来分担压力。不管是哪种,最终都要面对同一个问题——原来系统里的开发环境还能不能继续用。
我见过不少朋友,扩容之后直接用系统自带的迁移助手把整个用户目录搬过去,表面上数据都在,打开终端,git和node也都能找到,但真到干活的时候就开始出幺蛾子。某开发者跟我说过,他迁移完以后npm install经常报路径相关的错误,后来才发现是全局node版本和某个项目要求的版本冲突,旧缓存和新路径混在一起,怎么查都查不清楚。最后花了整整一下午才解决,比重新装一遍还累。
为什么会这样?因为git和node这类开发工具,不是单纯的文档或者App,它们牵扯的东西很多:可执行文件的存放路径、动态库的链接关系、环境变量里的PATH、全局包的位置、SSH密钥和配置文件,还有各种缓存目录。这些信息有的是绝对路径,有的跟随旧系统盘的目录结构,一旦系统盘换了位置,很多隐形的线索就断了。表面上命令还能用,底层已经千疮百孔。
1.2 “更干净”到底意味着什么
我理解的干净重装,不是简单地把旧文件清一清,再装个新的完事,而是一个有取舍的过程:不留旧目录里的软链接残留,不把上个系统时期的PATH配置带过来,不顺着迁移助手的套路把旧包一股脑搬回来。该重装的重装,该手动恢复的手动恢复,该清理的缓存彻底清干净。
这样做的价值不只是看着舒服。干净的环境,意味着以后排查问题时线索清晰——你知道git一定是Homebrew装的,node一定是某个版本管理器装的,全局包装在哪里心里有数。而不干净的环境,最常见的结果就是:出问题了先怀疑自己写错代码,折腾半天才发现是环境里残留了两个node互相打架。
所以接下来这套流程,核心思路是:先全面盘点,再彻底清理,然后从零安装,最后手动恢复个人配置。总共四步走下来,你的环境会比以前清爽得多。
2. 动手之前,先盘点和备份
2.1 五分钟摸清当前环境
在删任何东西之前,我强烈建议你先花五分钟看清当前环境到底装了些什么。这一步看起来费时间,实际上能省掉后面大量的踩坑时间。而且很多人在卸载之前根本不知道自己装的是哪种方式,结果清了一个,另一个残留还留在那里继续捣乱。
我给自己定了一套标准检查流程,就几条命令:
which git which node which npm git --version node -v npm -v brew list --formula | grep -E "git|node" uname -m这几条命令分别能告诉你:git和node装在哪个可执行目录、当前版本号是多少、是不是由Homebrew管理的、你的Mac是Apple Silicon(arm64)还是Intel(x86_64)。后面这个东西尤其关键,因为Apple Silicon上的Homebrew默认装到/opt/homebrew,而Intel Mac是/usr/local,路径不一样,PATH配置也不一样,很多人环境出问题就是栽在架构判断上。
然后打开终端配置文件看一眼。现在的Mac默认shell是zsh,所以主要看这两个文件:
cat ~/.zshrc cat ~/.zprofile如果有用bash的话,再看~/.bash_profile和~/.bashrc。这里记录了大量环境变量的设置,比如export PATH=...、source nvm.sh之类的行,这些就是待会儿要清理的地雷区。
2.2 需要带走的“家当”只有这四样
盘点完了就要决定备份什么。我的原则是:能重新生成的坚决不备份,只有真正属于个人配置的才值得带走。按照这个标准,其实需要带走的就四样东西。
第一样是~/.ssh文件夹。里面存着你的SSH密钥,这是访问代码托管平台和远程服务器的通行证,丢了就只能重新生成并重新配置。备份它的时候我建议整个目录拷贝走,但拷贝之前先看一眼里面有没有不用的旧私钥——有的话就只挑常用的带走,省得把垃圾config一起搬过来。
第二样是~/.gitconfig文件。这里面存了你的git用户信息、提交签名、别名等配置。如果你有多个身份,比如个人的和工作项目的,可以把对应的includeIf配置也一起记下来。
第三样是~/.npmrc。这里存了你对npm的个性化配置,比如registry地址、缓存位置等。别小看这个文件,少了它,很多全局配置要重来。
第四样是npm全局包的清单。不用备份包本身,只要记下名字就行。执行:
npm ls -g --depth=0 > ~/backup/npm-global.txt等下安装完再看着这个清单一个一个装回来。全局包这种数据,版本更新换代非常快,你辛辛苦苦备份的完整内容,过几个月可能就全是过时依赖了,所以保留清单比保留实体明智得多。
除了这四样,像项目里的node_modules、Homebrew的旧安装包、npm缓存、各种Library/Caches里的内容,一律不用也不应该备份。它们体积大、容易坏、还能随时重建,带了反而是负担。备份完以后,把这四样东西统一放在一个目录里,比如~/backup,然后放到移动硬盘或者其他安全的地方,这一步别省。
3. 彻底卸载残留的git与node
3.1 先拆git:三种安装形态分别怎么清
git在Mac上的存在形式其实有几种情况。一种是Homebrew装的,一种是带图形界面的安装包装的,还有一种是系统自带的跟CommandLineTools绑定在一起的。清理之前先分清是哪一种,不然容易误删。
如果是Homebrew安装的,卸载命令很简单:
brew uninstall git如果想要更彻底,还可以把相关的依赖一并清掉:brew autoremove。不过这条命令要小心,它会把所有不再被依赖的包都删掉,如果你还有别的工具靠这些依赖活着,可能会被一起拆了。我一般不推荐刚装完就用,还是手动逐个检查更稳。
如果是用安装包装的,比如在某官网下载的dmg或者pkg格式,那卸载要手动一点。这类安装一般都会把git可执行文件放到/usr/local/bin或者/opt/homebrew/bin下,同时带一份文档和引用文件在某些目录里。你可以用which git先看路径,然后顺着路径往上找对应目录,把git相关的可执行文件、符号链接和文档目录清理掉。如果当年是手动编译源码安装的,还要注意/usr/local下面有没有git的源码目录或者版本目录。
至于系统自带的git,你不需要专门卸载它,它属于CommandLineTools的一部分,等会儿我们装新git的时候,只要新工具出现在PATH的前面,系统自带的就会被压住。如果非要确认,可以用ls -l /usr/bin/git看一眼它的指向,那是给Xcode用的,不影响我们使用。
无论哪种方式,卸载完成后建议检查一下:
which git这一步输出应该是“git not found”或者告诉你它还在/usr/bin下面,这都算正常。如果which git还指向旧的/usr/local/bin/git,说明还有残留,回到上面再清一遍。
3.2 再拆node:清理要狠,路径别留
node的安装方式比git还要复杂一点,因为它常见的装法就有三种:用Homebrew装的、用nvm(或者别的版本管理器)装的、用官方pkg安装包装的。三种方式的卸载手段完全不一样,混着装的情况也不少见,所以要先看which node的输出路径来猜它是什么类型。
如果路径里带有~/.nvm/versions/node,说明是nvm管理的,那卸载方法很简单:先清空nvm本身,再删掉配置。直接执行rm -rf ~/.nvm,然后打开~/.zshrc把nvm相关的加载语句删掉。nvm的特点是它所有node版本都存在~/.nvm下面,删掉整个目录就等于把全部版本连根拔起,很干净。
如果路径在/opt/homebrew/bin/node或者/usr/local/bin/node,大概率是Homebrew装的。卸载命令是:
brew uninstall node如果有多个版本存在(比如之前升级过又没清理),可以用brew list --versions node查看有没有残留的版本,然后brew autoremove收拾一下依赖。
如果是用官方pkg安装包装的,麻烦一点,因为系统不知道它被注册成什么样子,只能手动删。你需要在/usr/local/bin/node、/usr/local/bin/npm、/usr/local/include/node、/usr/local/lib/node_modules这些路径下把node相关的文件和目录清理掉。有些安装包还往/usr/local/share/man/man1下面塞了node的man手册,也可以顺手删了。
删除node本体之后,还有两块残留必须清。第一块是全局包目录,旧系统上的node_modules可能会留在/usr/local/lib/node_modules或者/opt/homebrew/lib/node_modules,这些要整个删掉,否则新node装完后,全局包可能还在但版本号是旧的,排查起来特别迷惑。第二块是npm缓存,在~/.npm目录里。npm cache clean --force这个命令可以在卸载前跑一下,或者干脆把~/.npm整个删掉,因为这些都是缓存数据,删除不影响任何配置,重新安装node以后会自动重新生成。
清理完了记得重新加载一下配置文件,或者干脆开一个全新的终端窗口,再跑which node,确保任何路径下都找不到旧的node了,才算真正干净。
3.3 顺手把shell配置里的“地雷”排掉
很多人的环境问题根本不在git和node本身,而在shell配置文件里残留的PATH。卸载完软件之后,这些配置还躺在~/.zshrc里,它们会告诉系统去哪找命令,结果系统去找的地方已经被我们删光了。这样一来,新装的git和node不但没法正常工作,反而会和旧路径互相干扰。
打开~/.zshrc,重点找三类内容。第一类是export PATH=...的行,尤其是包含旧node路径、旧git路径、旧npm全局包路径的,比如export PATH="/usr/local/lib/node_modules/bin:$PATH"这种,该删就删。第二类是各种source和eval语句,比如nvm的加载脚本[ -s "$HOME/.nvm/nvm.sh" ] && source "$HOME/.nvm/nvm.sh",这个在删完~/.nvm以后就完全没用了,留着只会输出没意义的报错。第三类是各种alias,比如给旧命令起的快捷方式,也要看清楚删掉。
我个人的操作习惯是:先把~/.zshrc完整复制一份备份成.zshrc.bak,再开始逐行清理。这样万一改错了还能秒恢复。改完以后执行source ~/.zshrc,然后开新终端验证一下PATH里是否还残存旧目录的痕迹:
echo $PATH这一步的输出应该是一个干干净净的路径列表,不再包含任何旧node或者git的路径。只要有看到类似/usr/local/lib/node_modules这样的字符串,说明还有漏网之鱼,回去继续找。
到这一步,你的系统基本回到了“刚开机、没额外装开发工具”的状态,后面就可以踏踏实实从零开始了。
4. 从零安装git与node
4.1 前置准备:CommandLineTools缺不了
正式开始装之前,有一件事必须确认:Mac的命令行工具链装好没有。你可以先敲:
xcode-select -p如果能输出路径,一般是/Library/Developer/CommandLineTools,说明已经装好了。如果没装,会提示,这时执行:
xcode-select --install然后等系统弹出安装窗口,大概几分钟装完。这个东西不是Xcode本身,只是一个精简的命令行工具集,包含clang、make等基础编译器。你可能想:我又不编译源码,装它干嘛?等你确实需要编译某个包或者某个原生模块的时候,没有它就会当场卡住,报一堆莫名其妙的错误。所以这个前置步骤,无论你是纯前端还是做全栈,最好都走一遍。
4.2 装git:走Homebrew比直接下包更省心
新系统上建议统一用Homebrew来装git。原因很简单,Homebrew能帮你管理可执行文件的路径、版本升级和卸载,以后想换个版本或者更新到最新版,一条命令就搞定,比自己手动下载安装包省心多了。如果之前系统里没有Homebrew,先装它。装完以后,先确认一下你的Homebrew目录在哪:
which brew在Apple Silicon机器上一般是/opt/homebrew/bin/brew,Intel机器上是/usr/local/bin/brew。然后安装:
brew install git装完以后检查一下which git是不是指向了Homebrew目录下的git。如果是,说明PATH的优先级没问题,系统自带的git被压住了。如果还是指向/usr/bin/git,那需要把Homebrew的bin目录加到PATH的最前面,在~/.zshrc里添加类似这样的行:
export PATH="/opt/homebrew/bin:$PATH"然后重新加载配置,再确认一次。
装完不要急着写代码,先把git的基础配置设好:
git config --global user.name "你的名字" git config --global user.email "你的邮箱"这两项是提交代码必须的。如果你还有更多的习惯配置,比如默认编辑器、别名、颜色输出等,也顺手配一下。这里有个小技巧:如果你的个人项目和工作项目用的身份不一样,可以按目录配置不同的includeIf,这样以后在哪个目录下提交,就用对应的身份,省得每次切换。
4.3 装node:用fnm做版本管理
node的安装,我现在的首选方案是用版本管理器,而不是直接下载官方安装包。为什么?因为你在实际做项目的时候,经常会遇到“这个老项目要用node 14,那个新项目要node 22”的情况,直接用版本管理器切换版本最省事,还能避免全局包和系统版本强绑定。版本管理器里,我推荐试试fnm,它和nvm相比,最大的优势是速度快、天然支持Apple Silicon,而且是原生的shell加载方式,配置起来很干净。
用Homebrew安装fnm最方便:
brew install fnm装完以后,在~/.zshrc里加上一行初始化代码:
eval "$(fnm env --use-on-cd)"然后重新加载配置。之后就可以安装node了,我建议装LTS版本:
fnm install --lts fnm use lts-latest fnm default lts-latest第一条命令会下载并安装最新LTS版本的node,第二条命令在当前终端激活它,第三条命令把默认版本设为LTS,这样每次打开新终端,node都是这个版本。装完以后验证一下:
node -v如果输出的是你安装的版本号,说明环境已经通了。如果你更习惯用nvm,也可以继续用nvm,只是它加载起来略慢,而且某些配置在Apple Silicon上有轻微兼容问题。重点不是选哪个,而是你要知道你的node是通过版本管理器管的,以后升级和切换都在这个管理器里操作,而不是再去官网下载安装包折腾。
4.4 恢复配置:SSH密钥、git身份、npm全局包
环境装完,接下来把个人配置请回来。这一步的顺序很重要,一定是在git和node都装好、基础版本验证无误之后再恢复,不然容易造成二次混乱。
先把之前备份的.ssh目录拷贝回用户目录:
cp -r ~/backup/ssh ~/.ssh然后用chmod把权限收紧:
chmod 700 ~/.ssh chmod 600 ~/.ssh/*这一步很多人忽略。SSH密钥的权限如果太宽松,系统会拒绝使用。不是开玩笑,新系统上如果权限是默认的644,跑ssh的时候直接被拒,报权限过宽的提示,你可能会觉得莫名其妙。所以这个chmod必须做。
接着测试一下SSH是否能用。用你常访问的代码托管平台,在账户设置里把~/.ssh/id_ed25519.pub的内容粘贴到SSH Keys配置处,然后执行类似下面这样的命令来验证:
ssh -T git@你的托管平台地址如果看到一串欢迎信息,说明SSH通道已经通了。如果没有,检查密钥是否放对位置、权限是否正确、远程端的公钥是否添加成功。这一步拿下了,后面推送代码就无忧。
git的用户身份我之前已经用git config设置过,这里再确认一遍就好。如果你还有签名密钥、diff工具、别名之类的习惯配置,都在这时候一起写进~/.gitconfig。
然后恢复npm全局包。打开备份的清单文件看一眼:
cat ~/backup/npm-global.txt一条一条装回去。我建议装之前先冷静一下:你真的需要这么多全局工具吗?很多人装了五六个全局脚手架,可能其中一大半一年都用不上一次。全局包越少,环境越清爽,以后升级node也少一点麻烦。所以我的建议是,挑出真正常用的三四个装回,其他的用到再装。
5. 安装完别急着开发,先过一遍验证和排坑
5.1 一套完整的验证清单
环境搭好以后,千万不要直接打开老项目就开始写代码。磨刀不误砍柴工,先把下面这套验证清单过一遍,最多五分钟,跑完基本就能确认环境是不是健康的。
我常用的验证顺序是这样的:
which git git --version which node node -v npm -v npm ls -g --depth=0 echo $PATH ssh -T git@你的托管平台地址这里检查的每一个项目都有意义:which命令确认可执行文件路径是我们预期的那条;版本号确认安装成功;全局包列表确认哪些工具还在;PATH确认没有旧路径残留;SSH测试确认远程通道正常。
最后,建议再做一个真实项目压力测试。找个老项目的目录,删掉node_modules和lock文件,重新执行一次install:
cd ~/your-project rm -rf node_modules npm install如果整个安装流程能顺利跑完,项目能正常启动,你的开发环境就基本算站住了。这一步比任何单独检查都实在,因为环境真不真实,只有在真实项目里跑过才知道。
5.2 常见问题速查表
我在帮别人折腾环境的时候,发现不少问题特别典型,而且都是有固定套路的。这里整理一个速查表,以后遇到直接照着排查。
| 现象 | 可能原因 | 处理办法 |
|---|---|---|
| git command not found | Homebrew路径没进PATH | echo $PATH检查,把brew的bin目录加进去 |
| node command not found | fnm/nvm没有初始化或没开新终端 | 重新source配置,开新终端 |
| SSH报权限过宽 | 密钥权限太宽 | chmod 700 ~/.ssh;chmod 600 ~/.ssh/* |
| npm install编译报错 | 缺少CommandLineTools | 补装xcode-select --install |
| brew update很慢 | 网络原因 | 换用可访问速度更快的镜像源 |
| git推送时提示身份不明 | 用户信息没配 | git config --global user.email/user.name |
| node版本总自动跳 | fnm/nvm没有设置默认版本 | 执行fnm default lts-latest |
这些问题的处理思路,核心原则就一句话:先确认系统在哪个目录找命令,再确认命令是不是我们装的那个,然后一层层往下缩。绝大多数环境问题,本质上都是路径和身份问题,很少是工具本身坏了。
5.3 踩过几次坑后的小建议
最后说一点我自己的真实感受。硬盘扩容这件事,最容易犯的错误就是迷信迁移助手。我见过太多人,为了省事把整个用户目录原封不动搬过来,结果环境里的线索全断了,最后反而比从零装更费劲。我的做法是:迁移助手只用来搬文档、照片、项目文件这些内容型数据,开发环境一律手动重装,配置手动恢复。这样虽然前期多花半小时,后续几个月的维护都要省心得多。
另外,环境重装完以后,花十分钟把自己的安装习惯固化下来。比如以后装node、装git一定用Homebrew,全局包一定从清单里挑,cache目录定期清理。这些规矩看起来不起眼,但长久坚持下来,你的Mac会比大多数人干净很多。就算下次再换硬盘,整个过程也能压缩到一顿午饭的时间。
好了,这套流程跑完,你已经拥有了一个几乎全新的开发环境。去忙吧,这次它应该不会再给你添乱了。