Golang最被诟病的三个问题: module管理机制, 泛型, 错误处理
go mod 就是用来解决 module 管理机制
首先,把 go 的版本升级到 1.12.x. 可以用 go help mod 看到 go mod 的子命令

Note that support for modules is built into all the go commands,
not just 'go mod'. For example, day-to-day adding, removing, upgrading,
and downgrading of dependencies should be done using 'go get'.
See 'go help modules' for an overview of module functionality.

Usage:
    go mod <command> [arguments]

The commands are:
    
    download    download modules to local cache (下载依赖包)
    edit        edit go.mod from tools or scripts (编辑go.mod)
    graph       print module requirement graph (打印模块依赖图)
    init        initialize new module in current directory (在当前目录初始化mod)
    tidy        add missing and remove unused modules (拉取缺少的模块,移除不用的模块)
    vendor      make vendored copy of dependencies (将依赖复制到vendor下)
    verify      verify dependencies have expected content (验证依赖是否正确)
    why         explain why packages or modules are needed (解释为什么需要依赖)
    
Use "go help mod <command>" for more information about a command.

其次,在项目目录下,一般是 main.go(func main()所在的源文件) 所在的目录下,执行 go mod init 项目名,这个命令会在执行命令的当前目录下生成一个 go.mod 文件,内容如下:

D:\GOProject\src\go-printcloud-authemail>go mod init go-printcloud-authemail
go: creating new go.mod: module go-printcloud-authemail
go: copying requirements from Godeps\Godeps.json
......

设置 GO111MODULE

  • GO111MODULE = off,go命令行将不会支持 module功能,寻找依赖包的方式将会沿用旧版本那种通过 vendor 目录或者 GOPATH 模式来查找。
  • GO111MODULE = on,go命令行会使用 modules,而一点也不会去 GOPATH 目录下查找。
  • GO111MODULE = auto,默认值,go命令行将会根据当前目录来决定是否启用 module 功能。这种情况下可以分为两种情形:

    1. 当前目录在 GOPATH/src 之外且该目录包含 go.mod文件
    2. 当前文件在包含 go.mod 文件的目录下面。

当modules 功能启用时,依赖包的存放位置变更为 $GOPATH/pkg,允许同一个 package 多个版本并存,且多个项目可以共享缓存的 module。

最重要的一步来了,因为众所周知的原因,很多包不能直接下载,可以用 proxy,如果找不到 proxy,那么只能用 replace,用文本编辑器打开 go.mod,加入如下内容:

replace (
    golang.org/x/text => github.com/golang/text latest
    golang.org/x/net => github.com/golang/net latest
    golang.org/x/crypto => github.com/golang/crypto latest
    golang.org/x/tools => github.com/golang/tools latest
    golang.org/x/sync => github.com/golang/sync latest
    golang.org/x/sys => github.com/golang/sys latest
)

然后执行 go mod tidy 这个命令会把 latest 自动替换成最新的版本号,例子:

replace (
    golang.org/x/crypto => github.com/golang/crypto v0.0.0-20191011191535-87dc89f01550
    golang.org/x/sys => github.com/golang/sys v0.0.0-20191024073052-e66fe6eb8e0c
    golang.org/x/text => github.com/golang/text v0.3.2
    golang.org/x/time => github.com/golang/time v0.0.0-20191024005414-555d28b269f0
    google.golang.org/genproto => github.com/google/go-genproto v0.0.0-20191009194640-548a555dbc03
    google.golang.org/grpc => github.com/grpc/grpc-go v1.24.0
)

如果是老项目,一般不会那么容易就成功,会提示各种错误,比如出现如下错误:

go: github.com/Sirupsen/logrus@v0.0.0-20190423093405-5521996833c0: parsing go.mod: unexpected module path "github.com/sirupsen/logrus"
go: error loading module requirements

其实就是提示 Sirupsen/logrus 其实应该是 sirupsen/logrus 路径问题,所以我们手动修改go.mod。然后再执行 go mod tidy ,如果出错,看是路径还是版本或者其它问题,再把需要的版本加入修改go.mod 文件,反复几次,最后就可以成功了。我最后的go.mod 是这样的:

module go-printcloud-authemail
go 1.12

replace (
    github.com/Sirupsen/logrus v1.0.5 => github.com/sirupsen/logrus v1.0.5
    github.com/Sirupsen/logrus v1.3.0 => github.com/Sirupsen/logrus v1.0.6
    github.com/Sirupsen/logrus v1.4.0 => github.com/sirupsen/logrus v1.0.6
    golang.org/x/crypto => github.com/golang/crypto v0.0.0-20191011191535-87dc89f01550
    golang.org/x/net => github.com/golang/net v0.0.0-20191028085509-fe3aa8a45271
    golang.org/x/sync => github.com/golang/sync v0.0.0-20190911185100-cd5d95a43a6e
    golang.org/x/sys => github.com/golang/sys v0.0.0-20191024073052-e66fe6eb8e0c
    golang.org/x/text => github.com/golang/text v0.3.2
    golang.org/x/time => github.com/golang/time v0.0.0-20191024005414-555d28b269f0
    golang.org/x/tools => github.com/golang/tools v0.0.0-20191029041327-9cc4af7d6b2c
    golang.org/x/xerrors => github.com/golang/xerrors v0.0.0-20191011141410-1b5146add898
    google.golang.org/genproto => github.com/google/go-genproto v0.0.0-20191009194640-548a555dbc03
    google.golang.org/grpc => github.com/grpc/grpc-go v1.24.0
)

