我正在尝试编写一个调用 python 程序的脚本,暂停直到程序输出某条消息(而不是程序结束时),然后继续。
如果我有像这样的 example.py,它会无限期地运行:
doSomething() print('I did something') doSomethingElseForever()
我想要一个类似这样的脚本:
echo "Running python program" python3 example.py & waitForOutput("I did something") echo "Python program did something, it's still running in the background" doSomeMoreScriptStuff
理想情况下,我只需运行脚本,它就会启动 example.py,暂停直到 example.py 输出“我做了一些事情”,然后继续启动更多程序或其他任何程序,而不会停止 example.py(因此是 &)。
顺便说一下,我在 Ubuntu 中工作。
编辑:我认为目前在我的特定应用程序中,我可以更改我的python脚本以创建文件而不是print(),但为了学习(因为这似乎是一种复杂的做事方式),让我们假设我无法编辑python文件。所以我所要做的就是print()语句的已知输出。
您可以使用 来执行此操作pexpect。我启动一个线程,该线程调用pexpect.spawn()来运行您的子脚本。它等待您想要的输出,然后设置一个事件,以便主程序知道事件已发生。然后它等待子程序退出,这反过来又允许主程序退出:
pexpect
pexpect.spawn()
#!/usr/bin/env python3 import pexpect import time import threading doneIt = threading.Event() def childHandler(): """Spawns the child and manages its output""" global doneIt print('HANDLER: Spawning child') child = pexpect.spawn('./example.sh') print('HANDLER: Child spawned, waiting for it to do something') child.expect('I did something') doneIt.set() print('HANDLER: Waiting for child to finish') child.expect(pexpect.EOF) print('HANDLER: Done') if __name__ == "__main__": print('MAIN: Starting') cH = threading.Thread(target=childHandler) cH.start() # Wait for event and do other stuff, like printing while True: print('MAIN: waiting for child to do something') if doneIt.wait(1): break print('MAIN: Continuing...') # Wait till childHandler exits before exiting cH.join() print('MAIN: Exit')
我使用它example.sh作为您所调用的 Python 脚本的模型:
example.sh
#!/bin/bash LOG="run.txt" date +'Running: %H:%M:%S' > "$LOG" for ((i=8;i>0;i--)) ; do date +'Running: %H:%M:%S' >> "$LOG" sleep 1 done date +'SUCCESS: %H:%M:%S' >> "$LOG" echo "I did something" for ((i=1;i<10;i++)) ; do date +'Continuing: %H:%M:%S' >> "$LOG" sleep 1 done date +'DONE: %H:%M:%S' >> "$LOG"
以下是日志:
Running: 13:05:27 Running: 13:05:27 Running: 13:05:28 Running: 13:05:29 Running: 13:05:30 Running: 13:05:31 Running: 13:05:32 Running: 13:05:33 Running: 13:05:34 SUCCESS: 13:05:35 Continuing: 13:05:35 Continuing: 13:05:36 Continuing: 13:05:37 Continuing: 13:05:38 Continuing: 13:05:39 Continuing: 13:05:40 Continuing: 13:05:41 Continuing: 13:05:42 Continuing: 13:05:43 DONE: 13:05:44