Python 定时检测域名过期,并发送邮件通知

一、背景概要:

公司里有很多https域名,证书都是使用的ssl免费证书,需要手动运维。 经常会遇到证书过期导致项目无法访问的问题,所以写了一个脚本自动检测已有域名里,哪些域名要过期了,发送邮件通知运维。

二、需求描述:
  1. 每日检查特定域名的SSL证书到期情况
  2. 到期不足7天的域名收集
  3. 邮件发送通知

三、运行要求:

  1. 需要有一个smtp邮箱服务,用于邮件发送,这个主流的邮件公司基本都支持。如 QQ SMTP怎么配置?怎么使用
  2. 收集目前正在使用的https域名
  3. 修改配置,搭建Python运行环境,在服务器里运行
四、脚本代码:

脚本名称:ssl_validate.py

import smtplib
import socket
import ssl
import time
from datetime import datetime
from email.mime.text import MIMEText

import schedule

# 发件人
ENTRY_EMAIL_SENDER = 'xx@qq.com'
# 授权码
ENTRY_EMAIL_PWD = 'xxx'
# 设置发件服务器地址
ENTRY_EMAIL_HOST = 'smtp.exmail.qq.com'
# 设置发件服务器端口
ENTRY_EMAIL_PORT = 465


def send_email(subject, receiver, body):
    """
    :param receiver: 设置邮件接收人,可以是QQ邮箱
    :param body:正文
    :param subject 标题
    :return:
    """
    msg = MIMEText(body, _charset="utf-8")
    # 设置邮件标题
    msg['subject'] = u'系统通知' if not subject else subject
    # 设置发送人
    msg['from'] = ENTRY_EMAIL_SENDER
    # 设置接收人
    msg['to'] = receiver
    try:
        # 注意!如果是使用SSL端口,这里就要改为SMTP_SSL
        s = smtplib.SMTP_SSL(ENTRY_EMAIL_HOST, ENTRY_EMAIL_PORT)
        # 登陆邮箱
        s.login(ENTRY_EMAIL_SENDER, ENTRY_EMAIL_PWD)
        # 发送邮件!
        s.sendmail(ENTRY_EMAIL_SENDER, receiver, msg.as_string())
        return True, ''
    except smtplib.SMTPException as e:
        print('发生邮件失败,具体原因是 %s', e)
        return False, str(e)


def check_ssl_expiry(hostname, port=443, buffer_days=7):
    """
    检查给定主机名的SSL证书到期情况。

    :param hostname: 要检查的主机名或IP地址
    :param port: 端口号,默认为443(HTTPS)
    :param buffer_days: 到期前开始通知的天数
    :return: 表示SSL证书状态的消息
    """
    try:
        context = ssl.create_default_context()
        with socket.create_connection((hostname, port)) as sock:
            with context.wrap_socket(sock, server_hostname=hostname) as ssock:
                cert = ssock.getpeercert()

        # 提取过期日期并与当前日期比较
        expiry_date = datetime.strptime(cert['notAfter'], '%b %d %H:%M:%S %Y %Z')
        current_date = datetime.now()
        days_remaining = (expiry_date - current_date).days

        # 检查证书是否接近过期
        if days_remaining < 0:
            return hostname, f"SSL证书已经过期!"
        elif days_remaining <= buffer_days:
            return hostname, f"SSL证书将在 {days_remaining} 天后过期。"
        else:
            return None, None
        #     return hostname, f"SSL证书还有 {days_remaining} 天过期。"
    except ssl.CertificateError as e:
        return hostname, f"SSL证书过期 "
    except ssl.SSLError as e:
        return hostname, f"SSL证书不存在 "
    except Exception as e:
        print(e)
        return hostname, f"SSL获取发生错误 "


def daily_check():
    """
    每日检查特定域名的SSL证书到期情况。
    """
    domain_dict = {'xx.com': ['xxx.xxx.com' ]}
    hostnames = []
    for key in domain_dict.keys():
        val_list = domain_dict.get(key)
        for val in val_list:
            hostnames.append(val)
    # 替换为要检查的域名列表
    info = "以下域名SSL证书即将过期,请及时更新:\n"
    need_send = False
    for hostname in hostnames:
        result = check_ssl_expiry(hostname)
        if result and result[0]:
            need_send = True
            info += (result[0] + "," + result[1] + "\n")
    print(info)
    notification_email_list = ["xx@qq.com"]  # 收件人邮箱
    if need_send:
        for notification_email in notification_email_list:
            send_email("SSL 证书到期通知", notification_email, info.encode("utf-8"))


# 设置定时任务,每天执行一次
schedule.every().day.at("10:00").do(daily_check)  # 每天10:00执行

# 运行定时任务
while True:
    schedule.run_pending()
    time.sleep(60)  # 每60秒检查一次任务


五、运行效果:

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值