我可以使用 heredoc 在 bash 中输入密码吗?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3796345/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-17 22:42:09  来源:igfitidea点击:

Can I use a heredoc to enter a password in bash?

bashsshexpectheredoc

提问by B Johnson

I know about RSA authentication, but for my purposes I want to use a heredoc to specify the password. I want something like the following, but I can't get it to work. Is this even possible?

我了解 RSA 身份验证,但出于我的目的,我想使用 heredoc 来指定密码。我想要类似以下的东西,但我无法让它工作。这甚至可能吗?

#!/bin/bash
echo -n "Enter Password: "
read -s password
ssh myhost << EOL
$password
echo "I'm logged onto myhost"
EOL
echo done

This is what I get when I try it:

这是我尝试时得到的:

$ ./testssh 
Enter Password: 
Pseudo-terminal will not be allocated because stdin is not a terminal.
user@myhost's password: 
Warning: No xauth data; using fake authentication data for X11 forwarding.
Warning: no access to tty (Bad file descriptor).
Thus no job control in this shell.
mypassword: Command not found.
I'm logged onto myhost
done

EDIT:

编辑:

Based on bmargulies' answer, I reworked my script and came up with the following:

根据 bmargulies 的回答,我重新编写了脚本并提出了以下内容:

#!/bin/bash
echo -n "Enter the Host: "
read HOST
echo -n "Enter Username: "
read USER
echo -n "Enter Password: "
read -s PASS
VAR=$(expect -c "
spawn ssh $USER@$HOST
expect \"password:\"
send \"$PASS\r\"
expect \">\"
send \"ls\r\"
send \"echo 'I\'m on $HOST'\r\"
expect -re \"stuff\"
send \"logout\"
")
echo -e "\n\n\n========"
echo VAR = "$VAR"
echo done

回答by bmargulies

Programs that read passwords often specifically open /dev/tty to defeat redirection. In which case, the tool you need is 'expect', which will run one behind a pseudo-tty.

读取密码的程序通常专门打开 /dev/tty 以阻止重定向。在这种情况下,您需要的工具是“expect”,它将在伪 tty 后面运行。

回答by EJ Campbell

If you mix in w/ perl, you can do something "clean" (from a non needing to quote view) like this:

如果您混合使用 perl,您可以像这样做一些“干净”的事情(从不需要引用的视图中):

#!/bin/bash
cmd="ssh myhost << EOL"
echo -n "Enter Password: "
read -s password
# answer password prompt
#   note we use ctl-A as our quote delimeter around the password so we run
#   no risk of it escaping quotes
script='
use Expect;
use ysecure;
my $exp = new Expect;
$exp->raw_pty(1);
$exp->spawn(q|<CMD>|);
$exp->expect(30,">");
$exp->send(q^A<PASSWORD>^A . "\n");
$exp->soft_close();
$exp->exitstatus() && die;
'

script=${script//<CMD>/$cmd}
script=${script//<PASSWORD>/$password}

perl -e "$script"