go.mod 在修订时有 post-v0 模块路径 "git.example.com/owner/repo/v3" ...?

go.mod has post-v0 module path "git.example.com/owner/repo/v3" at revision ...?

我的同事在更新 go.mod 以具有 /v3 后缀 (https://github.com/golang/go/wiki/Modules#releasing-modules-v2-or-higher) 之前推送了一个标签 v3.0.1。我更新了模块路径 (go.mod) 和所有导入路径 (*.go) 来修复它,标记为 v3.0.2.

现在的问题是:

go get -v git.example.com/owner/repo@v3.0.2
go: finding git.example.com/owner/repo v3.0.2
go: git.example.com/owner/repo@v0.0.0-20190722053407-d85c4f69ad17: go.mod has post-v0 module path "git.example.com/owner/repo/v3" at revision 
d85c4f69ad17

找到这个:go build keeps complaining that: go.mod has post-v0 module path

所以,我删除了 v3.0.0v3.0.1 标签,将其指向最新提交,重新推送但问题仍然存在。

我注意到 go.mod 仍然将旧版本称为间接依赖:

require (
    git.example.com/owner.repo v0.1.2 // indirect

即使我把它改成/v3 v3.0.2,它也会自动恢复到v0.1.12

为什么?

我是不是漏掉了什么?


7 月 23 日星期二 05:54:56+07 2019

rm go.*
go mod init git.example.com/dependent/project
go mod tidy

go.mod现在已正确更新:

require (
-       git.example.com/owner/repo v0.1.2
+       git.example.com/owner/repo/v3 v3.0.2

但是go get -v git.example.com/owner/repo@v3.0.2仍然返回错误:

go: finding git.example.com/owner/repo v3.0.2
go: git.example.com/owner/repo@v0.0.0-20190722053407-d85c4f69ad17: go.mod has post-v0 module path "git.example.com/owner/repo/v3" at revision 
d85c4f69ad17

d85c4f69ad17master 中的最新提交)

我注意到 go.sum 中同时存在 v0.1.2v3.0.2:

git.example.com/owner/repo v0.1.2 h1:mCGJEmyrFDTCGkRfUIORpqdrNkSONQ6K+AcTNgxqveY=
git.example.com/owner/repo v0.1.2/go.mod h1:FfUKnyPrARCtAXQZ3BQVJI7h2eJ0UpQBMLg4bNs4Kdc=
git.example.com/owner/repo/v3 v3.0.2 h1:mJtDKLeiP8vMRSZo08i/k/KDbIoZTlKW2aWu7DUBvMM=
git.example.com/owner/repo/v3 v3.0.2/go.mod h1:64LE0ts0Lk9InIQyhPYGmnxs6LZIl6H4Iorl1EXfqxo=

例如,您可以用这个 hack 替换存储库:https://github.com/golang/go/wiki/Modules

require {
...
}

replace git.example.com/owner.repo v0.1.2 => git.example.com/owner.repo v3.0.2

或者您可以在您想要的提交散列处使用 go get

go get git.example.com/owner.repo@af044c0995fe

go get 将正确更新依赖文件(go.mod、go.sum)。

更多信息:https://github.com/golang/go/wiki/Modules#how-to-upgrade-and-downgrade-dependencies

或者对于最后一个示例,您应该清理缓存

  1. 删除 go.modgo.sum
  2. go cache clean
  3. go mod vendor

请关注我的go get指令:

go get -v git.example.com/owner/repo@v3.0.2

应该是:

go get -v git.example.com/owner/repo/v3@v3.0.2

从@quanta 扩展 ...

您正在做:

go get -v git.example.com/owner/repo@v3.0.2

因为它是 v3 模块,go get 命令应该在 @:

之前包含一个 /v3

go get -v git.example.com/owner/repo/v3@v3.0.2

一旦 v3.x.y 包是一个具有自己的 go.mod 的模块,那么当您使用 modules enabled 进行操作时,您几乎总是包含 /v3引用 v3.x.y 模块,包括:

  • 在命令行上 go get 的参数
  • .go 代码中为消费者导入语句
  • 消费者 go.mod 中的
  • require 语句 消费者 go.mod
  • 中的
  • replaceexclude 语句
  • v3 模块的 go.mod 文件的 module
  • v3 模块中 .go 代码中的内部导入语句导入 v3 模块中的其他包
  • 等等

一种思考方式是,模块的名称现在实际上是 git.example.com/owner/repo/v3,其中它的名称包括结尾的 /v3.

如果您是 vN 模块的使用者并且需要更新 .go 文件中的导入路径以包含 vN,那么 github.com/marwan-at-work/mod 是社区中常用的工具,可自动在所有需要的位置添加 /vN。另外,如果您是 v2+ 模块的模块作者,它还会自动将 /vN 放置在所有必需的位置。

来自 Go 模块 wiki 的 "Semantic Import Versioning" 部分:

If the module is version v2 or higher, the major version of the module must be included as a /vN at the end of the module paths used in go.mod files (e.g., module github.com/my/mod/v2, require github.com/my/mod/v2 v2.0.0) and in the package import path (e.g., import "github.com/my/mod/v2/mypkg").

我可能遇到过类似的问题,我更新了一个模块以使用 /v2 导入路径,但是获取模块总是返回有关无效的错误 go.mod

解决方案是 go get -u github.com/<me>/<pkg>/v2