Golang modules 初探

今天天色刚刚亮起,起床看到golang 1.11正式发版了,有着两个重要的特性:modules和WebAssembly。

本博文只要说的是modules,congJava转golang的同学肯定是对golang的包管理充满了无奈之情,我也曾在博客中介绍过glide,也介绍过dep,现在我们再一次升级介绍modules。

什么是modules

现在都在说modules,那么它是什么?
到文档看看 Modules, module versions, and more

A module is a collection of related Go packages. Modules are the unit of source code interchange and versioning. The go command has direct support for working with modules, including recording and resolving dependencies on other modules. Modules replace the old GOPATH-based approach to specifying which source files are used in a given build.

翻译一下:

模块是相关Go包的集合。modules是源代码交换和版本控制的单元。 go命令直接支持使用modules,包括记录和解析对其他模块的依赖性。modules替换旧的基于GOPATH的方法来指定在给定构建中使用哪些源文件。

可以得到两个重要信息:

  • Go命令行支持modules操作
  • modules用来替换GOPATH的

大家不需要太担心了,golang 1.11版本仅仅是指对modules的初步支持,之前老的GOPATH还是可以继续使用的,有人说是在golang 1.12去除,但是我觉得有点早了,毕竟人的惯性不是这么容易改变的。

如何使用modules

modules是一个新的特性,那么就需要新的Golang版本进行支持了,可以到官网下载,一定要是go 1.11及以上的版本(写博文的时候go 1.11刚刚出来)。
这么部署就在这里说了,相信初学者也是知道怎么做的。

还有人记得vendor刚刚出来时候golang提供的环境变量GO15VENDOREXPERIMENT吗?现在modules出来,按照惯例也提供了一个环境变量GO111MODULE,这个变量的三个1太有魔性了。

GO111MODULE

GO111MODULE可以设置为三个字符串值之一:off,on或auto(默认值)。

  • off,则go命令从不使用新模块支持。它查找vendor 目录和GOPATH以查找依赖关系;也就是继续使用“GOPATH模式”。
  • on,则go命令需要使用模块,go 会忽略 GOPATH 和 vendor 文件夹,只根据 go.mod下载依赖。
  • auto或未设置,则go命令根据当前目录启用或禁用模块支持。仅当当前目录位于GOPATH/src之外并且其本身包含go.mod文件或位于包含go.mod文件的目录下时,才启用模块支持。

Defining a module

开始的时候谁也不知道怎么使用?不过go已经给我提供了工具了,可以在控制台输入:

go help modules

看到一大串的文档输出,看着都头疼了,一会儿我们再简要说明重点,现在先进行操作。

