Скрипт Python, который отслеживает статус служб systemctl и отправляет электронную почту через sendmail, если он возвращает false

Немного нуби здесь.

Я пытаюсь написать скрипт python, который по существу будет смотреть на подстатус службы с помощью утилиты systemctl, а затем отправлять электронное письмо с помощью sendmail, если обнаружит, что подстатус НЕ «работает».

В этом конкретном случае недостаточно просто показать, активна ли служба, но и работает ли она.

У меня есть скрипт, с которым я работал, но изначально он искал статусы URL, и я изменил его, чтобы смотреть на отдельные сервисы. Я хочу отслеживать 6 различных служб, но отправляю электронное письмо, если какой-либо из них возвращает что-либо, кроме «работает».

Ниже приведен сценарий, который у меня есть до сих пор:

#!/usr/bin/python


import time
import os
from email.mime.text import MIMEText
from subprocess import Popen, PIPE

#The url being monitored.
service1 = "tomcat"
#service2 = "hostcontext"
#service3 = "ecs-ec"
#service4 = "ecs-ep"
#service5 = "ariel_proxy_server"
#service6 = "ecs-ec-ingress"


#The contents of the email
msg = MIMEText(service1 + " is not responding.  Please investigate.")
msg["From"] = "sending address"
msg["To"] = "recipient address"
msg["Subject"] = service1 + "is not responding"

#This loops while the script is running.
# It gets the status returned from the urllib call, if it's not 200 it will email the email contents above.
while True:
    status = os.system('systemctl show tomcat -p SubState | sed "s/SubState=//g"')

    if status == 'running':
        #This is what sends the email.  If you don't have sendmail then update this.
        p = Popen(["/usr/sbin/sendmail", "-t", "-oi"], stdin=PIPE)
        p.communicate(msg.as_string())
    #The number of seconds the loop will pause for before checking again.  I set it to 60.
    time.sleep(60)

person Mike    schedule 28.02.2020    source источник
comment
Привет @Mike, добро пожаловать в StackOveflow! Каков твой вопрос?   -  person Pedro Lobito    schedule 28.02.2020


Ответы (1)


Я бы сделал что-то вроде:

import time, traceback
from subprocess import getoutput
services = ["mariadb", "apache"]

while 1:
    for service in services:
        try:
            status = getoutput(f"systemctl show {service} -p SubState").split("=")[1].lower()
            if status != 'running':
                print(f"Service {service} is down, send email...")
        except:
            pass
            print(traceback.print_exc())
            # log the error if needed
    time.sleep(60)
person Pedro Lobito    schedule 28.02.2020
comment
Спасибо @Педро! Я попробовал это, но у меня были некоторые проблемы с выводом. Похоже, он выводит сообщение об ошибке независимо от того, что я поставил. Кроме того, часть {service}, которую нужно подобрать для переменной, не подхватывается, она буквально просто печатает сообщение, как вы видите, Service {service} не работает, отправьте электронное письмо... - person Mike; 28.02.2020