自我更新的Python服务会自杀



TLDR:我想从git自我更新服务。Bash脚本需要停止此服务。但它扼杀了自我更新。如何从Python启动bash脚本,即使Python脚本被杀死,它也会完成

我想从作为服务运行的Python脚本到self-update服务运行self-update-bash脚本(update.sh(。问题是我需要停止服务,因为我需要从git中提取新数据。在不停止服务的情况下,我处理了损坏的数据。

这是Python脚本的一部分,它作为服务运行。该部分应处理服务的自我更新:

import subprocess
subprocess.call('sudo /home/pi/myproject/update.sh', shell=True)

这是更新.sh脚本(如果我在终端中运行它,则100%有效(:

#!/bin/bash
systemctl stop myproject.service
su - pi -c "cd /home/pi/myproject; git reset --hard; git pull;"
su - pi -c "cd /home/pi/myproject; chmod +x update.sh"
systemctl start myproject.service

执行systemctlstop-myproject.service命令时,服务将被终止,并且不会执行下一行。

是否可以在某些环境中启动update.sh,即使myproject.service被终止也会完成?

您可以通过调用来实现这一点

subprocess.call('sudo at now -f /home/pi/myproject/update.sh', shell=True)

at将生成一个新的shell进程,以便可以停止启动进程,然后从生成的进程重新启动。

最简单的选项是启动脚本,将服务作为后台进程重新启动。这将"分离"它,这样终止/重新启动服务就不会影响脚本。

这是通过对subprocess.call:使用close_fds参数来完成的

subprocess.call('sudo /home/pi/myproject/update.sh', shell=True, close_fds=True)

但是,请注意,由于这个进程现在是分离的,如果它挂起或阻塞,就不会有任何东西来整理它。您可能需要放入额外的代码,以确保它在自身正常清理之后(例如超时(。

或者,您可能希望在"main"命令之前,在服务启动时运行"update"脚本。然后,如果您只调用systemctl start/restart,它将在主服务启动之前运行git命令。

您可以通过在systemctl服务中添加ExecStartPre来做到这一点:

[Service]
ExecStartPre=sudo /home/pi/myproject/update.sh

最新更新