当前位置:   article > 正文

一文搞懂Go Mod

一文搞懂Go Mod

Go Mod

Go Mod包管理教程

随着 go 1.11 的发布,go 官方引入了 go module 来解决依赖管理问题,go module 被集成到原生的 go cmd 中。

但是如果你的代码库在 $GOPATH 中,go1.11 的 module 功能是默认不会开启的,想要开启也非常简单,通过一个环境变量即可开启 go module:

export GO111MODULE=on
  • 1

Go Mod与GoPath

现在 modules 机制仍在早期阶段,所以 golang 提供了一个环境变量 “GO111MODULE”,默认值为 auto。

如果当前目录里有 go.mod 文件,就使用 go modules,否则使用旧的 GOPATH 和 vendor 机制,因为在 modules 机制下 go get 只会下载 go modules,这一行为会在以后版本中成为默认值,这里我们保持 auto 即可,如果你想直接使用 modules 而不需要从 GOPATH 过度,那么把 “GO111MODULE” 设置为on。

modules 和传统的 GOPATH 不同,不需要包含例如 src,bin 这样的子目录,一个源代码目录甚至是空目录都可以作为 module,只要其中包含有 go.mod 文件。

关于$GOPROXY

使用

当我们使用 go 的时候,go 默认会直接从代码库中去下载所需的相关依赖,GOPROXY 这个环境变量可以让我们控制自己从哪里去下载源代码

如果 GOPROXY 没有设置,go 会直接从代码库下载相关依赖代码。如果你像下面这样设置了这个环境变量,那么你就会通过 goproxy.io 下载所有的源代码,设置 proxy 的命令如下:

export GOPROXY=https://goproxy.io
  • 1

你可以通过置空这个环境变量来关闭 proxy,命令如下:

export GOPROXY=
  • 1

原理

以前执行 go get golang.org/x/net 时,那么 net 代码库会下载到本地 GOPATH 中,以后有任何项目引用到了 golang.org/x/net 都不会再去下载这个代码库,因为本地 GOPATH 已经有了,哪怕版本不对,golang 也会引用。

但是随着 module 概念引入 go 语言,每个引入的 module 拥有了 version。随着代码库的不断更新迭代,大家即使是对同一个代码库的引用也可能用了不同的 tag 或者 commit hash,基于这个现状,go1.11 的 module 会比以前更频繁的下载源代码。

但是基于中国有中国特色的互联网,我们有时候很难 get 到我们需要的依赖源代码,进而导致项目编译失败,CI 失败。于是,我们需要一个 proxy。

代理设置

代理地址

主要有两个地址,如下:

https://goproxy.io
https://athens.azurefd.net
  • 1
  • 2

以上两个地址,可以根据个人喜好随意选择。

设置方法

Windows
$env:GOPROXY = "https://goproxy.io"
  • 1
Linux
export GOPROXY=https://goproxy.io
  • 1

Go Mod使用

go module的初始化

我们首先,创建一个空的项目文件夹

E:\Code\gomod
  • 1

接着,我们进行项目初始化:

#Linux
export GO111MODULE=on
export GOPROXY=https://goproxy.io

#Windows
$env:GO111MODULE=on
$env:GOPROXY="https://goproxy.io"

go mod init [module name]
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

初始完成后会在目录下生成一个 go.mod 文件,里面的内容只有一行 “module test”。

包管理

当我们使用 go build,go test 以及 go list 时,go 会自动得更新 go.mod 文件,将依赖关系写入其中。如果你想手动处理依赖关系,那么使用如下的命令:

go mod tidy

  • 1
  • 2

这条命令会自动更新依赖关系,并且将包下载放入cache。

Go Mod常用命令

go.mod文件命令

go.mod 提供了 module、require、replace 和 exclude 四个命令,如下:

命令描述
module语句指定包的名字(路径)
require语句指定的依赖项模块
replace语句可以替换依赖项模块
exclude语句可以忽略依赖项模块

go mod常用命令

