这类似于
another issue,但是如果我正在运行特定目标并且尚未指定强制变量,我只希望make提示输入值.
目前的代码:
install-crontab: PASSWORD ?= "$(shell read -p "Password: "; echo "$$REPLY")" install-crontab: $(SCRIPT_PATH) @echo "@midnight \"$(SCRIPT_PATH)\" [...] \"$(PASSWORD)\""
Password: read: 1: arg count @midnight [...] ""
这里重要的一点是,我必须仅在运行此目标时询问,并且仅在未定义变量时才询问.我不能使用配置脚本,因为显然我不应该在配置脚本中存储密码,因为这个目标不是标准安装过程的一部分.
解决方法
事实证明,Makefile不使用Dash / Bash风格的引用,并且Dash的内置读取需要一个变量名,与Bash不同.结果代码:
install-crontab-delicIoUs: $(DELICIoUS_TARGET_PATH) @while [ -z "$$DELICIoUS_USER" ]; do \ read -r -p "DelicIoUs user name: " DELICIoUS_USER;\ done && \ while [ -z "$$DELICIoUS_PASSWORD" ]; do \ read -r -p "DelicIoUs password: " DELICIoUS_PASSWORD; \ done && \ while [ -z "$$DELICIoUS_PATH" ]; do \ read -r -p "DelicIoUs backup path: " DELICIoUS_PATH; \ done && \ ( \ CRONTAB_NOHEADER=Y crontab -l || true; \ printf '%s' \ '@midnight ' \ '"$(DELICIoUS_TARGET_PATH)" ' \ "\"$$DELICIoUS_USER\" " \ "\"$$DELICIoUS_PASSWORD\" " \ "\"$$DELICIoUS_PATH\""; \ printf '\n') | crontab -
结果:
$crontab -r; make install-crontab-delicIoUs && crontab -l DelicIoUs user name: a\b c\d DelicIoUs password: e f g DelicIoUs backup path: h\ i no crontab for <user> @midnight "/usr/local/bin/export_DelicIoUs" "a\b c\d" "e f g" "h\ i" $DELICIoUS_PASSWORD=foo make install-crontab-delicIoUs && crontab -l DelicIoUs user name: bar DelicIoUs backup path: baz @midnight "/usr/local/bin/export_DelicIoUs" "a\b c\d" "e f g" "h\ i" @midnight "/usr/local/bin/export_DelicIoUs" "bar" "foo" "baz"
这段代码:
>将所有输入字符视为文字,因此它适用于空格和反斜杠,>如果用户在没有写任何内容的情况下按Enter键,则可以避免>使用环境变量(如果存在),和>无论crontab是否为空,它都有效.