require (
    github.com/360EntSecGroup-Skylar/excelize v0.0.0-20190407060441-4e7d93a77796
    github.com/BurntSushi/toml v0.3.1 // indirect
    github.com/Sirupsen/logrus v1.4.0
    github.com/denisenkom/go-mssqldb v0.0.0-20191001013358-cfbb681360f0 // indirect
    github.com/emersion/go-imap v1.0.0
    github.com/emersion/go-message v0.10.4
    github.com/emersion/go-sasl v0.0.0-20190704090222-36b50694675c // indirect
    github.com/erikstmartin/go-testdb v0.0.0-20160219214506-8d10e4a1bae5 // indirect
    github.com/go-sql-driver/mysql v0.0.0-20190510102335-877a9775f068 // indirect
    github.com/hashicorp/hcl v0.0.0-20180404174102-ef8a98b0bbce // indirect
    github.com/jinzhu/gorm v0.0.0-20180625050753-0fd395ab37ae
    github.com/jinzhu/inflection v0.0.0-20180308033659-04140366298a // indirect
    github.com/jinzhu/now v1.1.1 // indirect
    github.com/konsorten/go-windows-terminal-sequences v1.0.2 // indirect
    github.com/lib/pq v0.0.0-20190507191818-2ff3cb3adc01 // indirect
    github.com/magiconair/properties v1.8.0 // indirect
    github.com/martinlindhe/base36 v1.0.0 // indirect
    github.com/mattn/go-sqlite3 v1.11.0 // indirect
    github.com/mitchellh/mapstructure v0.0.0-20180511142126-bb74f1db0675 // indirect
    github.com/onsi/ginkgo v1.10.2 // indirect
    github.com/onsi/gomega v1.7.0 // indirect
    github.com/pelletier/go-toml v1.2.0 // indirect
    github.com/robfig/cron v1.2.0
    github.com/sirupsen/logrus v1.4.2 // indirect
    github.com/spf13/afero v1.1.1 // indirect
    github.com/spf13/cast v1.2.0
    github.com/spf13/jwalterweatherman v0.0.0-20180109140146-7c0cea34c8ec // indirect
    github.com/spf13/pflag v0.0.0-20180601132542-3ebe029320b2 // indirect
    github.com/spf13/viper v0.0.0-20180507071007-15738813a09d // indirect
    github.com/sunmi-OS/gocore v1.0.1-0.20190723035437-2c216bcac93b
    github.com/urfave/cli v0.0.0-20190203184040-693af58b4d51
    gopkg.in/airbrake/gobrake.v2 v2.0.9 // indirect
    gopkg.in/gemnasium/logrus-airbrake-hook.v2 v2.1.2 // indirect
    gopkg.in/yaml.v2 v2.2.3-0.20190319135612-7b8349ac747c // indirect
)

最后,附上常用的replace列表:

golang.org/x/text => github.com/golang/text latest

golang.org/x/net => github.com/golang/net latest

golang.org/x/crypto => github.com/golang/crypto latest

golang.org/x/tools => github.com/golang/tools latest

golang.org/x/sync => github.com/golang/sync latest

golang.org/x/sys => github.com/golang/sys latest

cloud.google.com/go => github.com/googleapis/google-cloud-go latest

google.golang.org/genproto => github.com/google/go-genproto latest

golang.org/x/exp => github.com/golang/exp latest

golang.org/x/time => github.com/golang/time latest

golang.org/x/oauth2 => github.com/golang/oauth2 latest

golang.org/x/lint => github.com/golang/lint latest

google.golang.org/grpc => github.com/grpc/grpc-go latest

google.golang.org/api => github.com/googleapis/google-api-go-client latest

google.golang.org/appengine => github.com/golang/appengine latest

golang.org/x/mobile => github.com/golang/mobile latest

golang.org/x/image => github.com/golang/image latest

cloud.google.com/go => github.com/googleapis/google-cloud-go v0.34.0

github.com/go-tomb/tomb => gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7

go.opencensus.io => github.com/census-instrumentation/opencensus-go v0.19.0

go.uber.org/atomic => github.com/uber-go/atomic v1.3.2

go.uber.org/multierr => github.com/uber-go/multierr v1.1.0

go.uber.org/zap => github.com/uber-go/zap v1.9.1

google.golang.org/api => github.com/googleapis/google-api-go-client v0.0.0-20181220000619-583d854617af

google.golang.org/appengine => github.com/golang/appengine v1.3.0

google.golang.org/genproto => github.com/google/go-genproto v0.0.0-20181219182458-5a97ab628bfb

google.golang.org/grpc => github.com/grpc/grpc-go v1.17.0

gopkg.in/alecthomas/kingpin.v2 => github.com/alecthomas/kingpin v2.2.6+incompatible

gopkg.in/mgo.v2 => github.com/go-mgo/mgo v0.0.0-20180705113604-9856a29383ce

gopkg.in/vmihailenco/msgpack.v2 => github.com/vmihailenco/msgpack v2.9.1+incompatible

gopkg.in/yaml.v2 => github.com/go-yaml/yaml v0.0.0-20181115110504-51d6538a90f8

labix.org/v2/mgo => github.com/go-mgo/mgo v0.0.0-20160801194620-b6121c6199b7

launchpad.net/gocheck => github.com/go-check/check v0.0.0-20180628173108-788fd7840127

最后修改:2020 年 06 月 09 日 12 : 47 PM
如果觉得我的文章对你有用,请随意赞赏