使用makefile帮助GO项目开发

使用makefile可以快捷管理和构建自己的go项目, 适用于linux远程开发等环境.

提供一个基础的makefile供开发使用.

大部分是针对常用指令的二次封装

Makefile

先展示文件内容, 之后讲解具体指令功能和实现

# -------------------------------------------------------------------------------
# Makefile for go project
# -------------------------------------------------------------------------------

# -------------------------------------------------------------------------------
# variables
# -------------------------------------------------------------------------------
MAIN_FILE := main.go

BIN_DIR := ./bin
APP := main # the name of the application

# the name of the docker image
# DOCKER_IMAGE_NAME := docker-image-name-example

# args
STATIC_ARGS := -ldflags='-extldflags "-static"'
RACE_ARGS := -race

# this dir is for the test output when u run `test` cmd
TEST_OUTPUT_DIR := ./test_output

# color code
GREEN_COLOR_CODE_HEAD := \033[32m
GREEN_COLOR_CODE_END := \033[0m
RED_COLOR_CODE_HEAD := \033[31m
RED_COLOR_CODE_END := \033[0m

# -------------------------------------------------------------------------------
# commands
# -------------------------------------------------------------------------------

# build the application
.PHONY: build
build:
	go build -o $(BIN_DIR)/$(APP) $(MAIN_FILE)

# build the application statically
# you can use this if you want to run the application on a system without a C compiler
# if you use glibc, you can also use the static version of glibc(like musl)
.PHONY: build-static
build-static:
	go build $(STATIC_ARGS) -o $(BIN_DIR)/$(APP) $(MAIN_FILE)

# build the application with docker
# u need to set the DOCKER_IMAGE_NAME variable
.PHONY: build-docker
build-docker:
	docker build -t $(DOCKER_IMAGE_NAME) .
	@$(show_info)"Docker image built successfully: $(GREEN_COLOR_CODE_HEAD)$(DOCKER_IMAGE_NAME)$(GREEN_COLOR_CODE_END)";

# run the application with race detector
# use this cmd when u develop
.PHONY: run
run:
	go run $(RACE_ARGS) $(MAIN_FILE)

# test application
# it will create a coverage.out file(for test coverage)
.PHONY: test
test:
	mkdir -p $(TEST_OUTPUT_DIR)
	go test -v -covermode=set -coverprofile=$(TEST_OUTPUT_DIR)/coverage.out ./...

# show the test coverage
# it will create a coverage.html file from coverage.out
# so, u need to run `test` cmd first
.PHONY: test-coverage
test-coverage: test
	go tool cover -html=$(TEST_OUTPUT_DIR)/coverage.out -o $(TEST_OUTPUT_DIR)/coverage.html
	@$(show_info)"Please open $(GREEN_COLOR_CODE_HEAD)$(TEST_OUTPUT_DIR)/coverage.html$(GREEN_COLOR_CODE_END) to see the test coverage"

# clean the application
# it will remove the bin directory and the test output directory
.PHONY: clean
clean:
	go clean
	rm -rf $(BIN_DIR) $(TEST_OUTPUT_DIR)

# -------------------------------------------------------------------------------
# functions
# -------------------------------------------------------------------------------

# echo time
TIMESTAMP_FORMAT := %Y-%m-%d %H:%M:%S
define timestamp
	$(shell date "+$(TIMESTAMP_FORMAT)")
endef

# show info
INFO_PREFIX := *INFO
define show_info
	@echo -e "$(GREEN_COLOR_CODE_HEAD)$(INFO_PREFIX):$(GREEN_COLOR_CODE_END)"
	@echo -e $(1)
endef

# show error
# it will exit the program
ERROR_PREFIX := *ERROR
define show_error
	@echo -e "$(RED_COLOR_CODE_HEAD)$(ERROR_PREFIX):$(RED_COLOR_CODE_END)"
	@echo -e $(1)
	exit 1
endef
  • build: 基本构建指令, 最简单的编译二级制可执行文件的指令.
  • build-static: 编译静态文件
  • build-docker: 打包docker image
  • run: 开发中测试代码
  • test: 运行单元测试
  • test-coverage: 使用HTML的方式展示单元测试的覆盖率
  • clean: 清理

build

# build the application
.PHONY: build
build:
	go build -o $(BIN_DIR)/$(APP) $(MAIN_FILE)

最基础的go的编译运行的方式

  • 编译出来的可执行文件在bin目录下

build-static

# build the application statically
# you can use this if you want to run the application on a system without a C compiler
# if you use glibc, you can also use the static version of glibc(like musl)
.PHONY: build-static
build-static:
	go build $(STATIC_ARGS) -o $(BIN_DIR)/$(APP) $(MAIN_FILE)

GO默认编译出来的就是静态的文件, 但是可能需要依赖C的库, 为了进一步的静态编译, 可以使用这个指令

在设置网络编程的时候, 可能存在glibc库无法编译进去, 可以使用musl版本的

build-docker

# build the application with docker
# u need to set the DOCKER_IMAGE_NAME variable
.PHONY: build-docker
build-docker:
	docker build -t $(DOCKER_IMAGE_NAME) .
	@$(show_info)"Docker image built successfully: $(GREEN_COLOR_CODE_HEAD)$(DOCKER_IMAGE_NAME)$(GREEN_COLOR_CODE_END)";

打包docker image, 需要自己在当前目录编写好dockerfile

  • 需要自己设置好DOCKER_IMAGE_NAME配置的名字

运行成功之后会输出Docker image built successfully: XXX

run

# run the application with race detector
# use this cmd when u develop
.PHONY: run
run:
	go run $(RACE_ARGS) $(MAIN_FILE)

在dev的时候运行程序, 带上-race检查竞态

它可以帮助开发者检测并发程序中的数据竞争问题。数据竞争是指多个goroutine同时访问共享内存,并且至少有一个访问是写操作,而没有使用同步机制来保护共享数据,这会导致程序的行为变得不可预测,甚至崩溃。

test

# test application
# it will create a coverage.out file(for test coverage)
.PHONY: test
test:
	mkdir -p $(TEST_OUTPUT_DIR)
	go test -v -covermode=set -coverprofile=$(TEST_OUTPUT_DIR)/coverage.out ./...

执行单元测试

会创建一个用于单元测试输出的文件夹

输出的coverage.out文件说明了单元测试的覆盖率情况, 这一般使用百分比表示

效果:

.
└── test_output
    ├── coverage.html
    └── coverage.out

test-coverage

# show the test coverage
# it will create a coverage.html file from coverage.out
# so, u need to run `test` cmd first
.PHONY: test-coverage
test-coverage: test
	go tool cover -html=$(TEST_OUTPUT_DIR)/coverage.out -o $(TEST_OUTPUT_DIR)/coverage.html
	@$(show_info)"Please open $(GREEN_COLOR_CODE_HEAD)$(TEST_OUTPUT_DIR)/coverage.html$(GREEN_COLOR_CODE_END) to see the test coverage"

生成展示单元测试覆盖情况的HTML文件

可以在浏览器中打开并且查看效果

clean

# clean the application
# it will remove the bin directory and the test output directory
.PHONY: clean
clean:
	go clean
	rm -rf $(BIN_DIR) $(TEST_OUTPUT_DIR)

清除文件

包含GO的编译文件和test输出文件

函数

# show info
INFO_PREFIX := *INFO
define show_info
	@echo -e "$(GREEN_COLOR_CODE_HEAD)$(INFO_PREFIX):$(GREEN_COLOR_CODE_END)"
	@echo -e $(1)
endef

# show error
# it will exit the program
ERROR_PREFIX := *ERROR
define show_error
	@echo -e "$(RED_COLOR_CODE_HEAD)$(ERROR_PREFIX):$(RED_COLOR_CODE_END)"
	@echo -e $(1)
	exit 1
endef

一些函数帮助格式化输出一些tips内容

  • 打印error message的时候会直接使用exit 1退出, 因为出现了错误
posted @   xuhe2  阅读(17)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 微软正式发布.NET 10 Preview 1:开启下一代开发框架新篇章
· 没有源码,如何修改代码逻辑?
· PowerShell开发游戏 · 打蜜蜂
· 在鹅厂做java开发是什么体验
· WPF到Web的无缝过渡:英雄联盟客户端的OpenSilver迁移实战
点击右上角即可分享
微信分享提示