在Golang项目开发中,我们经常需要执行编译生成二进制文件、运行单元测试、清理临时文件、跨平台打包发布等操作,这些重复的命令如果每次都手动输入不仅效率低,还容易出错。Makefile作为一款经典的构建工具,可以通过定义规则把这些操作整合起来,只需要执行简单的make命令就能完成一系列流程。

Makefile基础语法说明
Makefile的核心是由规则组成的,每条规则的基本结构如下:
目标: 依赖
命令
其中目标是要执行的任务名称,依赖是执行该任务需要的前置条件,命令是具体要执行的操作,注意命令前必须有一个Tab键缩进,不能使用空格。我们可以通过make 目标名的方式来执行对应的规则,如果不指定目标,默认执行第一个规则。
Golang项目常用Makefile规则编写
编译当前项目
我们可以定义一个build目标,用来编译当前Golang项目,生成对应操作系统的二进制文件:
# 定义变量,指定编译后的二进制文件名称
BINARY_NAME=myapp
build:
go build -o ${BINARY_NAME} main.go
执行make build之后,就会在当前目录生成名为myapp的可执行文件。
清理编译产物
定义clean目标,用来删除编译生成的二进制文件和临时缓存:
BINARY_NAME=myapp
clean:
rm -f ${BINARY_NAME}
go clean
运行单元测试
定义test目标,执行项目的所有单元测试并输出覆盖率:
test:
go test -v -cover ./...
跨平台打包
Golang支持交叉编译,我们可以定义build-linux和build-win目标,分别生成Linux和Windows平台的二进制文件:
BINARY_NAME=myapp
# 编译Linux平台64位可执行文件
build-linux:
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o ${BINARY_NAME}_linux main.go
# 编译Windows平台64位可执行文件
build-win:
CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build -o ${BINARY_NAME}_win.exe main.go
完整Makefile示例
下面是一个整合了上述所有功能的完整Makefile示例,可以直接复制到Golang项目根目录使用:
# 二进制文件名称
BINARY_NAME=myapp
# 默认目标,执行build
all: build
# 编译当前平台二进制文件
build:
go build -o ${BINARY_NAME} main.go
# 清理编译产物
clean:
rm -f ${BINARY_NAME} ${BINARY_NAME}_linux ${BINARY_NAME}_win.exe
go clean
# 运行单元测试
test:
go test -v -cover ./...
# 编译Linux平台64位文件
build-linux:
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o ${BINARY_NAME}_linux main.go
# 编译Windows平台64位文件
build-win:
CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build -o ${BINARY_NAME}_win.exe main.go
# 打包所有平台产物
package: build-linux build-win
使用注意事项
- Makefile中命令前的缩进必须是Tab键,使用空格会导致执行报错
- 如果项目有多个main包,需要调整编译命令的路径,比如指定
./cmd/app作为编译入口 - 可以通过定义变量来统一管理二进制名称、编译参数等配置,后续修改更方便
- 如果需要执行make命令时传入参数,可以使用
make build VERSION=1.0.0的方式,在Makefile中通过${VERSION}获取参数值