GOPATH
痛点:如果我的 myProject01 和 myProject02 分别依赖 calc库 的两个不同版本?
vendor
myProject01,myProject02 中都有一个 vendor 目录,存放引用的库,互相隔离,就没有冲突了。
加载的优先级: vendor -> GOPATH
一般使用 godep 来作为vendor的依赖管理工具。
go module
go 1.11 推出,go 1.13 内置为默认。
有了 go module 后,我们不用过于关心 GOROOT,GOPATH 的位置了。
GO111MODULE
是一个go的环境变量,值有 auto,off,on,较新的版本,默认值就是on,也就是默认项目都是采用go module的方式管理依赖了。
- GO111MODULE=off,禁用,依赖管理基于 vendor,GOPATH
- GO111MODULE=on,启用,go.mod ,go.sum
- GO111MODULE=auto,自动,项目下有 go.mod 时,自动按 go module 方式。
GOPROXY
go env -w GOPROXY=https://goproxy.cn,direct // direct表示回源到包的源地址去抓取
可以配多个值,用 , 分隔
GOPRIVATE
go env -w GOPRIVATE="git.mycompany.com" // 一般是针对私有仓库,比如公司的,同样也支持多个地址
GONOPROXY
GONOPROXY=none // 允许拉取私有仓库的包
go get
go get -u 升级项目中的库到最新的次要版本,比如calc库为v1.2.3,库的新版本是v1.3.0,那么go get -u 后,我们项目中的calc库更新为v1.3.0
go get -u=patch 升级项目中的库到最新的修订版本,比如当前为calc v1.0.0,可能会更新到v1.0.1
go get package@version 安装或更新到指定的版本,比如 go get github.com/junwind/calc@v1.2.3,会安装或更新calc库为v1.2.3
go get package@master 根据分支来
go get package@e3702bed2 根据提交的hash值来
replace
replace (
golang.org/x/crypto v0.0.0-20180820150726-614d502a4dac => github.com/golang/crypto v0.0.0-20180820150726-614d502a4dac
golang.org/x/net v0.0.0-20180821023952-922f4815f713 => github.com/golang/net v0.0.0-20180826012351-8a410e7b638d
golang.org/x/text v0.3.0 => github.com/golang/text v0.3.0
)
go mod 常用命令
go mod init 初始化当前文件夹, 创建 go.mod 文件
go mod download
下载go.mod中的所有依赖,下载的包会放在 GOPATH/pkg/mod 中
go mod tidy
整理go.mod,比如删除go.mod中,项目没有用到的库,或者依照go.mod下载,更新,项目所需的库。
go mod vendor 将依赖复制到 vendor 下
go mod edit 编辑go.mod文件
go mod edit -fmt 格式化go.mod文件
go mod edit -require=golang.org/x/text 添加依赖项
go mod edit -droprequire=golang.org/x/text 移除依赖项,代码中其实还在
go mod graph 打印模块依赖图
go mod verify 校验依赖
go mod why 解释为什么需要依赖
go.mod
module github.com/Q1mi/studygo/blogger // 项目名称
go 1.12 // 使用的go 版本
require ( // 项目所需依赖
github.com/DeanThompson/ginpprof v0.0.0-20190408063150-3be636683586
github.com/gin-gonic/gin v1.4.0
github.com/go-sql-driver/mysql v1.4.1
github.com/jmoiron/sqlx v1.2.0
github.com/satori/go.uuid v1.2.0
google.golang.org/appengine v1.6.1 // indirect 间接依赖
)
使用一个远程包
先新建一个项目
mkdir holiday
cd holiday
go mod init holiday
新建一个main.go文件,并引入 github.com/q1mi/hello
包
下载此包
go get -u github.com/q1mi/hello
go get -u github.com/q1mi/hello@v0.1.0
go get github.com/q1mi/hello@2ccfadd
// 或者在go.mod文件中添加
require github.com/q1mi/hello latest 或 require github.com/q1mi/hello 2ccfadda 或指定版本
// 然后执行
go mod download
使用此包
vim main.go
package main
import "github.com/q1mi/hello"
func main() {
hello.SayHi()
}
使用本地同模块下的包
holidy
├── go.mod
├── go.sum
├── main.go
└── summer // summer包
└── summer.go // 里面有一个 Diving() 函数
main.go 中如何使用这个 Diving() 函数呢?
package main
import (
"holiday/summer"
"github.com/q1mi/hello"
)
func main() {
hello.SayHi()
summer.Diving()
}
使用本地其它模块下的包
在 go.mod 中添加
require (
overtime.com/overtime v0.0.0
)
replace overtime.com/overtime => ../../learnProject/overtime
使用这个包:
package main
import (
"fmt"
"overtime.com/overtime"
)
func main() {
fmt.Println(overtime.Add(1, 2))
}
发布一个远程包
1、先在GitHub上创建一个公开的goTools项目仓库,先不用创建readme.md文件。
echo "# goTools" >> README.md
git init
git add README.md
git commit -m "first commit"
git branch -M master
git remote add origin git@github.com:xiaoquanwei/goTools.git
git push -u origin master
2、本地构建goTools项目
mkdir goTools
cd goTools
go mod init github.com/xiaoquanwei/goTools // 注意这里的模块名称是什么
3、我们在goTools下添加一个加密包,比如有 md5 加密,base64加密
4、将代码上传到github仓库中
cd goTools
git init
git add .
git commit -m "init"
git remote add origin git@github.com:xiaoquanwei/goTools.git
git push -u origin master
5、切到其它项目下,使用 goTools 下的 secret 包
go get -u github.com/xiaoquanwei/goTools
main.go
package main
import (
"fmt"
"github.com/xiaoquanwei/goTools/secret"
)
func main() {
fmt.Println(secret.Md5("hello"))
}
6、发布版本号
上面提交的包,其实还没有一个发布的版本
git tag -a v1.0.0 -m "release version v1.0.0"
git push origin v1.0.0
6、上面的 secret 包中的 Md5 函数返回是乱码的,我们修复一下,提交后,然后打一个版本出来。
// 修复了代码
git add .
git commit -m "fixed Md5()"
git push origin master
git tag -a v1.0.1 -m "fixed Md5()"
git push origin v1.0.1
7、将包更新到v1.0.1版本
go get github.com/xiaoquanwei/goTools@v1.0.1
再次测试Md5() 函数是否乱码