5

Stackoverflow 的新手,所以首先,你好。

我正在为我的学校做一个小项目,该项目应该是开源 Unison 程序的自定义 gui(用 python 编写,对我来说是一个教育挑战,因为我从未使用过 python)。我们正在尝试让学生和教职员工在家里和学校同步文件夹,方法是通过尽可能少的输入启动这个程序(如果你愿意的话,请防止白痴)。该界面应该只是他们是学校用户名和密码,而 gui 包装器应该只是将用户名和密码发送到 Unison 并同步它们。

问题是 Unison 依次启动 SSh 并提示输入密码,但 python subprocess.communicate(input) 方法不会让 ssh 获取密码。我意识到 ssh 只会接受来自终端的输入,我不知道如何欺骗它。我读过一些关于使用伪终端的东西,但我仍然很难过。RSA 密钥将是理想的解决方案,但生成它们然后将它们放置在远程服务器上仍然需要我至少使用密码登录一次,这需要解决上述问题,或者终端不是白痴证明。

def startSync(self):
    '''
    '''
    userName = self.userNameIn.get()
    userPass = self.userPassIn.get()
    localDir = "/Users/localuser/syncFolder/"
    remoteDir = " ssh://schoolServer/remotesyncFolder" #for testing purposes, I set this to my own home machine which logs into my own account if I don't provide me@myserver.net
    unisonExecRemotePath = " -servercmd /Users/RemoteMe/unison" #unison is the unix executable responsible for launching unison on the remote system
    silenceCmdPrompts = " -silent" #keeps unison from displaying directory differences and asking if its okay to sync
    executionString = "./unison" + localDir + remoteDir + unisonExecRemotePath + silenceCmdPrompts

   mainProcess = subprocess.Popen(executionString,shell = True, stdin = subprocess.PIPE)
   mainProcess.communicate(userPass)

如果我将其粘贴到终端中,执行字符串可以正常工作。如果您愿意,任何一般的 python 提示也将不胜感激。

谢谢!

Unison 用户手册:http ://www.cis.upenn.edu/~bcpierce/unison/download/releases/stable/unison-manual.html

编辑:我还应该注意,虽然我目前正在 OSX 和 Linux 下进行开发,但我最终必须使这个 Windows 兼容,因为我学校的大多数学生都将 Windows 作为他们的主要(或唯一)机器运行。

4

2 回答 2

3

查看pexpect

import pexpect

child = pexpect.spawn('ssh myname@host.example.com')
child.expect('Password:')
child.sendline(mypassword)
child.interact()
于 2012-05-11T16:42:28.930 回答
2

如果您想向您发送密码,ssh您需要打开伪终端 (a pty) 并使用它与它交谈,而不仅仅是使用stdin/ stdout。看看pexpect模块,它就是专门为此而设计的。

另一种解决方案将涉及某种用于分发公钥的带外机制:例如,设置一个简单的 Web 应用程序,人们可以在其中粘贴公钥并让它authorized_keys代表用户管理文件。

于 2012-05-11T16:40:47.393 回答