Skip to content

Go 语言实战 第 3 章 打包和工具链

🏷️ Go 《Go 语言实战》

在 Go 语言中,包是个非常重要的概念。
其设计理念是使用包来封装不同语义单元的功能。

所有的 .go 文件,除了空行和注释,都应该在第一行声明自己所属的包。
每个包都在单独的目录里。
同一个目录下的所有 .go 文件必须声明同一个包名。

给包命名的惯例是使用包所在目录的名字。
给包及其目录命名时,应该使用简洁、清晰且全小写的名字。

main 包

在 Go 语言中,命名为 main 的包具有特殊的含义。
所有用 Go 语言编译的可执行程序都必须有一个名叫 main 的包。
main() 函数是程序的入口。
程序编译时,会使用声明为 main 包的代码所在的目录的目录名作为二进制可执行文件的文件名。

导入

使用 import 语句导入包。
编译器会使用 Go 环境变量设置的路径,通过引入的相对路径来查找磁盘上的包。
标准库中的包会在安装 Go 的位置找到。Go 开发者创建的包会在 GOPATH 环境变量指定的目录里查找。
GOPATH 指定的这些目录就是开发者的个人工作空间。

一旦编译器找到一个满足 import 语句的包,就停止进一步的查找。
编译器会首先查找 Go 的安装目录,然后才会按顺序查找 GOPATH 变量里列出的目录。

Go 语言的工具链本身支持从 DVCS(Distributed Version Control Systems)网站获取源代码。
这个过程使用 go get 命令完成。

go
import "github.com/spf13/viper"

命名导入

导入的多个包具有相同的名字时,可以使用命名导入

go
import (
    "fmt"
    myfmt "mylib/fmt"
)

导入未在代码中使用的包时,可以使用空白标识符_)。

go
import (
    _ "fmt"
)

init 函数

所有被编译器发现的 init 函数都会安排在 main 函数之前执行。
init 函数用在设置包、初始化变量或者其它要在程序运行前优先完成的引导工作。

使用 Go 的工具

查看 Go 提供的命令:

powershell
PS C:\go\src\hello> go
Go is a tool for managing Go source code.

Usage:

        go <command> [arguments]

The commands are:

        bug         start a bug report
        build       compile packages and dependencies
        clean       remove object files and cached files
        doc         show documentation for package or symbol
        env         print Go environment information
        fix         update packages to use new APIs
        fmt         gofmt (reformat) package sources
        generate    generate Go files by processing source
        get         add dependencies to current module and install them
        install     compile and install packages and dependencies
        list        list packages or modules
        mod         module maintenance
        run         compile and run Go program
        test        test packages
        tool        run specified go tool
        version     print Go version
        vet         report likely mistakes in packages

Use "go help <command>" for more information about a command.

Additional help topics:

        buildmode   build modes
        c           calling between Go and C
        cache       build and test caching
        environment environment variables
        filetype    file types
        go.mod      the go.mod file
        gopath      GOPATH environment variable
        gopath-get  legacy GOPATH go get
        goproxy     module proxy protocol
        importpath  import path syntax
        modules     modules, module versions, and more
        module-get  module-aware go get
        module-auth module authentication using go.sum
        module-private module configuration for non-public modules
        packages    package lists and patterns
        testflag    testing flags
        testfunc    testing functions

Use "go help <topic>" for more information about that topic.

编译 & 清除

powershell
PS C:\go\src\hello> go build .\hello.go
PS C:\go\src\hello> go clean .\hello.go

大部分 Go 工具命令都会接受一个包名作为参数。

有些命令可以简写。如 build ,此时默认使用当前目录来编译。

powershell
PS C:\go\src\hello> go build

可以直接指定包,此时还可以使用通配符。三个点表示匹配所有字符串。

powershell
PS C:\go\src> go build .\github.com\goinaction\code\chapter3\wordcount
PS C:\go\src> go build .\github.com\goinaction\code\chapter3\wordcount\...

文件在当前目录时,可以使用段路径:文件名 或者 .

powershell
PS C:\go\src\github.com\goinaction\code\chapter3\wordcount> go build .\wordcount.go
PS C:\go\src\github.com\goinaction\code\chapter3\wordcount> go build .

编译和运行一起执行时可以使用 run 命令。

powershell
PS C:\go\src\hello> go run .\hello.go
Hello World!

go vet: 帮助开发人员检测代码的常见错误:

  • Printf 类函数调用时,类型匹配错误的参数;
  • 定义常用的方法时,方法签名的错误;
  • 错误的结构标签;
  • 没有指定字段名的结构字面量。

go fmt:自动格式指定的源代码并保存。

go doc:在终端上打印文档。

godoc:启动一个 Web 服务器,通过点击的方式查看 Go 语言的包的文档。支持开发者自己写的代码。

powershell
godoc -http:6060

代码文档规则:

  • 在标识符之前,把想要的文档作为注释加入到代码中。
  • 如果想给包写一段文字量比较大的文档,可以在工程里包含一个叫做 doc.go 的文件,使用同样的包名,并把包的介绍使用注释加在包声明之前。
  • 多行注释使用 \* *\ 符号。

创建代码库以分享:

  • 包应该在代码库的根目录中。
  • 包可以非常小。
  • 对代码执行 go fmt
  • 给代码写文档。

依赖管理

  • Keith Rarikgodep
  • Daniel Theophanesvendor
  • Gustavo Niemeyergopkg.in

godepvendor 使用第三方 verdoring 导入路径重写特性解决依赖问题。

gb

gb 是一个由 Go 社区成员开发的全新的构建工具。
gb 工程会区分开发人员写的代码和开发人员需要依赖的代码(第三方代码)。
gb 一个最好的特点是,不需要重写导入路径。
gb 工具首先会在 $PROJECT/srv/ 目录查找代码,如果找不到,会在 $PROJECT/vendor/src 目录里查找。
自己写的代码在工程目录的 src 目录中,第三方依赖代码在工程目录的 verdor/src 目录中。

gb 工程和 Go 官方工具链(包括 go get)并不兼容。

powershell
gb build all

更多 gb 特性可以访问 getgb.io

小结

  • 在 Go 语言中包是组织代码的基本单位。
  • 环境变量 GOPATH 决定了 Go 源代码在磁盘上被保存、编译和安装的位置。
  • 可以为每个工程设置不同的 GOPATH,以保持源代码和依赖的隔离。
  • go 工具是在命令行上工作的最好工具。
  • 开发人员可以使用 go get 来获取别人的包并将其安装到自己的 GOPATH 指定的目录。
  • 想要为别人创建包很简单,只要把源代码放到公用代码库,并遵守一些简单规则就可以。
  • Go 语言在设计时将分享代码作为语言的核心特性和驱动力。
  • 推荐使用依赖管理工具来管理依赖。
  • 由很多社区开发的依赖管理工具,如 godepvendorgb