为什么这些命令在 ProxyCommand 中不可用?

为什么这些命令在 ProxyCommand 中不可用?

我试图了解如何ProxyCommand运作

%> ssh -oProxyCommand='ls' root@ubuntu
ssh_exchange_identification: Connection closed by remote host

%> ssh -oProxyCommand='useradd' root@ubuntu
/bin/bash: line 0: exec: useradd: not found
ssh_exchange_identification: Connection closed by remote host

我也尝试了诸如 之类的内置命令env,但它也没有输出。

任何想法,为什么我不能执行任意命令?

编辑

我知道我可以执行类似的命令ssh host $command,我只是想弄清楚为什么 ProxyCommand 不能只运行任何命令,真的不知道为什么人们反对它。

答案1

ProxyCommand选项不是在远程系统上运行的任意命令,而是用于代理一些数据流。来自手册页ssh_config(强调):

代理命令

指定要使用的命令连接到服务器。命令字符串延伸到行尾,并使用用户的 shell 'exec' 指令执行以避免 shell 进程延迟。

在命令字符串中,任何出现的“%h”都将替换为要连接的主机名,“%p”将替换为端口,“%r”将替换为远程用户名。该命令基本上可以是任何内容,并且应该从其标准输入读取并写入其标准输出。 它最终应该连接在某些机器上运行的 sshd(8) 服务器,或者在某处执行 sshd -i

如果您只想在远程系统上运行命令,请在命令行末尾提供它ssh,如下所示

ssh root@ubuntu ls

答案2

ProxyCommand指定的是不是在远程主机上执行。它在本地(客户端)端运行,作为打开到远程主机的 TCP 连接(通常是端口 22)的替代连接方法。运行的可执行文件ProxyCommand预计通过stdoutstdin作为套接字自己的代理recv()和与本地 ssh 客户端进行通信send(),但从客户端的角度来看,其行为应该是逐字节替换到实际 ssh 服务器的 TCP 会话。

通常的用法ProxyCommand是通过一台服务器设置 ssh 隧道以连接到辅助服务器,否则辅助服务器将无法建立直接连接。使用带有netcat(nc) 命令的 ssh 客户端可以实现此目的,其中处理套接字端的to和to 的netcat链接。stdoutsend()stdinrecv()

当您调用ProxyCommand未建立stdoutstdin匹配 SSH 协议期望的内容以协商正确的 SSH 传输时,客户端会退出并显示错误:ssh_exchange_identification: Connection closed by remote host

如果您实际上希望在建立 ssh 会话并经过身份验证后在远程主机上执行该命令,则可以将其包含在 ssh 命令行的末尾(不带ProxyCommand),并且 ssh 客户端将在远程主机上调用该命令。远程主机,而不是交互式 shell。

尝试ssh root@ubuntu ls一下。

相关内容