使用伪版本和GoCenter

更新:截至2021年5月1日,GoCenter中央存储库已经关闭,所有功能都已弃用。有关中心日落的更多信息,请阅读弃用博客文章
Go模块为Go开发带来了秩序,但也潜藏着一些混乱。管理模块伪版本可能会很困难,特别是对于Go的一些最新更改。
JFrog GoCenter的免费存储库去模块,现在包含了一些重要的更新,可以帮助你坚持下去。让我们来看看伪版本是如何工作的,以及您可以从这些更改中得到什么。我们还提供了一些指导,帮助您在升级到Go 1.13和更高版本时保持Go构建正常工作。
Go模块版本控制
版本的能力去模块是一个关键特性,为开发人员提供了一种方法来确保他们的应用程序使用他们想要的依赖项。当模块被版本化时,应用程序可以指定使用他们知道的模块版本,该模块版本将与运行时的其余部分兼容。
Go模块的版本是通过在底层源存储库中标记其修订版本来分配的。的去命令使用语义版本控制标准形式的vX.Y.Z描述模块版本。版本号根据API的变化而变化:

从这个标准格式中,可以比较模块版本,以确定哪个应该被认为是最新的,哪个应该被认为是最不最新的。
使用Pseudo-Versions
版本化的Go模块是为一般用途而发布的模块,应该是大多数开发人员的首选。但是,在某些情况下,您无法发布模块的最新版本。
例如,一个团队可能需要在开发期间共享一个临时版本。当一个依赖的项目还没有发布版本,所以它还没有被标记为版本时,这种情况尤其明显。类似地,您可能需要针对尚未标记的提交进行开发。
要使用模块的未标记版本作为依赖项,它必须由其pseudo-version标识符。伪版本具有以下格式:

