近期需要实现服务器上跑过个服务,然后供用户使用,由于内存及用户量的问题,总是隔段时间会导致某个服务被kill。 人力重启实在是太熬人,所以写了段python来监听。如果发现哪个崩了,就对其进行重启。
先上一段错误示例
import subprocess
import time
# 定义需要检测的端口号
PORTS = [6007, 6008]
# 定义每个端口对应的启动脚本文件名
START_SCRIPTS = {
6007: "6007start.py",
6008: "6008start.py"
}
while True:
for port in PORTS:
# 检测端口是否正常
result = subprocess.run(["lsof", "-i", f":{port}"], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
if result.returncode != 0:
# 端口崩溃,执行对应的启动脚本
print(f"Port {port} crashed, restarting...")
subprocess.run(["python", START_SCRIPTS[port]])
else:
# 端口正常
print(f"Port {port} is running")
# 休眠5秒后继续监测
time.sleep(5)
这个是能检测并重启了,但是蛋疼的是,检测到并重启后,就把监听的服务挤没了。。 没法继续监听,属于一次性的,这肯定不是我们想要的。
于是优化一下:
import subprocess
import time
import multiprocessing
# 定义需要检测的端口号
PORTS = [6007, 6008]
# 定义每个端口对应的启动脚本文件名
START_SCRIPTS = {
6007: "6007start.py",
6008: "6008start.py"
}
def start_process(port):
subprocess.run(["python", START_SCRIPTS[port]])
if __name__ == "__main__":
while True:
for port in PORTS:
# 检测端口是否正常
result = subprocess.run(["lsof", "-i", f":{port}"], stdout=subprocess.PIPE, stderr=subprocess.PIPE)
if result.returncode != 0:
# 端口崩溃,启动子进程执行对应的启动脚本
print(f"Port {port} crashed, restarting...")
p = multiprocessing.Process(target=start_process, args=(port,))
p.start()
# 等待5秒,确保子进程启动服务成功
time.sleep(5)
else:
# 端口正常
print(f"Port {port} is running")
# 休眠5秒后继续监测
time.sleep(5)
保证监听运行在主任务,其余是开启的子进程。 注意while里面的sleep了5s,是为了等待子进程启动完毕(否则子线程启动的过程中,监听还会继续,会导致启动一大堆服务!),这个写法还可以优化,欢迎大家帮忙