安全地将 Make 变量传递给 shell 命令
Safely pass Make variable to shell commands
考虑这个 Makefile:
VAR1=oneword
VAR2=two words
VAR3=three" quoted "words
test:
printf '>%s< ' "$(VAR1)" "$(VAR2)" "$(VAR3)"
@echo
如果我运行它,我得到
$ make test
printf '>%s< ' "oneword" "two words" "three" quoted "words"
>oneword< >two words< >three< >quoted< >words< print
但我希望得到与我 运行 以下命令相同的结果:
$ printf '>%s< ' "oneword" "two words" "three\" quoted \"words"
>oneword< >two words< >three" quoted "words<
假设我无法更改变量,即我必须以某种方式更改对 printf
的调用。
换句话说:如何将 Make 变量的内容作为一个参数传递给 shell 命令,而不会拆分为多个或任何特定的 shell 效果?
Make 支持 export
指令通过环境传递文字内容:
VAR1=oneword
VAR2=two words
VAR3=three" quoted "words
export VAR1
export VAR2
export VAR3
test:
printf '>%s< ' "$$VAR1" "$$VAR2" "$$VAR3"
echo
输出:
$ make test
printf '>%s< ' "$VAR1" "$VAR2" "$VAR3"
>oneword< >two words< >three" quoted "words< echo
我找到了解决办法。它的可读性不是很好,但似乎非常可靠。
想法是在 shell 级别 ('
) 使用单引号,因为那里没有变量插值或其他奇怪的事情发生。此外,这意味着我们唯一需要担心的变量内容中的字符是单引号,并且可以可靠地替换这些字符:
VAR1=oneword
VAR2=two words
VAR3=three" quoted 'words
test:
printf '>%s< ' '$(subst ','\'',$(VAR1))' '$(subst ','\'',$(VAR2))' '$(subst ','\'',$(VAR3))'
@echo
现在我明白了
$ make test
printf '>%s< ' 'oneword' 'two words' 'three" quoted '\''words'
>oneword< >two words< >three" quoted 'words<
请注意 make 如何正确转义 '
,以及 shell 命令如何可靠地接收它。
考虑这个 Makefile:
VAR1=oneword
VAR2=two words
VAR3=three" quoted "words
test:
printf '>%s< ' "$(VAR1)" "$(VAR2)" "$(VAR3)"
@echo
如果我运行它,我得到
$ make test
printf '>%s< ' "oneword" "two words" "three" quoted "words"
>oneword< >two words< >three< >quoted< >words< print
但我希望得到与我 运行 以下命令相同的结果:
$ printf '>%s< ' "oneword" "two words" "three\" quoted \"words"
>oneword< >two words< >three" quoted "words<
假设我无法更改变量,即我必须以某种方式更改对 printf
的调用。
换句话说:如何将 Make 变量的内容作为一个参数传递给 shell 命令,而不会拆分为多个或任何特定的 shell 效果?
Make 支持 export
指令通过环境传递文字内容:
VAR1=oneword
VAR2=two words
VAR3=three" quoted "words
export VAR1
export VAR2
export VAR3
test:
printf '>%s< ' "$$VAR1" "$$VAR2" "$$VAR3"
echo
输出:
$ make test
printf '>%s< ' "$VAR1" "$VAR2" "$VAR3"
>oneword< >two words< >three" quoted "words< echo
我找到了解决办法。它的可读性不是很好,但似乎非常可靠。
想法是在 shell 级别 ('
) 使用单引号,因为那里没有变量插值或其他奇怪的事情发生。此外,这意味着我们唯一需要担心的变量内容中的字符是单引号,并且可以可靠地替换这些字符:
VAR1=oneword
VAR2=two words
VAR3=three" quoted 'words
test:
printf '>%s< ' '$(subst ','\'',$(VAR1))' '$(subst ','\'',$(VAR2))' '$(subst ','\'',$(VAR3))'
@echo
现在我明白了
$ make test
printf '>%s< ' 'oneword' 'two words' 'three" quoted '\''words'
>oneword< >two words< >three" quoted 'words<
请注意 make 如何正确转义 '
,以及 shell 命令如何可靠地接收它。