在Makefile中使用.env
的最佳方法是什么,即加载该文件并导出make
中子shell的所有变量?
如果建议的解决方案仅适用于make
,例如,不使用任何第三方工具。此外.env
个文件支持多行变量,如:
FOO="this\nis\na\nmultiline\nvar"
这就是this solution可能不够的原因。
答案 0 :(得分:3)
Make不提供任何方法将文件内容读取到某个变量。因此,我认为不使用外部工具就无法实现结果。但是,如果我错了,我会很高兴学到一些新技巧。
因此,我们假设有两个文件.env
,它们是技术上正确的shell文件:
FOO=bar
BAR="notfoo" # comment
#comment
MULTILINE="This\nis\nSparta!"
# comment
和script.sh
:
#!/bin/bash
echo FOO=${FOO}
echo BAR=${BAR}
echo -e ${MULTILINE}
一种解决方案是包含.env
文件,然后确保导出变量:
include .env
$(eval export $(shell sed -ne 's/ *#.*$//; /./ s/=.*$$// p' .env))
all:
./script.sh
由于shell和make对引号的处理方式不同,您将在输出中看到引号。
您可以通过make:
重新处理变量来避免这种情况include .env
VARS:=$(shell sed -ne 's/ *\#.*$$//; /./ s/=.*$$// p' .env )
$(foreach v,$(VARS),$(eval $(shell echo export $(v)="$($(v))")))
all:
./script.sh
然后多行变量变为单行。
最后,您可以生成一个临时文件,由bash处理并在运行任何命令之前将其获取:
SHELL=bash
all: .env-export
. .env-export && ./script.sh
.env-export: .env
sed -ne '/^export / {p;d}; /.*=/ s/^/export / p' .env > .env-export
哦,在这种情况下,多行变量中的新行被搞乱了。你需要另外引用它们。
最后,您可以使用上面的export
命令将sed
添加到.env,然后执行:
SHELL=bash
%: .env-export
. .env-export && make -f secondary "$@"