命令描述
download下载模块到本地缓存,具体可以通过命令 go env 查看,其中环境变量 GOCACHE 就是缓存的地址,如果该文件夹的内容太大,可以通过命令 go clean -cache
edit从工具或脚本中编辑 go.mod 文件
graph打印模块需求图
init在当前目录下初始化新的模块
tidy添加缺失的模块以及移除无用的模块
verify验证依赖项是否达到预期的目的
why解释为什么需要包或模块

Go Mod案例

引用第三方库

我们首先,在 E:\Code\gomod 创建 main.go 文件,并输出以下内容:

package main
    
    import (
    	"context"
    	"log"
    	"time"
    
    	"github.com/chromedp/chromedp"
    )
    
    func main() {
    	// create chrome instance
    	ctx, cancel := chromedp.NewContext(
    		context.Background(),
    		chromedp.WithLogf(log.Printf),
    	)
    	defer cancel()
    
    	// create a timeout
    	ctx, cancel = context.WithTimeout(ctx, 15*time.Second)
    	defer cancel()
    
    	// navigate to a page, wait for an element, click
    	var example string
    	err := chromedp.Run(ctx,
    		chromedp.Navigate(`https://golang.org/pkg/time/`),
    		// wait for footer element is visible (ie, page is loaded)
    		chromedp.WaitVisible(`#footer`),
    		// find and click "Expand All" link
    		chromedp.Click(`#pkg-examples > div`, chromedp.NodeVisible),
    		// retrieve the value of the textarea
    		chromedp.Value(`#example_After .play .input textarea`, &example),
    	)
    	if err != nil {
    		log.Fatal(err)
    	}
    	log.Printf("Go's time.After example:\n%s", example)
    }

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39

接着,我们开始下载包,输入以下命令:

go mod tidy

  • 1
  • 2

接着,我们可以发现,go.mod 和 go.sum 都增加了包的依赖文件。现在,我们就可以直接进行编译,输入以下命令:

go build

  • 1
  • 2

引用自定义库

我们首先创建如下目录:

E:\Code\wolferserver
E:\Code\wolferserver\base
E:\Code\wolferserver\base\configs

E:\Code\wolferserver\src
E:\Code\wolferserver\src\logicserver

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

接着,我们再创建如下文件:

E:\Code\wolferserver\base\configs\configs.go
E:\Code\wolferserver\src\logicserver\main.go

  • 1
  • 2
  • 3

每个文件的文件内容如下:

//configs.go
package configs

import "fmt"

func Demo(){
	fmt.Println("Hello Demo")
}
    
    
//main.go
package main

import (
	"github.com/gin-gonic/gin"
	"wolferserver/base/configs"
)

func main(){
	logInit()
}

func logInit() {
	configs.Demo()

	gin.New()
}

  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28

最后,我们直接输入以下命令,就可以运行我们的程序:

go run src/lpgicserver/main.go

  • 1
  • 2

版本控制

包管理的另外一项重要功能就是包的版本控制。modules 同样可以做到。

go.sum

github.com/chromedp/cdproto v0.0.0-20190429085128-1aa4f57ff2a9 h1:ARnDd2vEk91rLNra8yk1hF40H8z+1HrD6juNpe7FsI0=

  • 1
  • 2

前面部分是包的名字,也就是 import 时需要写的部分,而空格之后的是版本号,版本号遵循 “版本号+时间戳+hash”。

我们自己指定版本时只需要制定版本号即可,没有版本 tag 的则需要找到对应 commit 的时间和 hash 值。默认使用最新版本的 package。

更改版本

现在我们要修改依赖关系了,我们想使用 chromedp 的 v0.1.0 版本,只需要如下命令

go mod edit -require="github.com/chromedp/chromedp@v0.1.0"

  • 1
  • 2

@ 后面加上你需要的版本号。go.mod 已经修改了。我们还需要让 go modules 更新依赖关系,这里我们手动 go mod tidy 即可。

嗨客网(www.haicoder.net)

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/笔触狂放9/article/detail/569845
推荐阅读
相关标签
  

闽ICP备14008679号