- 🚀本仓库是 
Go Mod的相关官方文档翻译。 - 👏欢迎任何人加入翻译的工作。
 - 🌟你的star就是我的动力。
 
Go 自从 1.11 版本以来就包含了对版本化模块 (versioned modules) 的支持。最初的原型vgo是在2018年2月发布的,2018年7月,版本化模块正式登陆Go的主分支。
在 Go 1.14 中,Go Module已经可以投入生产环境中使用,并且鼓励所有用户从其他的依赖管理工具迁移过来。如果在迁移过程中使用Go工具链出现了问题,可以去看issues。
详细请见:Go 1.14 发布日志
- 当主模块包含一个顶层的vendor,且
go.mod中指定了Go的版本在1.14或以上的时候,go命令行会默认带上-mod=vendor的参数; - 当
go.mod文件是只读且没有顶层vendor目录的时候,-mod=readonly将被设为默认值; - 新参数
-modcacherw,模块缓存中的文件权限也会被复制到go命令创建的新目录(之前是全部只读); - 当
GO111MODULE=on时,如果没有go.mod文件,大多数go命令行功能会被限制; - Go命令行现在支持仓库的子版本了;
 
详情请见:Go 1.13 发布日志
- Go命令行现在默认从公共Go模块镜像 https://proxy.golang.org 下载,而且默认会从 https://sum.golang.org 校验checksum的值;
- 如果你是私有的代码,那就应该配置
GOPRIVATE参数(比如说go env -w GOPRIVATE=*.corp.com,github.com/secret/repo),或者更详细一点,使用GONOPROXY或者GONOSUMDB,这种方式比较少见,详见文档 
 - 如果你是私有的代码,那就应该配置
 - 当
GO111MODULE=auto时,就算go.mod位于GOPATH内也能正确激活“模块模式(module-mode)”了(在之前的版本中,GOPATH内无法激活模块模式); go get的参数发生了变化:go get -u现在只升级当前package下的直接依赖和间接依赖,不再检查整个模块了;- 从模块的根目录执行
go get -u ./...现在会升级所有你的模块的直接和间接依赖,并且现在会排除测试依赖; go get -u -t ./...类似,不过也会升级测试依赖;go get现在不再支持-m参数了(因为一些改动导致它和-d参数的功能几乎重合了,所以你现在可以使用go get -d foo来代替go get -m foo)。
介绍 (Introduction)
该系列文章官方发布于 2019年3月19日 。
该部分已由GCTT (studygolang) 翻译,下面的链接可以直达。
- 第一部分 — 开始使用 Go Modules | 翻译 / 原文
 - 第二部分 — 迁移到 Go Modules | 翻译 / 原文
 - 第三部分 — 发布 Go Modules | 翻译 / 原文
 - 第四部分 — Go Modules: v2 和未来 | 翻译 / 原文
 
文档 (GitHub Wiki)
快速上手
详细的内容在本页面的其他部分都会介绍,现在让我们先来从一个简单的例子入手,看看如何快速创建一个模块。
首先在GOPATH以外的地方创建一个目录,并初始化代码仓库(可选):
$ mkdir -p /tmp/scratchpad/repo
$ cd /tmp/scratchpad/repo
$ git init -q
$ git remote add origin https://github.com/my/repo
初始化一个新的模块:
$ go mod init github.com/my/repo
go: creating new go.mod: module github.com/my/repo
写下你的代码:
$ cat <<EOF > hello.go
package main
import (
    "fmt"
    "rsc.io/quote"
)
func main() {
    fmt.Println(quote.Hello())
}
EOF
构建并运行:
$ go build -o hello
$ ./hello
Hello, world.
go.mod文件已经被自动更新了,包含了你的依赖包和版本号,版本号标签严格遵循semver规范。
$ cat go.mod
module github.com/my/repo
require rsc.io/quote v1.5.2
可以发现在上面的例子中,我们都没有使用到go get命令。
你的日常使用流程可以是:
- 在你的
.go代码中根据需要添加import声明; - 一些标准的命令例如
go build或go test会自动添加新的依赖包以此来满足imports的需要(自动更新go.mod文件并且下载新的依赖包); - 如果需要的话,可以在
go get命令或在编辑go.mod文件的时候指明版本号,例如go get foo@v1.2.3,go get foo@master(foo@default),go get foo@e3702bed2。 
其他你可能也经常会用到的功能也简单介绍一下:
go list -m all—— 列出所有在build过程中会被直接和间接依赖的包的版本号;(详情)go list -u -m all—— 列出所有依赖包可用的升级;(详情)go get -u ./...或go get -u=patch ./...(在模块的根目录执行)—— 升级所有依赖包到最新版本(无视预发布的版本);(详情)go mod tidy—— 从go.mod中清理所有不再需要的依赖包,并且增加其他需要的依赖包;(详情)- 在
go.mod中使用replace可以使用其他依赖路径,比如fork的仓库、本地的拷贝或精确的版本号(例如replace example.com/project/foo => ../foo);(详情) go mod vendor一个可选的步骤,用于创建一个vendor路径。(详情)
在你读完接下来的“新概念”中的四小节内容后,足够应付大部分项目了。重新浏览目录也能帮助你熟悉Go Modules的一些更细节的讨论。
新的概念
接下来的几个小节将会详细介绍Go Modules的几个概念。更详细的细节请参考40分钟的介绍:GopherCon Sg 2018,官方文档或最初的vgo系列
一个模块(module)定义为一系列相关的Go包(package)的集合,这些包作为一个单一单元被版本化。(译注:Go package其实就是一个目录下的单个或多个.go文件组成的包。)
模块记录了详细的依赖关系,且一个模块的构建过程也是可复现的。
大多数情况下,一个有版本控制的代码仓库,其根目录下只会包含一个模块。(单仓库多模块也是支持的,但是相较于单仓库单模块,会导致更多的版本管理的工作)
总结一下版本库(repo)、模块(module)和包(package)之间但关系:
- 一个版本库包含一个或多个Go模块;
 - 每个模块包含一个或多个Go包;
 - 每个包由一个目录下的单个或多个
.go文件组成。 
模块必须严格按照semver规范来打上有意义的版本号,通常情况下遵循格式v(major).(minor).(patch),比如v0.1.0,v1.2.3,或者v1.5.0-rc.1。开头的v是必需的。如果使用Git,请在发布的时候用tag标上版本号。公有库、私有库和镜像仓库都受到支持(见下方FAQ)
- 如何使用 Modules
 - 迁移到 Modules
 - 其他参考资料
 - 从最初的 Vgo 发布后做的改变
 - GitHub Issues
 - FAQs
 
提供相关翻译至docs/目录下即可,待校对完毕后,README由我来更新就好。
