GoCenter为Go moudles加速

一、背景

Go语言是Google开发的一种静态强类型、编译型、并发型,并具有垃圾回收功能的编程语言。为了方便搜索和识别,有时会将其称为Golang。自2009年11月Google正式宣布推出,成为开放源代码项目以来,Go语言已成为当今开发人员和DevOps领域最流行的语言之一, 它被用于设计和编写Kubernetes和Helm。

但是,相比语言本身已经得到了广泛的普及和使用,Go语言的包管理方案却大大滞后了。2018年Google终于在Go1.11官方推出了Go modules,为Go语言提供了支持版本化的依赖管理方案。

Go modules现在已成为Go语言标准的依赖管理工具和包仓库规范。而GoCenter为Go modules的实现和推广提供了依赖包的公共仓库,使得Go语言的开发人员能够更为稳定和方便地开发可重复构建的Go应用程序。

除了提供Go仓库外,在获取和下载Go module包方面,GoCenter提供了比传统的如GitHub等版本管理系统更为快速的支持。

二、验证GoCenter速度的测试

为了验证GoCenter提供了更快获取Go modules的方式,我们设计了如下测试方案:

1、我们选取了两个Go项目,用以比较不同项目规模下速度的不同。一个是私有项目,webhook-bridge(https://github.com/retgits/webhook-bridge);一个是公共项目,静态站点生成器Hugo(https://github.com/gohugoio/hugo)。

2、我们在两个网络环境下分别执行测试,用以比较不同网络条件下速度的不同。一个是JFrog的公司网络,一个是家庭网络。

3、构建Go 项目通常包含两步,第一是下载依赖,第二是编译可执行程序。本次测试集中在第一部分,Go依赖包的下载速度。为了使测试尽可能公平和不间断, 我们编写了一个脚本, 在运行“go get”之前删除了所有模块,然后对于同一个项目分别使用 GitHub和GoCenter来获取依赖。这些命令将运行10次, 结果记录在文件中。测试使用的脚本参见https://github.com/xingao0803/GoCenter-Performance/blob/master/testscript.sh

同时,为了保证测试的公正性,我们测试的时候并没有通知GoCenter团队。他们既不能对测试所用的项目或模块产生影响,也无法篡改我们的测试数据。

三、测试结果

测试结果的详细列表参见https://github.com/xingao0803/GoCenter-Performance/blob/master/GoCenter-performance.xlsx。在这里,我们统计一下,列出每个项目的最快和最慢运行之间的差异。

1、私有项目的测试结果

在JFrog公司网络测试私有项目:

越小越好

GoCenter/GitHub

用户模式下CPU秒数

内核模式下

CPU秒数

CPU占比

总运行秒数

比较最慢运行

0.18

0.29

0.83

0.30

比较最快运行

0.18

0.29

0.69

0.26

在家庭网络测试私有项目:

越小越好

GoCenter/GitHub

用户模式下CPU秒数

内核模式下

CPU秒数

CPU占比

总运行秒数

比较最慢运行

0.16

0.30

0.83

0.42

比较最快运行

0.17

0.29

0.53

0.23

最后一列“总运行时间”,是测试下载Go项目依赖包并放入正确位置的时间。从上述统计可以看出,通过GoCenter获取Go modules依赖比从GitHub获取速度更快,消耗资源更少。

这个私有项目只有6个直接依赖和12个间接依赖的Go module。如果使用更大规模的项目,如Hugo,包括43个直接依赖和11个间接依赖,效果又会如何呢?

2、Hugo项目的测试结果

在JFrog公司网络测试私有项目:

越小越好

GoCenter/GitHub

用户模式下CPU秒数

内核模式下

CPU秒数

CPU占比

总运行秒数

比较最慢运行

0.13

0.19

1.50

0.12

比较最快运行

0.13

0.20

1.26

0.10

在家庭网络测试私有项目:

越小越好

GoCenter/GitHub

用户模式下CPU秒数

内核模式下

CPU秒数

CPU占比

总运行秒数

比较最慢运行

0.14

0.20

1.48

0.12

比较最快运行

0.14

0.19

1.32

0.11

从上述统计可以看出,对于大型Go项目,虽然CPU占比相对较高,但是从GoCenter获取依赖的速度相对更快了。

3、测试总结

通过上述针对测试结果的分析和统计,不难看出,使用GoCenter获取Go modules依赖,比直接从GitHub等版本控制系统获取这些依赖速度更快,而且还节省了CPU周期。而且,随着项目复杂性的增长(更大的依赖树),性能的提升更为明显。

四、分析GoCenter快速的原因

要了解GoCenter速度更快的原因,我们需要深入分析go客户端是如何获取Go modules依赖包的。我们来比较一下,在是否设置GOPROXY变量的情况下,执行go get获取modules有什么不同?

1、获取module信息

第一个区别从“import”库开始。使用Go编写的每一个应用都会使用库。这些库可能是标准库,如“fmt”或“io”,也可能是由别处分享的。

如果没有设置GOPROXY变量,且项目包位于任意预定义好的版本控制系统(如GitHub),Go客户端会知道如何解析URL以获取相关模块。如果项目包不在这些系统中,Go客户端将会执行动态HTML检查,来查找表明如何、以及在何处获取相关模块的元数据标记。这个过程需要HTTP重定向和HTML解析。

如果设置GOPORXY变量指向GoCenter,Go客户端就会向GoCenter发送一个请求来获取module信息。GoCenter更快速的第一个原因就在于不需要复杂的HTML和HTTP处理,而是直接使用一个简单的HTTP请求。这个优势在大量依赖存活在预定义的版本控制系统之外的Go项目上会显得更为突出。

2、下载module

下一步是要把相关module下载到本地。Go module已被打包成zip文件,以及少数附加的元数据文件(我们稍后讨论)。

如果不设置GOPROXY变量,Go客户端将执行“git clone”,并在$GOPATH/pkg/mod/cache/vcs目录创建一个“bare”仓库。

如果将GOPROXY变量设置为GoCenter,Go客户端将会发送HTTP GET请求并下载zip文件。GoCenter赢得速度的第二点就在于,下载文件通常比执行“git clone”快得多。在这种情况下,由于Go module是压缩好的文本文件,下载会节省更多的时间和带宽。

3、构建module

接下来要构建module,以便在Go应用中使用。 如前所述,Go module是带附属文件的zip压缩包,这些附属文件包括.info(包含版本号和提交时间)和.mod(下载的module文件)等。Go客户端需要这些文件及其实际来源。

如果没有设置GOPROXY变量,Go客户端需要计算并生成这些文件,再把他们和module文件一起放到$GOPATH/pkg/mod/cache/download文件夹。稍后还需要把他们移动到$GOPATH/mod//文件夹。

如果GOPROXY已设置为GoCenter,这些文件已经随之前的下载并放到$GOPATH/pkg/mod/cache/download里。Go客户端只需简单地解压zip文件,然后把源文件(不带元数据文件)放到$GOPATH/mod//。解压文件可比计算校验和、生成文件,并获取“bare”仓库的副本要快得多了,这正是GoCenter的第三个速度优势。

4、总结

我们总结一下。当不设置GOPROXY时,Go客户端采取的步骤是:

· 寻找module的位置以及访问协议,这可能需要额外的HTTP和HTML处理;

· 执行“git clone”,并在$GOPATH/pkg/mod/cache/vcs创建“bare”仓库;

· 生成zip文件,计算校验和,生成元数据文件,并把它们放到$GOPATH/pkg/mod/cache/download;

· 把不带元数据文件的源文件放到$GOPATH/mod//

而设置GOPROXY为GoCenter后,Go客户端的工作就简化了很多:

· 下载module的.mod、.info和.zip文件,并放到$GOPATH/pkg/mode/cache/download(只有3个HTTP GET操作);

· 把源文件解压到$GOPATH/mod//

通过使用GoCenter,去掉了查找module的HTTP和HTML处理,“昂贵”的源码clone操作,以及元数据文件的生成操作。

五、总结

Go语言是目前最为流行的编程语言之一,而Go modules的推出为Go语言增加了完善的依赖管理方案。

JFrog推出的GoCenter,做为Go modules的中央仓库,为广大的Go开发者提供了丰富的、版本化管理的公共Go modules包。

除此之外,因为在下载文件是采用正确的协议、节省HTTP调用次数,以及无需在客户端重新创建模块等特性,GoCenter还为Go modules的应用提供了更快速的支持。

我们针对GoCenter的支持速度进行了测试,结果验证了我们的预期。这一测试结果在Go社区也得到了众多正面回应。我们测试所用的项目、脚本,以及测试结果都在前文中列出,欢迎大家自己实际操作、验证一下。

想要了解有关 GoCenter 更多深入的技术信息?请查看GoCenter的Github项目,https://github.com/jfrog/gocenter

六、参考文献

Golanghttps://golang.org

Go Modules: https://github.com/golang/go/...

GoCenterhttps://gocenter.io/


**欢迎观看JFrog杰蛙每周二在线课堂,点击报名:

https://www.bagevent.com/even...**

你可能感兴趣的:(devops,jenkins,debian,运维)