我正在尝试在Makefile中设置环境变量,以便它可以在运行于sam shell中的另一个程序中以make
的形式使用,但是要在make
运行之后使用。
更新:根据接受的带有答案的答案,这是不可能的。
步骤:
make test
设置环境:export TEST_ENV_ONE=OneString
TEST_ENV_ONE
尝试过:
不起作用:
test:
export TEST_ENV_ONE=OneString
$(shell export TEST_ENV_TWO=TwoString)
此后为空:
echo $TEST_ENV_ONE
echo $TEST_ENV_TWO
答案 0 :(得分:2)
您上面的export TEST_ENV_ONE=OneString
在专用的shell中运行。后续命令在其他Shell实例中运行。因此,它们不会继承环境变量TEST_ENV_ONE
。
您可以在生成文件中使用顶层(即不在目标配方中)export
directive:
export env_var := MyEnvVariable
.PHONY: all
all:
echo env_var: $$env_var
这样,变量env_var
被导出到将执行配方的shell中。
如果使用上面的生成文件运行make
:
$ make
echo env_var: $env_var
env_var: MyEnvVariable
从输出中可以看到,运行echo env_var: $env_var
的shell在其环境中具有变量env_var
。
答案 1 :(得分:1)
如果您希望将环境变量导出到您从中调用的外壳程序,将使事情变得有些困难,因为正如ネロク所解释的那样,您无法将环境变量直接从子进程(make
)导出到它的父进程(您从中调用make
的外壳)。但是,如果您接受调用make这样的话:
eval $(make)
那么这确实有可能:只需在食谱中回显export VARIABLE1=VALUE1; export VARIABLE2=VALUE2; ...
。警告:您还必须保证标准输入上的make不会回显其他任何内容。但是您可以改用标准错误。示例:
$ cat Makefile
export TEST_ENV_ONE := OneString
all:
@printf 'make variable TEST_ENV_ONE = %s\n' "$(TEST_ENV_ONE)" 1>&2
@printf 'in-recipe shell variable TEST_ENV_ONE = %s\n' "$$TEST_ENV_ONE" 1>&2
@printf 'export TEST_ENV_ONE="%s"\n' '$(TEST_ENV_ONE)'
$ unset TEST_ENV_ONE
$ printenv TEST_ENV_ONE
$ eval $(make)
make variable TEST_ENV_ONE = OneString
in-recipe shell variable TEST_ENV_ONE = OneString
$ printenv TEST_ENV_ONE
OneString
请注意,make或多或少将环境变量视为make变量。从GNU制作手册:
make中的变量可以来自运行make的环境。 make在启动时看到的每个环境变量都是 转换为具有相同名称和值的make变量。 但是,在makefile中或使用命令进行显式分配 参数,覆盖环境。 (如果指定了“ -e”标志, 然后来自环境的值将覆盖makefile中的分配。 请参阅选项摘要。但这不是推荐的做法。)
因此,除非变量的值是make自身进行复杂计算的结果,否则获得相同结果的更自然的方法是在父shell中定义环境变量并按原样使用它。生成文件:
$ cat Makefile
all:
@printf 'make variable TEST_ENV_ONE = %s\n' "$(TEST_ENV_ONE)"
@printf 'in-recipe shell variable TEST_ENV_ONE = %s\n' "$$TEST_ENV_ONE"
$ export TEST_ENV_ONE=OneString
$ make
make variable TEST_ENV_ONE = OneString
in-recipe shell variable TEST_ENV_ONE = OneString
$ printenv TEST_ENV_ONE
OneString