有3 .可接受的伪版本形式:
- vx .0.0-yyyymmddhhmms -abcdefxyz,如果没有较早版本的提交,在目标提交之前使用适当的主版本提交
- vX.Y.Z-pre.0。yyyymmddhhmss -abcdefxyz时,在目标提交之前提交的最新版本是vX.Y.Z-pre
- vX.Y。(Z + 1) 0。yyyymmddhhmss -abcdefxyz时,在目标提交之前提交的最新版本是vX.Y.Z
作为最佳实践,伪版本字符串永远不应该手工输入。go命令将接受普通的提交散列,并自动将其转换为伪版本。此方法有助于根据生成的时间戳比较修订。
例如,a去命令可能只使用模块查询的提交散列:
->请登录github.com/x/sys@c856192# records v0.0.0-20180517173623-c85619274f5d
不让go命令自动生成伪版本存在问题:
- 伪版本参与最小版本选择。如果它的版本前缀不准确,那么伪版本可能看起来比它后面的版本具有更高的优先级,从而有效地将模块固定在该提交上
- 伪版本中的提交日期提供了伪版本之间的总顺序,所以如果它被编辑,它将打乱顺序
尽管有此建议,但有时在手工编辑的go模块中可能存在伪版本。在其他情况下,完整的伪版本字符串可能由第三方工具生成。
更严格的规则
在1.12版本中,Go原谅了伪版本引用。大多数涉及伪版本的操作都接受版本字符串和日期的任意组合,并且只要该版本存在,就会解析为底层版本(通常是Git提交散列)。
Go 1.13的发布带来了更严格的执行,以解决上面提到的问题。Go 1.13限制了' Go '命令接受的伪版本,使一些先前接受但不规范的版本无效。
go客户端现在根据版本控制元数据对伪版本的不同元素执行一些验证:
- 的标签伪版本派生的源指向底层VCS工具报告的命名版本或其祖先之一,或者伪版本不是派生自任何标签(即在日期字符串之前有“vX.0.0-”前缀),并使用适合模块路径的最低主版本
- 的日期字符串伪版本中与底层VCS工具报告的版本的UTC时间戳相匹配
- 的修订的简称在伪版本中与go命令生成的短名称相同。
- 伪版本包括一个+不相容的仅当相应的主版本需要后缀时,并且仅当底层模块没有
go.mod文件 - 即使在从代理解析模块之后,go客户端也会尝试从校验和服务器,它强制执行相同的伪版本验证规则,并拒绝提供校验和内容。
如何修复不正确的伪版本
为了迁移到Go 1.13,开发人员必须纠正所有与上述要求不一致的伪版本引用。否则go客户端将标记一个异常:
去获取golang.org/x/sys@v0.0.0-20190726090000-fde4db37ae7a:无效的伪版本:不匹配版本控制时间戳(2019-08-13T06:44:41Z)
幸运的是,这很容易通过你的go.mod文件伪版本引用的地方。
如果go.mod文件的需要指令有不正确的伪版本,这可以通过
-
- 用提交哈希字符串替换完整的伪版本引用
要求{golang.org/x/sys fde4db37ae7a}运行
Go mod tidy整洁让客户端执行适当的替换。 - 如果其中一个传递依赖项引用了无效的伪版本,则可以使用
取代命令在你的行动。Mod文件强制更正:替换golang.org/x/sys v0.0.0-20190726091711-fde4db37ae7a => golang.org/x/sys fde4db37ae7a
- 用提交哈希字符串替换完整的伪版本引用
GoCenter如何提供帮助
GoCenter的一个重要原则是版本不可知。JFrog的社区工程团队已经对GoCenter进行了重要的更新,以支持Go 1.13到1.13的所有版本,我们正在进行进一步的更新,以适应Go 1.14的要求。
GoCenter现在通过重定向到正确的伪版本来帮助您遵守伪版本验证。中的元数据会被GoCenter修改info使用正确的版本,当模块下载请求不正确的伪版本。
->curl https://gocenter.io/golang.org/x/sys/@v fde4db37ae7a.info{" name ": " v0.0.0-20190813064441-fde4db37ae7a ", " shortName ": " v0.0.0-20190813064441-fde4db37ae7a ", " version ": " v0.0.0-20190813064441-fde4db37ae7az ", " time ": " 2019-08-13T08:03:52Z "}
要使用GoCenter,请设置您的GOPROXY
GOPROXY = https://gocenter.io/
For Go 1.12
对于Go 1.12的用户,GoCenter将会更新go.mod在其存储库中保存的具有正确伪版本的文件。GoCenter仍然会提供在此更改之前在GoCenter中处理的错误伪版本。
->去的版本Go版本go1.12.14达尔文/amd64 ->请访问golang.org/x/sys@v0.0.0- 201907260900,000 -fde4db37ae7aGo:查找golang.org/x/sys v0.0.0-20190726090000-fde4db37ae7a ->猫go.mod模块示例go 1.12 require golang.org/x/sys v0.0.0-20190813064441-fde4db37ae7a // indirect
For Go 1.13
Go 1.13用户将收到指向正确伪版本的错误消息。
->去的版本Go版本go1.13.5 darwin/amd64 ->请访问golang.org/x/sys@v0.0.0- 201907260900,000 -fde4db37ae7aGo:查找golang.org v0.0.0-20190726090000-fde4db37ae7a Go:查找golang.org/x v0.0.0- 201907260900000 -fde4db37ae7a Go:获取golang.org/x/sys@v0.0.0- 201907260900000 -fde4db37ae7a: golang.org/x/sys@v0.0.0- 201907260900000 -fde4db37ae7a:代理返回信息版本v0.0.0-20190813064441-fde4db37ae7a而不是请求的版本->猫go.mod模块example.com/mitali go 1.13
为了在go中更新正确的伪版本。Go 1.13用户需要修改去只包含伪版本的提交散列部分。
->请访问golang.org/x/sys@fde4db37ae7aGo:查找golang.org fde4db37ae7a Go:查找golang.org/x/sys fde4db37ae7a Go:查找golang.org/x fde4db37ae7a ->猫go.mod模块example.com/mitali go 1.13要求golang.org/x/sys v0.0.0-20190813064441-fde4db37ae7a // indirect
如果您想覆盖此行为,并让GoCenter提供先前处理的错误伪版本,那么您可以设置GOSUMDB =了。
1.14模块有什么变化
正如我们所提到的,JFrog正在对GoCenter进行修改以支持Go 1.14。以下是该版本中对Go的一些更改,这些更改会影响模块的操作,您可能需要注意:
Go命令标志
-
-
去命令不再接受国防部国旗mod =只读的如果没有顶级供应商目录,则默认设置。Mod文件是只读的-modfile =文件引入了新的标志,它指示go命令读取/写入另一个go。Mod文件和备用go。也将使用Sum文件。虽然一个名为go。Mod必须仍然存在,以便确定模块根目录
-
go.mod文件changes
-
-
去不会升级到an+不兼容主版本,除非明确请求或已经需要- Go命令(除了
Go mod tidy整洁)不会移除a需要指令,该指令指定主模块的其他依赖项已经隐含的间接依赖项的版本 - 当
mod =只读的标志设置,那么go命令将不会因为丢失go指令或任何错误而失败
-
模块下载
-
-
- Go命令现在支持颠覆存储库模块模式
- Go命令现在包含来自模块代理和其他HTTP服务器的纯文本错误消息片段。只有当它是有效的UTF-8并且由独占图形字符和空格组成时才会显示错误消息。
-
Go Forward With GoCenter
随着Go模块获得越来越多的认可,标准肯定会发生变化。您可以依靠JFrog GoCenter来跟上这些变化,并帮助您在需求变化时克服速度障碍。
如果你还没有探索过GoCenter的Go模块的免费存储库然而,我们邀请你这样做!通过一个丰富的UI,它可以帮助您检查所有600,000多个Go模块的数据,它可以帮助您获得对所使用的GoLang依赖项的强大命令。