真正生效的是gomodcache,不是gopath;gomodcache显式设置后完全覆盖gopath对模块缓存路径的影响,go env gomodcache才显示真实路径,go clean -modcache也只清理该位置。

go env GOPATH 和 GOMODCACHE 哪个才决定模块缓存位置?
真正生效的是 GOMODCACHE,不是 GOROOT 或未显式设置的 GO111MODULE=on 下的 GOPATH。虽然默认情况下 GOMODCACHE 会 fallback 到 $GOPATH/pkg/mod,但一旦你显式设置了 GOMODCACHE,Go 工具链就完全忽略 GOPATH 对模块缓存路径的影响。
常见误操作是改了 GOPATH 就以为缓存位置变了,结果 go mod download 还往老地方写——因为 GOMODCACHE 没变。
- 查真实路径必须用:
go env GOMODCACHE(不是go env GOPATH) - 设置新路径只需:
export GOMODCACHE=/path/to/modcache(Linux/macOS)或set GOMODCACHE=C:\modcache(Windows) - 修改后要新开终端或
source ~/.zshrc,否则go命令仍读旧值 -
go clean -modcache清的永远是GOMODCACHE指向的位置,和GOPATH无关
为什么 ls $GOPATH/pkg/mod 看不到干净的 github.com/user/repo@v1.2.3 目录?
因为 Go 不直接在 GOMODCACHE 根目录下建可读路径,而是用符号链接 + 伪版本目录组合实现“逻辑可见、物理隔离”。你看到的 github.com/user/repo@v1.2.3 实际是个软链接,指向类似 github.com/user/repo@v1.2.3-0.20240101000000-abcdef123456 的哈希目录。
这个哈希目录才是真实存放源码、go.mod、.info 的地方;软链接只是方便命令行工具识别版本语义。
-
go list -m all显示的是软链接名,不是物理路径 - 手动
rm -rf github.com/user/repo@v1.2.3只删了链接,源码还在,下次go build仍能用 - 想确认某版本是否真存在,得进
$GOMODCACHE/cache/download/查.zip和.info文件 - 直接
ls $GOMODCACHE看到一堆@开头的链接 +cache/子目录,这是正常结构
go mod download -x 输出的路径为什么和 go env GOMODCACHE 不一致?
因为 go mod download -x 打印的是「下载物缓存」路径(即 $GOMODCACHE/cache/download),而 GOMODCACHE 是整个模块缓存根目录(含解压后的源码树)。两者是包含关系,不是并列关系。
典型输出如:GET https://proxy.golang.org/github.com/user/repo/@v/v1.2.3.zip → 下载后存为 $GOMODCACHE/cache/download/github.com/user/repo/@v/v1.2.3.zip → 解压到 $GOMODCACHE/github.com/user/repo@v1.2.3-...。
-
-x仅暴露下载阶段路径,不反映解压后源码位置 - 若
go mod download卡住,先检查$GOMODCACHE/cache/download是否有残缺.zip(比如只有.zip没.info) -
go mod verify失败时,错误信息里提到的路径通常来自cache/download下的.info文件校验失败 - CI 中建议加
ls -la $GOMODCACHE/cache/download/**/v1.2.3.*快速确认下载物完整性
切换分支后依赖没变,但 go build 还是重新下载模块?
大概率不是缓存失效,而是 go.sum 里记录的 checksum 和当前缓存中 .info 文件的校验和不匹配——这往往发生在你本地改过 go.sum、或从不同代理拉过同一版本、或磁盘写入中断导致 .info 损坏。
Go 构建时不会信任“目录存在”,它强制比对 go.sum 和 .info,任一不一致就拒绝使用缓存,并报 checksum mismatch。
- 不要手动编辑
go.sum,尤其不要删行或重排;提交前用go mod tidy -v校验 - 私有模块若配置了
GOPROXY=direct但漏了,direct后缀,会导致部分模块走 proxy、部分直连,checksum 来源不一致 -
go mod verify是最快复现问题的命令:它不编译,只做校验,失败时直接指出哪个模块的.info不匹配 - 磁盘满导致
go mod download写一半中断,cache/download里会残留无.info的.zip,删掉对应@v/vX.Y.Z.*全套文件再重试
.info 和 go.sum 对不上,或者 GOPROXY 配置让不同机器拉到了不同来源的同版本归档。golang免费学习笔记(深入):立即使用
在学习笔记中,你将探索golang的核心概念和高级技巧!











