将密码发送到 Python 中的 sftp 子进程

Send password to sftp subprocess in Python

import subprocess

password= "xyz"

p = subprocess.Popen(["sudo", "-S", "whoami"], stdin=subprocess.PIPE, stdout=subprocess.PIPE)

print (p.communicate((password+"\n").encode())) 


ps = subprocess.Popen(["sftp", "user@sftphost"], stdin=subprocess.PIPE, stdout=subprocess.PIPE)

print (ps.communicate((password+"\n").encode())) # without print as well I get prompted for password

通过subprocess正确获取密码,第一个命令(sudo -S whoami)成功。但是,sftp 命令不接受密码——我仍然收到输入密码的提示。

我和Use subprocess to send a password有同样的问题。但是,我不想使用像 Pexpect 或 expect 这样的解决方案。我已经尝试了其余的解决方案。

想知道为什么 sftp 会失败,还有其他方法吗?

sftp 不从标准输入读取密码,而是打开 /dev/tty。这就是为什么通过通信发送密码不起作用的原因。

相反,您可以使用公钥身份验证并为您的 sftp 命令使用批处理文件 (sftp -b)。作为替代方案,您还可以使用 pexpect (https://pexpect.readthedocs.io/en/stable/).

与 sftp 交互

OpenSSH sftp 总是从终端读取密码(它没有 sudo -S 开关的等价物)。

似乎没有一种现成的方法可以用 subprocess.Popen 模拟终端,请参阅: How to call an ncurses based application using subprocess module in PyCharm IDE?


您可以使用所有常用于通过 OpenSSH sftp 自动进行密码验证的 hack,例如 sshpass 或 Expect:
How to run the sftp command with a password from Bash script?

或者使用public密钥认证。


虽然更好的是使用原生 Python SFTP 模块,例如 Paramiko or pysftp

有了它们,你就不会再有这些问题了。