[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ export GO111MODULE=on  #开启modules

[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ go mod init  gitlab.luojilab.com/zeroteam/ddkafka # 创建go.mod
go: creating new go.mod: module gitlab.luojilab.com/zeroteam/ddkafka

[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ ls    # 真的创建了,google大法好呀
README.md  go.mod  models.go  mq_interface.go  sarama  segmentio
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ cat go.mod    # 看看里面什么东西
module gitlab.luojilab.com/zeroteam/ddkafka
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ cd segmentio/
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka/segmentio (module)
$ go test   # 执行一下看看
go: finding github.com/segmentio/kafka-go latest
go: finding github.com/golang/glog latest
go: downloading github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b
go: downloading github.com/segmentio/kafka-go v0.0.0-20180716203113-48c37f796910
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka/segmentio (module)
$ go list -m
gitlab.luojilab.com/zeroteam/ddkafka

细心的同学一定可以发现,执行go mod init [module]使用go.mod只有一行信息module gitlab.luojilab.com/zeroteam/ddkafka,在执行 go build、 go test、 go list命令时会根据需要的依赖自动生成 require语句。

现在来说说如何定义一个modules,modules是由Go源文件目录结构定义的,如果目录下含有go.mod文件,该目录称为模块根目录(module root)。模块根目录及其子目录所有的Go包都是属于该modules的,但是如果子目录包含有了自己的go.mod文件就隶属于该modules。
举一个例子:

[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ tree
.
|-- README.md
|-- go.mod
|-- go.sum
|-- models.go
|-- mq_interface.go
|-- sarama
|   |-- sarama_consumer.go
|   |-- sarama_consumer_test.go
|   |-- sarama_producer.go
|   `-- sarama_producter_test.go
`-- segmentio
    |-- segmention_Consumer.go
    |-- segmention_consumer_test.go
    |-- segmention_producer.go
    `-- segmention_producter_test.go

gitlab.luojilab.com/zeroteam/ddkafka目录下含有了go.mod文件,所以其子目录saramasegmentio都属于gitlab.luojilab.com/zeroteam/ddkafka模块,但是如果在segmentio目录中加入了go.mod,那么segmentio就不再隶属于gitlab.luojilab.com/zeroteam/ddkafka模块。

那么依赖被下载到哪里了呢,你可以打开的目录$GPATH/pkg/mod就可以看到了。

主模块和构建列表

The main module and the build list 暂且翻译为主模块和构建列表。
“主模块”是包含运行go命令的目录的模块。 go命令通过查找当前目录中的go.mod或者当前目录的父目录,或者祖父目录,依次递归查找。

go.mod文件可以通过require,replace和exclude语句使用的精确软件包集。

  • require语句指定的依赖项模块
  • replace语句可以替换依赖项模块
  • exclude语句可以忽略依赖项模块

go list,可以查看当前的依赖和版本.

[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka/segmentio (module)
$ ls  # 这是模块的子目录
segmention_Consumer.go  segmention_consumer_test.go  segmention_producer.go  segmention_producter_test.go

[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka/segmentio (module)
$ go list -m #主模块的打印路径
gitlab.luojilab.com/zeroteam/ddkafka
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka/segmentio (module)
$ go list -m -f={{.Dir}} #print主模块的根目录
D:\code\gopath\src\gitlab.luojilab.com\zeroteam\ddkafka
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka/segmentio (module)
$ go list -m all # 查看当前的依赖和版本信息
gitlab.luojilab.com/zeroteam/ddkafka
github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b
github.com/segmentio/kafka-go v0.0.0-20180716203113-48c37f796910

go mod 命令

go mod命令之前可以使用过了go mod init,下面我们把常用的go mod命令罗列一下:

  • go mod init:初始化modules
  • go mod download:下载modules到本地cache
  • go mod edit:编辑go.mod文件,选项有-json、-require和-exclude,可以使用帮助go help mod edit
  • go mod graph:以文本模式打印模块需求图
  • go mod tidy:删除错误或者不使用的modules
  • go mod vendor:生成vendor目录
  • go mod verify:验证依赖是否正确
  • go mod why:查找依赖
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ go mod edit -json
{
        "Module": {
                "Path": "gitlab.luojilab.com/zeroteam/ddkafka"
        },
        "Require": [
                {
                        "Path": "github.com/golang/glog",
                        "Version": "v0.0.0-20160126235308-23def4e6c14b"
                },
                {
                        "Path": "github.com/segmentio/kafka-go",
                        "Version": "v0.0.0-20180716203113-48c37f796910"
                }
        ],
        "Exclude": null,
        "Replace": null
}
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ cat go.mod
module gitlab.luojilab.com/zeroteam/ddkafka

require (
        github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b
        github.com/segmentio/kafka-go v0.0.0-20180716203113-48c37f796910
)

[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ go mod edit -require=github.com/Shopify/[email protected]

[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ cat go.mod
module gitlab.luojilab.com/zeroteam/ddkafka

require (
        github.com/Shopify/sarama master
        github.com/golang/glog v0.0.0-20160126235308-23def4e6c14b
        github.com/segmentio/kafka-go v0.0.0-20180716203113-48c37f796910
)
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ go mod vendor  # 启动verdon
go: downloading github.com/Shopify/sarama v1.17.1-0.20180820172058-647feef69a1a
go: finding github.com/davecgh/go-spew/spew latest
go: finding github.com/eapache/queue v1.1.0
go: finding github.com/eapache/go-xerial-snappy latest
go: finding github.com/eapache/go-resiliency/breaker latest
go: finding github.com/rcrowley/go-metrics latest
go: downloading github.com/rcrowley/go-metrics v0.0.0-20180503174638-e2704e165165
go: finding github.com/bsm/sarama-cluster v2.1.15+incompatible
go: downloading github.com/eapache/go-xerial-snappy v0.0.0-20180814174437-776d5712da21
go: downloading github.com/bsm/sarama-cluster v2.1.15+incompatible
go: downloading github.com/eapache/queue v1.1.0
go: finding github.com/eapache/go-resiliency v1.1.0
go: downloading github.com/eapache/go-resiliency v1.1.0
go: finding github.com/davecgh/go-spew v1.1.1
go: downloading github.com/davecgh/go-spew v1.1.1
go: finding github.com/pierrec/lz4 v2.0.3+incompatible
go: downloading github.com/pierrec/lz4 v2.0.3+incompatible
go: finding github.com/golang/snappy latest
go: downloading github.com/golang/snappy v0.0.0-20180518054509-2e65f85255db

[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ ls
README.md  go.mod  go.sum  models.go  mq_interface.go  sarama  segmentio  vendor
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ go mod verify
all modules verified
[email protected] MINGW64 /d/code/gopath/src/gitlab.luojilab.com/zeroteam/ddkafka (module)
$ go mod why
go: finding github.com/onsi/ginkgo/extensions/table latest
go: finding github.com/onsi/ginkgo v1.6.0
go: finding github.com/Shopify/toxiproxy/client latest
go: finding github.com/onsi/gomega v1.4.1
go: downloading github.com/onsi/gomega v1.4.1
go: downloading github.com/onsi/ginkgo v1.6.0
go: finding github.com/onsi/ginkgo/extensions latest
go: finding github.com/Shopify/toxiproxy v2.1.3+incompatible
go: downloading github.com/Shopify/toxiproxy v2.1.3+incompatible
go: finding github.com/hpcloud/tail v1.0.0
go: finding github.com/golang/protobuf/proto latest
go: finding gopkg.in/yaml.v2 v2.2.1
go: downloading github.com/hpcloud/tail v1.0.0
go: downloading gopkg.in/yaml.v2 v2.2.1
go: finding github.com/golang/protobuf v1.2.0
go: downloading github.com/golang/protobuf v1.2.0
go: finding gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405
go: downloading gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405
go: finding gopkg.in/tomb.v1 latest
go: finding gopkg.in/fsnotify.v1 v1.4.7
go: downloading gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7
go: downloading gopkg.in/fsnotify.v1 v1.4.7
go: finding github.com/fsnotify/fsnotify v1.4.7
go: downloading github.com/fsnotify/fsnotify v1.4.7
# gitlab.luojilab.com/zeroteam/ddkafka
gitlab.luojilab.com/zeroteam/ddkafka

go的 mod与get

go get这个命令大家应该不会陌生,这是下载go依赖包的根据,下载Go 1.11出来了,go get命令也与时俱进,支持了modules。
go get 来更新 module:

  • 运行 go get -u 将会升级到最新的次要版本或者修订版本
  • 运行 go get -u=patch 将会升级到最新的修订版本(比如说,将会升级到 1.0.1 版本,但不会升级到 1.1.0 版本)
  • 运行 go get [email protected]将会升级到指定的版本号

运行go get如果有版本的更改,那么go.mod文件也会更改。

最后

最后说明一下最新出来的特性不建议立即使用到线上,最好再等等,等迭代一两个版本之后,得带最佳实践出来之后,毕竟现在支持modules模式的类库还真不多。

附录

原文地址:http://blog.51cto.com/qiangmzsx/2164520

时间: 2024-10-18 16:45:53

Golang modules 初探的相关文章

GO开发[一]:golang开发初探

一.Golang的安装 1.https://dl.gocn.io/ (国内下载地址) 2.https://golang.org/dl/ (国外下载地址) 3.现在studygolang中文网也可以了https://studygolang.com/dl 下载版本: mac darwin-adm64.tar.gzlinux amd64.tar.gzwindows amd64.msi 4.window编辑器 atom配合go-plus插件 sublime配合gosublime插件: emacs + s

在go modules中使用replace替换无法直接获取的package(golang.org/x/...)

上一篇里我们介绍了使用go get进行包管理. 不过因为某些未知原因,并不是所有的包都能直接用go get获取到,这时我们就需要使用go modules的replace功能了.(当然大部分问题挂个梯子就能解决,但是我们也可以有其它选项) 使用replace替换package replace顾名思义,就是用新的package去替换另一个package,他们可以是不同的package,也可以是同一个package的不同版本.看一下基本的语法: go mod edit -replace=old[@v]

golang 发布 1.11,带来新特性 modules

美国当地时间8月24日,Go 开发团队宣布推出 Go 1.11 正式版. 下载地址:https://golang.org/dl/ 国内下载地址:https://golang.google.cn/dl/ Go 1.11 带来了一个最值得关注且激动人心的新特性--模块(Modules). 此版本增加了对被称作"模块(Go Modules)"的初步支持,这是 GOPATH 的替代方案,集成了对版本控制和软件包分发的支持.该功能目前仍处于实验性阶段,并且仍有一些可能会影响使用的问题,因此请随意

Golang(八)go modules 学习

0. 前言 最近加入鹅厂学习 k8s,组内使用 Go 1.11 以上的 go modules 管理依赖,因此整理了相关资料 本文严重参考原文:初窥Go module 1. 传统 Golang 包依赖管理 Golang 设计深受 Google 主干开发模型影响: 所有开发人员基于主干 trunk/mainline 开发:提交到 trunk 或从 trunk 获取最新的代码(同步到本地 workspace) 版本发布时,建立 Release branch,release branch 实质上就是某一

golang性能监控初探

最近在用golang写一个server.压力测试过程发现反应比较慢,但是由于中间的操作都是串行的,无法知道在哪个操作消耗了比较多时间. 一开始想到的是打log.但是单个请求又是很快的,于是想到如下方案 在调用每个函数的时候,统计该函数的时耗,然后利用channel把同一个函数调用发送到同一个地方,利用map进行累计统计(这里可以更近一步,比如统计每个worker甚至每个services的状态,包括最长请求时间,最短请求时间,平均消耗等等,如果加上runtime还可以记录其他的运行相关信息). 一

初探CSS Modules

CSS Modules 介绍 CSS Modules到底是个什么东西,不妨先看看其官方解释CSS Modules 通过其官方的解释我们可以了解到,CSS Modules既不是官方标准,也不是浏览器标准,而是在构建步骤中对css 类名选择器做作用域限定的一种方式(通过hash实现类似命名空间的方法) CSS模块化 JS都已经全面实现的模块化,只有CSS的模块化还处于探索阶段,那麽为什么需要做CSS的模块化呢,主要有一下几个因素 CSS全局作用域问题 CSS规则都是全局的,任何一个组件的样式规则,对

【GO】golang 协程初探 ,基于生产者/消费者

package main import ( "fmt" "time" ) func main() { // 管道 固定5个int ch := make(chan int, 5) // 生成者 协程 // 管道只能存5个int, 但是要生产15个int, 这就要等消费者先消费完(未消费前生产会阻塞), 然后生产 go func(ch chan int) { for i := 0; i < 15; i++ { ch <- i fmt.Println(&quo

国外物联网平台初探(五):Exosite Murano

国外物联网平台初探(五)--Exosite Murano 马智 ? 定位 Murano是一个基于云的IoT软件平台,提供安全.可扩展的基础设施,支持端到端的生态系统,帮助客户安全.可扩展地开发.部署和管理应用.服务以及联网产品. ? 功能 Murano平台简化了整个IoT技术栈,可视为集成在一起的多个云软件层. Murano提供IoT基础设施.开发环境和功能集成,包括设备连接.产品管理.数据路由.服务集成(如data store/告警/第三方分析平台).应用开放API.用户认证/角色/权限和应用

Golang、Php、Python、Java基于Thrift0.9.1实现跨语言调用

目录: 一.什么是Thrift? 1) Thrift内部框架一瞥 2) 支持的数据传输格式.数据传输方式和服务模型 3) Thrift IDL 二.Thrift的官方网站在哪里? 三.在哪里下载?需要哪些组件的支持? 四.如何安装? 五.Golang.Java.Python.PHP之间通过Thrift实现跨语言调用 1) Golang 客户端和服务端的实现及交互 2) python 客户端的实现与golang 服务端的交互 3) php 客户端的实现与golang 服务端的交互 4) java