linux: Makefile编写技巧温故

2024-06-14 13:41:41 浏览数 (2)

在系统运维中,Makefile 是一种强大的工具,用于管理和自动化各种任务。它能够有效地处理任务执行、文件生成、系统管理等操作。本文将介绍一些常见的Makefile编写技巧,帮助运维工程师更好地利用Makefile来自动化任务。

1. 基础语法

Makefile 由一系列的规则组成,每条规则定义了一个目标及其依赖和生成方式。基本的Makefile语法如下:

代码语言:javascript复制

makefile
target: dependencies
    command

其中:

  • target 是要生成的文件或执行的任务。
  • dependencies 是生成目标所需的文件或任务。
  • command 是生成目标的命令,必须以一个TAB字符开头。

示例

代码语言:javascript复制

makefile
all: deploy

deploy:
    ansible-playbook -i inventory.ini site.yml

clean:
    rm -rf /tmp/deployment

2. 使用变量

在Makefile中使用变量可以提高可读性和可维护性。变量可以在定义时赋值,也可以通过命令执行时赋值。

代码语言:javascript复制

makefile
PLAYBOOK = site.yml
INVENTORY = inventory.ini

all: deploy

deploy:
    ansible-playbook -i $(INVENTORY) $(PLAYBOOK)

clean:
    rm -rf /tmp/deployment

3. 为特定目标设置变量

有时需要为特定目标设置不同的变量。这可以通过目标特定变量实现。

代码语言:javascript复制

makefile
deploy_prod: INVENTORY = prod_inventory.ini
deploy_dev: INVENTORY = dev_inventory.ini

deploy_prod: deploy
deploy_dev: deploy

deploy:
    ansible-playbook -i $(INVENTORY) $(PLAYBOOK)

clean:
    rm -rf /tmp/deployment

4. 使用条件赋值

条件赋值(?=)用于在变量未定义时进行赋值。这在需要提供默认值时非常有用。

代码语言:javascript复制

makefile
PLAYBOOK ?= site.yml
INVENTORY ?= inventory.ini

deploy:
    ansible-playbook -i $(INVENTORY) $(PLAYBOOK)

5. 忽略命令错误

可以通过在命令前添加减号(-)来忽略该命令的错误返回状态,使Make继续执行后续命令。

代码语言:javascript复制

makefile
clean:
    -rm -rf /tmp/deployment

6. 执行命令获取内容赋值给变量

在Makefile中,可以使用命令替换来执行命令并将其输出赋值给变量。

代码语言:javascript复制

makefile
BRANCH_NAME := $(shell git rev-parse --abbrev-ref HEAD)
CURRENT_DATE := $(shell date  %Y-%m-%d)

print_info:
    @echo Current Git branch: $(BRANCH_NAME)
    @echo Current date: $(CURRENT_DATE)

7. 组合规则和伪目标

伪目标用于定义不生成文件的目标,通常用于清理、测试等任务。使用.PHONY声明伪目标可以避免与文件名冲突。

代码语言:javascript复制

makefile
.PHONY: all clean deploy_prod deploy_dev

all: deploy_prod deploy_dev

deploy_prod: INVENTORY = prod_inventory.ini
deploy_dev: INVENTORY = dev_inventory.ini

deploy_prod: deploy
deploy_dev: deploy

deploy:
    ansible-playbook -i $(INVENTORY) $(PLAYBOOK)

clean:
    rm -rf /tmp/deployment

8. 高效自动化任务

通过使用模式规则,可以简化重复的规则定义,提高Makefile的可维护性。

代码语言:javascript复制

makefile
SCRIPTS = backup.sh cleanup.sh monitor.sh

%.run:
    ./scripts/$*

all: $(SCRIPTS:.sh=.run)

clean:
    rm -rf /tmp/deployment

在这个例子中,%.run 是一个模式规则,匹配所有以 .run 结尾的目标,并执行对应的脚本。SCRIPTS 变量列出了所有需要执行的脚本,并将其转换为相应的目标。

通过这些技巧,我们可以编写更高效、更灵活的Makefile,自动化管理我们的运维任务。无论是简单的脚本执行还是复杂的系统部署,Makefile都能提供强大的支持。

0 人点赞