预发布标签需显式加 -pre 参数才被 go list -m -versions 显示,且要求标签格式合规(用短横线)、go.mod 模块路径与主版本一致、远端上下文(权限/代理/CI fetch)完整。

预发布标签不被 go list -m -versions 显示?先确认是否真打了带 - 的语义化标签
Go 工具链默认只列出正式版(vMAJOR.MINOR.PATCH),预发布标签如 v1.4.0-rc1、v2.1.0-beta.2 必须显式加 -pre 参数才可见。常见错误是打完 git tag v1.4.0-rc1 后直接跑 go list -m -versions example.com/lib,结果为空——这不是标签没推,而是命令没告诉 Go “我要看预发布”。
正确做法:
- 打标签时严格用短横线
-,不能用下划线_或空格:git tag v1.4.0-rc1✅,git tag v1.4.0_rc1❌ - 推送时明确指定标签名:
git push origin v1.4.0-rc1,避免用git push --tags(可能混入本地测试标签) - 查版本时加
-pre:go list -m -versions -pre example.com/lib
go.mod 路径与标签主版本不匹配,导致预发布标签被忽略
标签名和 go.mod 中的模块路径必须语义一致。比如打了 v2.0.0-rc1,但 go.mod 仍是 module example.com/lib(没带 /v2),Go 会认为这个标签属于 v1 分支,直接跳过。
验证方式:go list -m -versions example.com/lib/v2 若返回空,说明要么远端没该标签,要么 go.mod 没同步改路径。
立即学习“go语言免费学习笔记(深入)”;
关键检查点:
- 预发布前,确保对应 commit 的
go.mod已更新为module example.com/lib/v2 - 所有内部 import 必须同步改为
example.com/lib/v2,Go 不自动重写 - 标签必须打在这个修改后的 commit 上,不能打在上一个 v1 的提交上
私有仓库或内网环境里,预发布标签“存在但不可见”
即使 git ls-remote --tags origin 能看到 v1.4.0-rc1,go list 仍可能报 no matching versions。这通常不是标签问题,而是模块发现机制被拦截。
优先排查三件事:
-
GOPROXY配置是否含,direct:例如GOPROXY=https://goproxy.cn,direct,缺,direct会导致私有域名或未缓存标签无法回源 -
GOSUMDB=off是否启用:内网若无法访问sum.golang.org,校验失败会静默丢弃标签,设为off可绕过 - 远程仓库权限:确保
go list执行机有读取该仓库 tags 的权限(尤其 GitHub/GitLab 私有 repo)
CI/CD 流水线里预发布标签被自动过滤
很多 CI 工具(如 GitHub Actions、GitLab CI)默认只 checkout 最近一次 commit,不 fetch tags;或者使用 shallow clone,导致 git tag -l 在构建机上根本看不到你刚 push 的 v1.4.0-rc1。
典型表现:本地 go list -pre 正常,CI 日志里却提示无版本。
修复动作:
- 在 CI 脚本开头加
git fetch --tags(GitHub Actions 可设fetch-depth: 0) - 避免用
actions/checkout@v3默认配置,显式声明fetch-tags: true - 打标签后,CI 触发的 job 必须基于该 tag 的 commit 运行,不能只靠 branch trigger
go.mod 路径是否同步、远端上下文(权限/代理/CI fetch)是否完整。漏掉任意一环,go get example.com/lib/v2@v2.0.0-rc1 就会报 unknown revision。


















