场景
ssh.exe来自微软编译的openSSH for Windows,也就是Win10自带的ssh命令行工具,直接调用系统自带的也可以。
现在,我要使用nodejs中child_process模块的spawn或execFile等方法运行ssh.exe,并通过stdio进程通信,实现自动输入密码登录的功能。
(备注:不用告诉我使用node-ssh之类的库,那些我知道哈)
代码如下
仅需几行代码:
const path = require('path')
const spawn = require('child_process').spawn
// 通过spawn方法运行ssh.exe
const ssh = spawn('ssh.exe', '-o StrictHostKeyChecking=no -o PasswordAuthentication=yes -P22 root@10.0.0.55'.split(' '))
// 当ssh.exe在输出流中输出内容时,判断如果内容提示输入密码,则向其输入流发送密码
ssh.stdout.on('data', data => {
process.stdout.write(data.toString()) // 这行竟然无效
if (/password:/gi.test(data)) ssh.stdin.write('my password') //这行竟然也无效
})
文件结构图:(实际上就只有index.js一个文件,其他ssh.exe等文件可无视,可直接调用系统自带的)
运行结果
失败,没有自动登录
如图:
疑问
如果是通常的exe程序,上述代码的进程通信方式是没有问题的,但是openSSH不知道是何原因,从ssh.stdout.on('data')
事件中监听不到root@10.0.0.55's password:
这行输出,且使用ssh.stdin.write()
向ssh.exe进程发送密码,也没有反应。
请问这是什么原因,有何解决方案实现这个自动登录的功能?
感谢大神解答。
别试了,这个我曾经研究过一段时间。
ssh
我怀疑是通过特殊的手法劫持了stdin
,你无法通过传统的管道方式喂数据给stdin来实现非交互式。能起作用的目前我所知的只有expect
方案,它是完全模拟用户的交互式输入,可以交互ssh,python有个对应的包装实现Pexpect
,没查过nodejs有没有类似的类库。目前社区上普遍采用的ssh非交互式方案是
sshpass
,它可以帮你实现ssh非交互式,比自己用expect
之类的简单的多,著名的ansible, salt-stack之类的工具都是依赖sshpass实现ssh非交互式控制服务器。如果你想实现ssh非交互式,建议你考虑这个方案。RHEL官方的系统管理员文档也推荐这个工具实现ssh非交互式 https://www.redhat.com/sysadm...