使用 Paramiko 时的环境变量差异

Uri*_*ren 7 python ssh environment-variables paramiko

我通过终端(在 Mac 上)连接到 SSH 并运行 Paramiko Python 脚本,由于某种原因,这两个会话的行为似乎不同。PATH在这些情况下,环境变量是不同的。

这是我运行的代码:

import paramiko
ssh = paramiko.SSHClient()
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
ssh.connect('host', username='myuser',password='mypass')
stdin, stdout, stderr =ssh.exec_command('echo $PATH')
print (stdout.readlines())
Run Code Online (Sandbox Code Playgroud)

知道为什么环境变量不同吗?

我该如何解决?

Mar*_*ryl 6

SSHClient.exec_command默认情况下不分配会话的伪终端。因此(可能)获取了一组不同的启动脚本(特别是对于非交互式会话,.bash_profile未获取)。和/或脚本中的不同分支基于TERM环境变量的不存在/存在而被采用。


要使用 模拟默认的 Paramiko 行为ssh,请使用-T开关:

ssh -T myuser@host
Run Code Online (Sandbox Code Playgroud)

看那ssh个人

-T 禁用伪 tty 分配。


相反,要ssh使用 Paramiko模拟默认行为,请将 的get_pty参数设置exec_commandTrue

def exec_command(self, command, bufsize=-1, timeout=None, get_pty=False):
Run Code Online (Sandbox Code Playgroud)

尽管不是通过在 Paramiko 中分配伪终端来解决这个问题,您应该更好地修复您的启动脚本以将PATH所有会话设置为相同。

为此,请参阅使用 Python Paramiko exec_command 执行时某些 Unix 命令失败并显示“<command> not found”


Uri*_*ren 5

使用Channel对象而不是SSHClient对象解决了我的问题。

chan=ssh.invoke_shell()
chan.send('echo $PATH\n')
print (chan.recv(1024))
Run Code Online (Sandbox Code Playgroud)

有关更多详细信息,请参阅文档

  • 虽然这确实有帮助,但答案无法解释原因。这与“Channel”与“SSHClient”无关。`SSHClient` 在内部使用 `Channel`。不同之处在于您的原始代码使用“exec”通道,默认情况下不分配伪终端。虽然您的新代码使用“shell”通道,但它默认分配一个伪终端。使用 shell 执行命令并不是一个好习惯。再说一遍,将您的帐户配置为对交互式和非交互式终端使用不同的“PATH”通常是一种不好的做法。 (3认同)