核心是git tag必须为vx.y.z格式且go.mod的module路径须与仓库地址完全一致,否则go get失败、模块系统无法识别、ci/cd发布中断;其他操作均为围绕这两点的补充。

Go 项目要让下游能正确 go get 到版本、模块系统能识别、CI/CD 能自动发布,核心就两点:Git tag 必须是 vX.Y.Z 格式,且 go.mod 的 module 路径必须与仓库地址完全一致。其他所有操作——注入版本号、生成 CHANGELOG、自动 bump——都只是围绕这两点的补充。
git tag 必须是 v1.2.3,不是 1.2.3 或 release/v1.2.3
Go 模块系统只把形如 v1.2.3、v0.1.0、v2.0.0-rc.1 的 tag 当作有效语义化版本;1.2.3、release-v1.2.3、v1.2.x 全部被忽略,go list -m -versions 不显示,go get @v1.2.3 直接失败。
- 打 tag 前先确认当前 commit 乾净:
git status无未提交变更,git diff --quiet退出码为 0 - 命令必须带
v前缀:git tag v1.2.3,不是git tag 1.2.3 - 推送时显式指定 tag 名:
git push origin v1.2.3,避免git push --tags误推测试 tag 或旧 tag - 如果打错了,立刻删掉重来:
git tag -d v1.2.3 && git push origin :refs/tags/v1.2.3
go.mod 的 module 路径必须和仓库地址完全匹配
你的代码托管在 github.com/user/repo,那 go.mod 第一行就必须是 module github.com/user/repo;若已升级到 v2,就必须是 module github.com/user/repo/v2,且对应 tag 必须是 v2.0.0。
初始化并管理阿里云SDK Go 客户端,涵盖 sync.Once 单例、goroutine 安全、endpoint 与 region 配置、VPC 端点及调试。
- 常见错误:fork 后改了
go.mod中的 module 名,但没同步更新所有 import 路径,导致依赖方import "github.com/user/repo"时拉不到 - 子模块路径(如
/v2)必须显式出现在go.mod和所有import语句中,否则go get @v2.0.0报unknown revision - 私有仓库需配置
GOPRIVATE=*.your-company.com,否则 Go 会尝试走 proxy.golang.org,返回 404
用 go build -ldflags 注入版本信息时,变量必须可导出且路径准确
go build -ldflags "-X main.Version=v1.2.3" 看似简单,但漏掉任一条件都会导致运行时输出仍是 "dev"。
- 变量必须首字母大写、定义在可导出包中,例如
var Version = "dev"在cmd/myapp/main.go里,那么 -X 参数必须写成-X main.Version=... - 如果变量在
internal/version/version.go,路径就得是-X internal/version.Version=...,不能简写 - CI 中建议从 Git 提取:用
git describe --tags --exact-match 2>/dev/null || echo "dev"获取精确 tag,避免v1.2.3-5-gabc123这类 dirty 版本混入生产二进制 - macOS 上
date不支持%s,统一用$(date -u +%Y-%m-%d)避免跨平台失败
CHANGELOG 生成依赖 Conventional Commits 解析,不是 git log --oneline
自动生成 CHANGELOG 的关键不是“列出所有提交”,而是结构化提取 feat:、fix:、break: 等前缀,并按 scope 分组。裸用 git log --oneline 只能得到一堆不可读的摘要。
- 推荐解析命令:
git log --pretty=format:"%H|%s|%b" v1.2.2..HEAD,再用正则匹配^(feat|fix|docs|test|refactor|chore)(\(.+\))?: - scope 提取很重要:比如
feat(api): add user endpoint应归入 “API” 分类,而非笼统的 “Features” - 预发布版本(如
v1.2.0-rc1)的 tag 必须存在,否则git log v1.2.0-rc1..HEAD会报错,脚本中断 - CHANGELOG.md 追加时,注意保留原有格式(如 # Changelog 标题、空行分隔),避免 CI 重复追加破坏 Markdown 结构
最容易被忽略的是:tag 推送成功 ≠ 模块可用。真正决定下游能否拉到的,是 proxy.golang.org 是否已完成索引——这可能延迟几十秒到几分钟。发布后务必用 go list -m -versions your/module 和 GO111MODULE=on go get your/module@v1.2.3 -v 实际验证,别只看 git push 输出。
golang免费学习笔记(深入):立即使用
在学习笔记中,你将探索golang的核心概念和高级技巧!










