![Bash 脚本:用户输入(读取)无法正常工作](https://linux22.com/image/121399/Bash%20%E8%84%9A%E6%9C%AC%EF%BC%9A%E7%94%A8%E6%88%B7%E8%BE%93%E5%85%A5%EF%BC%88%E8%AF%BB%E5%8F%96%EF%BC%89%E6%97%A0%E6%B3%95%E6%AD%A3%E5%B8%B8%E5%B7%A5%E4%BD%9C.png)
我正在编写一个 BASH 脚本,该脚本应该根据文件的名称、内容删除文件或直接关闭程序。具体来说,我在根据文件内容删除文件时遇到问题(情况 2)。我可以使用与内容匹配的任何文件填充文件。但是,当用户应该输入是否要删除文件(使用读取)时,我的代码出现故障。该变量不会要求用户输入,而是自动填充要删除的文件的位置。
#!/bin/bash
#set -x
#Programmer: Redacted
#Z: ID: Redacted
#Assignment: cleaner.sh
directory=`pwd` #sets the directory variable to pwd
string="string"
file="file"
fileFound=matched.txt
possibleFiles=''
result=''
function askDelete #asks for verification
{
#echo "$fileName was found, still want to delete it? (y/n)"
read -p "$fileName was found, still want to delete it? (y/n)" continue
echo "Continue is equal to: $continue"
}
echo "Welcome to my CLEANER script!"
echo "Enter 1: delete by filename."
echo "Enter 2: delete by a string within the file."
echo "Enter 3 or quit: exit this program."
read command
case $command in
"file")
command=1 ;;
"string")
command=2 ;;
esac
case $command in
1)
#Prompts user for which file they want to delete
echo "What file would you like to delete? "
read fileName
#find $PWD -type f -name "$fileName"
#result= -x $fileName
if [ -a "$fileName" ]
then
askDelete
if [ $continue == 'y' ] || [ $continue == 'Y' ]
then
rm $fileName
echo "File has been removed"
else
echo "File has not been removed"
fi
else
echo "No files were found"
fi
;;
#case where user entered 2
#user wants to enter a string within the files to delete
2)
touch 'matched.txt' #creates the file that will be used
echo "Enter the string that you wish to have the files containing it to be destroyed"
read pattern #user enters what they want to search for
find $PWD -type f 1>possibleFiles.txt
#echo $PWD
#grep -q "$pattern" 'foundFile.txt' 1> matched.txt
echo 'This is where it breaks'
cat possibleFiles.txt | while read fileName
do
#\echo $fileName
grep -q "$pattern" "$fileName" 1> matched.txt
if [ $? == 0 ]
then
askDelete
if [ $continue == 'y' ] || [ $continue == 'Y' ]
then
rm $fileName
else
echo "No found files have been removed"
fi
else
echo "No matches for the pattern were found"
fi
done
#
# if [ $? == 0 ]
# then
# askDelete
# if [ $continue == "Y" ] || [ $continue == "y" ]
# then
# #cat matched.txt
# for file in 'matched.txt'
# do
# echo 'bleh'
# done
# else
# echo "No found files have been removed"
# fi
# else
# echo "No matches for the pattern were found"
# fi
# fi
;;
#case where user entered 3
#user wants to exit
3)
echo "Goodbye friend"
exit
;;
*)
echo Digit 1, 2 or 3 must be entered
esac
我相信问题出在程序顶部附近的askDelete函数内部的某个地方。具体来说,是这一行: read -p "$fileName was found, still Want to delete it? (y/n)" continue
任何帮助表示赞赏
答案1
因为整个块while
...done
已从stdin
文件重定向(然后间接通过管道)possibleFiles.txt
,因此该块内的每个命令都继承相同的stdin
.因此,虽然这就是您想要的,read
但实际上并不是您想要的,因为它正在消耗所使用的askDelete
同一行输入。possibleFiles.txt
read
幸运的是,tty(您的终端)仍然可以通过/dev/tty
.只需将循环内部替换askDelete
为askDelete </dev/tty
,一切就应该按预期工作。
您仍然应该添加更多验证:例如,这个程序无法在终端之外运行(用其他文件提供预填充的 y/n 答案),因为这个简单的更正/dev/tty
将不再起作用:您必须找到方法不这样做“覆盖” stdin
。