从Go 1.11开始, 引入了官方包(package)依赖管理工具 go mod。之前Golang 主要依靠vendor和GOPATH来管理依赖库,vendor相对主流,但现在官方更推荐使用go mod。Go 1.12 会删除对 GOPATH 的支持,go get 命令也会变成只能获取模块,不能像现在这样直接获取一个裸包。

使用环境变量 GO111MODULE 开启或关闭模块支持,它有三个可选值:off、on、auto,默认值是 auto。

GO111MODULE=off 无模块支持,go 会从 GOPATH 和 vendor 文件夹寻找包。 GO111MODULE=on 模块支持,go 会忽略 GOPATH 和 vendor 文件夹,只根据 go.mod 下载依赖。 GO111MODULE=auto 在 $GOPATH/src 外面且根目录有 go.mod 文件时,开启模块支持。

GO111MODULE=on的时候,go get下载的依赖会储存在 $GOPATH/pkg/mod 中,所以会导致IDE包引入错误。
由于IDE现在默认还没有,需要自行修改,一下以Goland为例。

go mod使用

当开启go modules后,你的项目文件夹可以放在任意位置,无需放在 $GOPATH/src中。
例如:新建文件夹F:\Go\www\demo

cd F:\Go\www\demo
go mod init  demo

生成go.mod文件,打开文件内容

module demo

go 1.14

go.mod 是启用了 Go moduels 的项目所必须的最重要的文件,它描述了当前项目(也就是当前模块)的元信息,每一行都以一个动词开头,目前有以下 5 个动词:

module:用于定义当前项目的模块路径。 go:用于设置预期的 Go 版本。 require:用于设置一个特定的模块版本。 exclude:用于从使用中排除一个特定的模块版本。 replace:用于将一个模块版本替换为另外一个模块版本。

这里的填写格式基本为包引用路径+版本号,另外比较特殊的是 go $version,目前从 Go1.13 的代码里来看,还只是个标识作用,暂时未知未来是否有更大的作用。

新建main.go文件

package main

import (
"github.com/gin-gonic/gin"
"fmt"
)

func main() {
	r := gin.Default()
	r.GET("/ping", func(c *gin.Context) {
		fmt.Println("hello world!")
		c.JSON(200, gin.H{
			"message": "pong",
		})
	})
	r.Run() // listen and serve on 0.0.0.0:8080
}

执行go build

go build

go会自动下载相关的依赖

查看go.mod,内容已更新

module demo

go 1.14

require github.com/gin-gonic/gin v1.6.3

默认使用最新版本的package。

更换依赖版本

查看gin所有历史版本

go list -m -versions github.com/gin-gonic/gin

github.com/gin-gonic/gin v1.1.1 v1.1.2 v1.1.3 v1.1.4 v1.3.0 v1.4.0

如果想更换依赖版本,比如v1.3.0,怎么办?

只需执行如下命令

go mod edit -require="github.com/gin-gonic/gin@v1.3.0"
go mod  tidy #更新现有依赖

@后跟版本号,这个时候go.mod已经修改好了

require github.com/gin-gonic/gin v1.3.0

查看所有项目依赖的包

go list -m all

旧项目快速迁移项目至 Go Modules

在你项目的根目录下执行 go mod init 项目名 (项目名可不加),以生成 go.mod 文件。
执行 go mod tidy` 更新整理现有的依赖,删除未使用的依赖。

go mod 相关命令

go mod downloadgo mod tidygo mod graphgo mod initgo mod editgo mod vendorgo mod verifygo clean -modcachego mod