Go 包管理机制深入分析

87 篇文章 1 订阅
68 篇文章 11 订阅

前言

随着 Go 语言的深入使用,其依赖管理机制也一直是各位 Gopher 热衷于探讨的话题。Go 语言的源码依赖可通过 go get 命令来获取,但自动化程度不高,于是官方提供了 Dep 这样的自动化批量管理依赖的工具。虽然 Go 语言的依赖管理在很多方面还是不如人意,但整个体系正在日趋完善,本篇就将从最基本的依赖管理场景出发,一同探讨 Go 语言依赖管理的一些最佳实践。

 

Go 依赖管理的基本思路

 

在 Go 语言中,我们通过 go get 命令将 GitHub 或者 Google Code 上的代码下载到本地指定目录,然后在开发代码中通过 import 的形式引用本地的代码。

 

 

Go 语言可以通过直接分析代码中的 import 语句来查询依赖关系。go get 命令在执行时,就会自动解析 import 来安装所有的依赖。那么下载的依赖在本地是如何存储的呢?

 

这里就涉及到 Go 语言的 WORKSPACE 概念,简单来说就是通过 GOPATH 环境变量来设置 Go 代码的位置。一般来说,GOPATH 目录下会包含 pkg、src 和 bin 三个子目录,这三个目录各有用处。

 

  • bin 目录用来放置编译好的可执行文件,为了使得这里的可执行文件可以方便的运行,在 shell 中设置PATH变量。

  • src 目录用来放置代码源文件,在进行 import 时,是使用这个位置作为根目录的。自己编写的代码也应该放在这下面,不同的项目放在不同的目录下进行管理。

  • pkg 用来放置安装的包的链接对象(Object)的。这个概念有点类似于链接库,Go 会将编译出的可连接库放在这里,方便编译时链接。不同的系统和处理器架构的对象会在 pkg 存放在不同的文件夹中。

 

当项目在 src 目录下管理时,多个项目可能都会使用相同的依赖,如果每个项目都存一份依赖显然会带来大量的冗余,这里我们推荐一个设置 GOPATH 环境变量时的小技巧。

 

 

这样第三方包就会默认放置在第一个路径中,而你可以在第二个路径下编写自己的代码,多个项目共享一份依赖。

 

dep - 官方 Go 依赖管理工具

 

dep 是 Go 语言官方提供的依赖管理工具,跟其他依赖管理工具类似,都是通过一个文件描述依赖的坐标信息,然后批量管理(下载、升级等)依赖包(源码)。dep 是一个开源项目, 大家可以在 https://github.com/golang/dep 了解详细信息,其安装方式大家可以参考官方说明,这里我们主要介绍其使用。

 

基本操作

 

通过 dep init 命令来初始化,会创建Gopkg.lock,Gopkg.toml文件和一个空的vendor目录。

 

我们在代码中通过 import 命令添加依赖后,通过 dep ensure 就可以下载依赖到本地 $GOPATH/src 目录下。

 

main.go

 

 

Gopkg.lock

 

 

通过 dep status 我们可以查看当前依赖引用的情况

 

 

另外有一个 dep check 命令来检查是否存在依赖被引用,但是代码中并没有使用的情况,Go 语言对于依赖的引用比较严格,不允许引用了但是没使用的情况。从软件安全的角度考虑,这是一个很好的实践,避免引入一些安全风险。

 

 

当然,这种时候我们就需要移除本地依赖,最好不要手动删除vendor中的内容,而是通过 dep ensure -update 命令来移除。

 

从 dep 的目录结构,我们可以分析出 dep 的基本工作思路:

 

这里面有两个关键的步骤:

 

  • 解析依赖
    从当前项目的 import 文件中解析出整个工程的依赖情况,并结合 Gopkg.toml 定义的规则,然后将依赖关系输出给 Gopkg.lock,注意这个 lock 文件最好不要手动修改。

  • 获取依赖
    通过 Gopkg.lock 了解整个依赖关系之后,将依赖的具体内容拉取下来放到 vendor 目录中,然后执行 Go build 时从本地的 vendor 读取依赖并完成构建。

 

这一些都是在 dep ensure 时完成的,其实在执行这个命令时还可以传参数,最主要的是 -no-vendor 和 -vendor-only 这两个参数。

 

-no-vendor 参数只会导致运行 resolve 函数,结果是创建一个新的Gopkg.lock 文件,不会更新 vendor;而 -vendor-only 参数将跳过 resolve 并仅运行 vendoring 函数,导致 vendor/ 从已存在的Gopkg.lock 重新更新。

 

关于 dep 更多深入内容,可以参考 

https://golang.github.io/dep/docs/introduction.html

 

总结

 

Go dep 目前是一款比较好用的依赖管理工具,很多比较大型的项目都在使用,从中可以学习到依赖管理的一些基本思路,对于理解其他语言,比如 NPM 的依赖管理模型也是比较有好处的。

 

 

文章作者:付辉

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值