我想创建一个多次使用基本(提示和确认)函数的脚本,当我尝试设置返回任何变量时函数忽略参数
function promp() {
echo $*
read response
echo $response
}
function confirm() {
echo $*
read -rp $'(y/N) : ' -ei $'N' key;
case "$key" in
[yY][eE][sS]|[yY])
echo true
;;
*)
echo false
;;
esac
}
IS_RESPONSE=$(confirm "SOME QUESTION")
STRING_RESPONSE=$(promp "WRITE SOMETHING")
echo $IS_RESPONSE
echo $STRING_RESPONSE
SOME QUESTION
(y/N) : N
WRITE SOMETHING
#<< "some text"
false
some text
(y/N) : N
#<< "some text"
SOME QUESTION false
WRITE SOMETHING some text
我知道问题是函数内的回声是变量数据的一部分,但我希望打印出来。
我该怎么做?或者哪种方式最好?
答案 0 :(得分:3)
STRING_RESPONSE=$(promp "WRITE SOMETHING")
因此promp "WRITE SOMETHING"
命令的标准输出附加到变量赋值的上下文。
但是,标准错误仍附在终端上。如果将echo
的输出重定向到文件描述符2
,则只有在调用echo
时才会向用户显示输出,例如:
function promp() {
echo >&2 "$*"
read response
echo "$response"
}
另一种方法是使用-p
选项:read -p "Your prompt: "
prints the prompt string to the standard error。
答案 1 :(得分:1)
全局变量在shell脚本中比其他语言更常用;如果您的代码变得太复杂而无法轻松管理全局变量,那么可能是时候切换到另一种语言了。
# This is probably too trivial to even define as a function.
promp() {
read -p "$1" "$2"
}
confirm() {
printf '%s\n' "$1" >&2
read -rp $'(y/N) : ' -ei N key
case "$key" in
[yY][eE][sS]|[yY])
key=true
;;
*)
key=false
;;
esac
printf -v "$2" "$key"
}
# No expensive command substitutions needed;
# read and printf -v will both populate a global variable
# named by an argument.
confirm "SOME QUESTION" IS_RESPONSE
promp "WRITE SOMETHING" STRING_RESPONSE
echo "$IS_RESPONSE"
echo "$STRING_RESPONSE"
答案 2 :(得分:0)
使用read
命令中的提示代替echo
:
#!/bin/bash
function promp() {
read -p "$*"$'\n' response
echo $response
}
function confirm() {
read -rp "$*"$'\n'"(y/N) : " -ei $'N' key
case "$key" in
[yY][eE][sS]|[yY])
echo true
;;
*)
echo false
;;
esac
}
IS_RESPONSE=$(confirm "SOME QUESTION")
STRING_RESPONSE=$(promp "WRITE SOMETHING")
echo $IS_RESPONSE
echo $STRING_RESPONSE
结果:
$ ./test.sh
SOME QUESTION
(y/N) : N
WRITE SOMETHING
something
false
something
答案 3 :(得分:0)
使用@ 123,@ruslan和@chepner的答案我做了这个:
function prompt() {
printf '%s\n' "$1" > /dev/tty
read "$2"
echo $response
}
function confirm() {
local key
printf '%s\n' "$1" > /dev/tty
read -rp $'(y/N) : ' -ei $'N' key;
case "$key" in
[yY][eE][sS]|[yY]|[sS][iIíÍ]|[sS])
key=true
;;
*)
key=false
;;
esac
if [[ "$2" ]]; then
printf -v "$2" "$key"
else
echo "$key"
fi
}
$(confirm "SOME QUESTION") && echo "it works"
confirm "SOME OTHER QUESTION" IS_RESPONSE
prompt "WRITE SOMETHING" STRING_RESPONSE
echo $IS_RESPONSE
echo $STRING_RESPONSE