github actions 中 go test 失败主因是 go 版本不匹配、未启用 go modules(需 setup-go@v4 + go.mod + go mod tidy + go111module=on);-race 需配 -timeout 并避免高并发/sleep;跨平台构建须设 cgo_enabled=0 和 matrix;模块缓存 key 应基于 go.sum 哈希,路径为 ~/go/pkg/mod,并配置 goproxy 防超时。

Go test 在 GitHub Actions 里跑不起来?先检查 go 版本和模块初始化
GitHub Actions 默认环境不一定装了你本地用的 Go 版本,更常见的是没启用 Go modules —— 这会导致 go test 报 no Go files in 或找不到依赖。
- 必须在 workflow 中显式用
actions/setup-go@v4指定go-version,别依赖系统自带 - 项目根目录要有
go.mod;如果还没初始化,CI 里go mod init不够,得先go mod tidy拉依赖(否则测试会因 import 失败) - 确保
GO111MODULE=on,虽然新版本默认开启,但某些旧 runner 仍可能 fallback 到 GOPATH 模式
go test -race 在 CI 里失败但本地正常?注意并发资源与超时
竞态检测器(race detector)本身开销大,CI 环境 CPU/内存受限,容易触发超时或假阳性失败。
-
go test -race必须搭配-timeout,比如-timeout=60s,否则默认 10 分钟可能卡死在某个 goroutine 上 - 避免在测试中启动大量 goroutine 或 sleep 循环;
time.Sleep在 race 检测下行为更敏感,优先用sync.WaitGroup或 channel 控制 - 某些第三方库(如
github.com/gorilla/mux旧版)自带竞态问题,CI 失败未必是你的代码问题——先go list -m all | grep -i race看依赖是否已知有问题
构建二进制时 GOOS/GOARCH 混用导致产物不可用
CI 默认是 Linux x86_64,但如果你在 workflow 里手动设了 GOOS=windows 却没配交叉编译工具链,go build 会静默失败或产出空文件。
- 跨平台构建必须显式指定
CGO_ENABLED=0(除非你真需要 C 依赖),否则会报exec: "gcc": executable file not found - 多平台打包建议用 matrix:一个 job 跑
GOOS=linux GOARCH=amd64,另一个跑GOOS=darwin GOARCH=arm64,别试图在一个 job 里循环构建 - 产物路径要带平台标识,比如
./build/myapp-<code>$(go env GOOS)-$(go env GOARCH),否则 Windows 构建覆盖 Linux 构建
缓存 go mod download 无效?关键在 cache key 的粒度
很多人加了 actions/cache@v3 却发现每次还是重下模块,根本原因是 cache key 没包含 go.sum 或 go.mod 的哈希,导致 key 总是变化。
- cache key 应基于
go.sum文件内容,例如:${{ hashFiles('**/go.sum') }};只用${{ hashFiles('go.mod') }}不够,因为go.mod可能没变但go.sum已更新 - 缓存路径必须是
~/go/pkg/mod(Linux/macOS)或%USERPROFILE%\go\pkg\mod(Windows),不是项目下的vendor/ - 如果用了
go mod vendor,就别缓存pkg/mod,改缓存vendor/目录,但要注意go test默认不读 vendor,需加-mod=vendor
最常被跳过的其实是 go env -w GOPROXY=https://proxy.golang.org,direct 这一行——国内 CI 经常因代理不通直接卡在 go mod download,不报错只超时。加这行比换镜像源更稳。











