使用p.expect获取值

0 投票
4 回答
1978 浏览
提问于 2025-04-15 18:09

我有一个程序,可以登录到服务器并发送命令。最后的结果会在脚本结束时打印出来。下面的代码展示了我用来通过ssh发送命令的脚本。

import pexpect

ssh_newkey = 'Are you sure you want to continue connecting'
# my ssh command line
p=pexpect.spawn('ssh user@00.00.00.00')

i=p.expect([ssh_newkey,'password:',pexpect.EOF])
if i==0:
    print "I say yes"
    p.sendline('yes')
    i=p.expect([ssh_newkey,'password:',pexpect.EOF])
if i==1:
    print "I have entered the password. I will now flip camera through ",
    p.sendline("user")
    i=p.expect('user@hol-NA:')
    p.sendline("cd /opt/ad/bin")
    i=p.expect('user@hol-NA:')
    p.sendline("./ptzflip")
    i=p.expect('user@hol-NA:')
elif i==2:
    print "I either got key or connection timeout"
    pass
results = p.before # print out the result

print results

这个程序打印出的结果是:

Value = 1800
Min = 0
Max = 3600
Step = 1

我想要把打印出来的值抓取到。

针对下面的问题,我想把比如说'Value'抓取成一个变量,把'1800'抓取成它的值。我尝试把它们分开放到一个字典里,如下所示,但出现了错误。当我输入:

results_dict = {} 
for line in results: 
    name, val = line.split(' = ') 
    results_dict[name] = val

我得到了一个错误:

Traceback (most recent call last):
  File "ptest.py", line 30, in <module>
    name, val = line.split(' = ') 
ValueError: need more than 1 value to unpack

当我在Python中检查这段代码时,它把这些值存储成了字符串。它存储成:

'/opt/ad/bin$ ./ptzflip\r\nValue = 1800\r\nMin = 0\r\nMax = 3600\r\nStep = 1\r\n'

有没有人能帮我解决这个问题。谢谢

4 个回答

1

你是说要把它保存到一个文件里吗?那你可以试试这个

open("output.txt","w").write(results)

或者当你在命令行运行这个脚本的时候:

$ python script.py > output.txt

否则,你需要说明一下你说的“捕获”是什么意思

1

每次调用 p.expect 后,你可以获取到在匹配部分之前,子进程输出的所有内容(可以是多行),以及匹配的内容本身。这些内容分别被称为 beforeafter 属性,这就是你所说的“捕获”!

换句话说,正如文档中所说:

每次调用 expect() 后,beforeafter 属性会被设置为子应用程序打印的文本。before 属性会包含所有在预期字符串模式之前的文本,而 after 字符串则会包含与预期模式匹配的文本。match 属性会被设置为正则表达式的 MatchObject

文档中这部分后面的示例代码可以帮助你理解这一点——在与交互式 ftp 客户端建立 FTP 会话后,

   child.sendline('ls /pub/OpenBSD/')
   child.expect('ftp> ')
   print child.before   # Print the result of the ls command.
1

你是在问 Value = 1800 这些内容是不是 results 的内容吗?你想要“捕捉”这些内容吗?

你是想解析这些结果吗?还是想把它们当作 Python 代码来执行?

如果是前者,你可以试试下面这种方法(这个方法没有经过测试,代码也不太干净,而且没有仔细处理空格):

results_dict = {}
for line in results.splitlines():
    try:
        name, val = line.split(' = ')
    except ValueError:
        continue
    results_dict[name] = val

这样你就能得到一个 Python 字典,可以用来处理数据。如果你知道这些值总是数字的话,可以用 int(val)float(val) 来转换它们……(这里的 try...except 是用来忽略格式不正确的行;还有其他更稳妥的方法,比如 if " = " in line

如果你真的想得到一个名为 Value 的变量,并且它的值是 1800,你可以使用 eval(results) [或者更安全的替代方法],不过这需要先去掉格式不正确的行。

撰写回答