如何使用另一个命令python来终止子进程

时间:2016-07-26 12:44:50

标签: python server raspberry-pi subprocess kill

我在Python服务器脚本中运行两个子进程。子流程的目的是从我的Raspberry Pi中流式传输视频。

我的问题是当另一个命令发送到服务器时如何终止子进程。我目前正在使用Popen()来启动子进程。

这是我的服务器收到命令“startStream”时的代码。我使用Twisted库作为服务器协议。

class Echo(Protocol):
   def connectionMade(self):
        #self.transport.write("""connected""")
        self.factory.clients.append(self)
        print "clients are ", self.factory.clients

    def connectionLost(self, reason):
        self.factory.clients.remove(self)

    def dataReceived(self, data):
        print "data is ", data

        if data == "startStream":
            p = subprocess.Popen("raspistill --nopreview -w 640 -h 480 -q 5 -o /tmp/stream/pic.jpg -tl 100 -t 9999999 -th 0:0:0 &", shell=True)
            pn = subprocess.Popen("LD_LIBRARY_PATH=/usr/local/lib mjpg_streamer -i %s -o %s &" % (x,y), shell=True)

我想要的是这样的。

if data == "startStream":
        p = subprocess.Popen("raspistill --nopreview -w 640 -h 480 -q 5 -o /tmp/stream/pic.jpg -tl 100 -t 9999999 -th 0:0:0 &", shell=True)
        pn = subprocess.Popen("LD_LIBRARY_PATH=/usr/local/lib mjpg_streamer -i %s -o %s &" % (x,y), shell=True)
elif data == "stopStream":
        os.kill(p.pid)
        os.kill(pn.pid)

非常感谢!

1 个答案:

答案 0 :(得分:1)

你在这里缺少一些上下文,但基本上服务器会做类似的事情:

while True:
    data = wait_for_request()
    if data == 'startStream':
        p = subprocess.Popen("raspistill --nopreview -w 640 -h 480 -q 5 -o /tmp/stream/pic.jpg -tl 100 -t 9999999 -th 0:0:0 &", shell=True)
        pn = subprocess.Popen("LD_LIBRARY_PATH=/usr/local/lib mjpg_streamer -i %s -o %s &" % (x,y), shell=True)
    elif data == 'stopStream':
        p.terminate()
        pn.terminate()

关键部分是名称ppn存在于同一范围内,因此可以在不使用任何类型的全局状态的情况下访问它们。如果您的代码结构不同,则需要对其进行概述。

由于data_received在每次调用时都有自己的作用域,因此需要以不同的方式传递对Popen对象的引用。 幸运的是,您可以在类实例中保留引用。

def dataReceived(self, data):
    if data=='startStream':
        self.p = subprocess.Popen()  # ...
        self.pn = subprocess.Popen()  # ...
    elif data=='stopStream':
        self.p.terminate()
        self.pn.terminate()

Popen.terminate可以从Python 2.6获得,应该可以正常工作 - 我不确定问题的评论是什么问题。