如何使用Python中的子进程模块启动和停止Linux程序?

时间:2023-01-26 20:45:33

I’m writing a web app that uses Selenium to screen-scrape another website. This screen-scraping only happens once a day, so I’d rather not leave Selenium and Xvfb running all the time.

我正在编写一个使用Selenium来筛选另一个网站的网络应用程序。这种屏幕抓取每天只发生一次,所以我宁愿不让Selenium和Xvfb一直运行。

I’m trying to figure out how to start Xvfb and Selenium from Python, and then stop them once the screen-scraping’s done.

我试图找出如何从Python启动Xvfb和Selenium,然后在屏幕抓取完成后停止它们。

If I was doing it manually, I’d start them at the command line, and hit CTRL C to stop them. I’m trying to do the same thing from Python.

如果我是手动完成的,我会在命令行启动它们,然后点击CTRL C来阻止它们。我试图用Python做同样的事情。

I seem to be able to successfully start Xvfb like this:

我似乎能够像这样成功启动Xvfb:

xvfb = Popen('Xvfb :99 -nolisten tcp', shell=True)

But when I’ve tried to terminate it:

但是当我试图终止它时:

xvfb.terminate()

and then tried to start it again (by repeating my initial command), it tells me it’s already running.

然后尝试再次启动它(通过重复我的初始命令),它告诉我它已经在运行。

2 个解决方案

#1


7  

I don't know why you want to run Xvfb as root. Your usual X server only needs to run as root (on many but not all unices) only so that it can access the video hardware; that's not an issue for Xvfb by definition.

我不知道你为什么要以root身份运行Xvfb。您通常的X服务器只需要以root身份运行(在许多但不是所有unices上),以便它可以访问视频硬件;根据定义,这不是Xvfb的问题。

tempdir = tempfile.mkdtemp()
xvfb = subprocess.Popen(['Xvfb', ':99', '-nolisten', 'tcp', '-fbdir', tempdir])

When you terminate the X server, you may see a zombie process. This is in fact not a process (it's dead), just an entry in the process table that goes away when the parent process either reads the child's exit status or itself dies. Zombies are mostly harmless, but it's cleaner to call wait to read the exit status.

终止X服务器时,您可能会看到僵尸进程。这实际上不是一个进程(它已经死了),只是当进程表中的一个条目在父进程读取子进程或其自身死亡时消失。僵尸大多是无害的,但是等待阅读退出状态更为清晰。

xvfb.terminate()
# At this point, `ps -C Xvfb` may still show a running process
# (because signal delivery is asynchronous) or a zombie.
xvfb.wait()
# Now the child is dead and reaped (assuming it didn't catch SIGTERM).

#2


1  

I assume you can parametrize your system to allow any user to launch Xvfb as explained here solving all your problems

我假设您可以参数化您的系统,以允许任何用户启动Xvfb,如此处所解释的,解决您的所有问题

EDIT the correct command line is

编辑正确的命令行是

sudo chmod u+s `which Xvfb` 

#1


7  

I don't know why you want to run Xvfb as root. Your usual X server only needs to run as root (on many but not all unices) only so that it can access the video hardware; that's not an issue for Xvfb by definition.

我不知道你为什么要以root身份运行Xvfb。您通常的X服务器只需要以root身份运行(在许多但不是所有unices上),以便它可以访问视频硬件;根据定义,这不是Xvfb的问题。

tempdir = tempfile.mkdtemp()
xvfb = subprocess.Popen(['Xvfb', ':99', '-nolisten', 'tcp', '-fbdir', tempdir])

When you terminate the X server, you may see a zombie process. This is in fact not a process (it's dead), just an entry in the process table that goes away when the parent process either reads the child's exit status or itself dies. Zombies are mostly harmless, but it's cleaner to call wait to read the exit status.

终止X服务器时,您可能会看到僵尸进程。这实际上不是一个进程(它已经死了),只是当进程表中的一个条目在父进程读取子进程或其自身死亡时消失。僵尸大多是无害的,但是等待阅读退出状态更为清晰。

xvfb.terminate()
# At this point, `ps -C Xvfb` may still show a running process
# (because signal delivery is asynchronous) or a zombie.
xvfb.wait()
# Now the child is dead and reaped (assuming it didn't catch SIGTERM).

#2


1  

I assume you can parametrize your system to allow any user to launch Xvfb as explained here solving all your problems

我假设您可以参数化您的系统,以允许任何用户启动Xvfb,如此处所解释的,解决您的所有问题

EDIT the correct command line is

编辑正确的命令行是

sudo chmod u+s `which Xvfb`