2011-12-07 51 views
2

我需要在ssh登录到服务器,执行“su username”(无密码)以执行某些命令(没有用ssh直接登录)。在paramiko ssh连接上执行su用户(无密码)

从终端会是这样的:

[email protected]:~# su foo 
[email protected]:/root$ cd 
[email protected]:~$ ls 

我已经试过的paramiko(蟒蛇)要做到这一点:

import paramiko 
ssh = paramiko.SSHClient() 

ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy()) 

ssh.connect('host', username='root', password='mypassword', key_filename='<filename>') 

stdin, stdout, stderr = ssh.exec_command('su foo') 
print stdout.readlines() 
stdin, stdout, stderr = ssh.exec_command('cd') 
print stdout.readlines() 
stdin, stdout, stderr = ssh.exec_command('pwd') 
print stdout.readlines() 
ssh.close() 

但剧本还没有结束。

日志是这些:

... 
DEB [20111207-16:22:25.538] thr=1 paramiko.transport: userauth is OK 
INF [20111207-16:22:25.921] thr=1 paramiko.transport: Authentication (publickey) successful! 
DEB [20111207-16:22:25.923] thr=2 paramiko.transport: [chan 1] Max packet in: 34816 bytes 
DEB [20111207-16:22:26.088] thr=1 paramiko.transport: [chan 1] Max packet out: 32768 bytes 
INF [20111207-16:22:26.088] thr=1 paramiko.transport: Secsh channel 1 opened. 
DEB [20111207-16:22:26.151] thr=1 paramiko.transport: [chan 1] Sesch channel 1 request ok 

如果我只有这个尝试:

stdin, stdout, stderr = ssh.exec_command('su foo') 
#without print 
stdin, stdout, stderr = ssh.exec_command('pwd') 
print stdout.readlines() 

它执行PWD为根,而不是FOO。

怎么了?

回答

6

每个exec_command()调用发生在一个新的shell中,所以没有状态从以前的命令中继承。如果命令依靠先前的命令执行,则必须以单个语句或脚本形式发送它们。如果你想要一个交互式shell,有invoke_shell命令,但是你需要解析shell输出来模拟交互式使用(这里可以使用pexpect库)。

您可以使用sudo命令或su -c执行该命令。但是,我会建议配置所需用户的安全登录,并以该用户的身份直接连接。

+0

thx。我的目标是打电话给su用户,然后cd(去他的家),然后svn在那个目录。有办法连接这个,或者在paramiko中维护状态吗? – apelliciari

+1

'su foo -c“svn up/home/foo”'是一种可能性。首先在命令行中进行编写,因为这与paramiko无关。这并不是说你无法在paramiko中“维护状态”,而是你正在执行两个独立的shell。 – JimB