-
-
Notifications
You must be signed in to change notification settings - Fork 6
/
Copy pathnotification.py
167 lines (147 loc) · 6.71 KB
/
notification.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
import logging # For logging notification events and errors
import requests # For sending HTTP requests (used by Gotify and Uptime Kuma)
import smtplib # For sending emails
from email.mime.text import MIMEText # For constructing email messages
from abc import ABC, abstractmethod # Abstract base classes for notification interfaces
from config import DEFAULTS # Configuration values
# Abstract base class for notification proxies
class NotificationProxy(ABC):
"""
Abstract class representing a generic notification proxy.
Classes inheriting from this must implement the send_notification method.
"""
@abstractmethod
def send_notification(self, title: str, message: str, priority: int = 5):
pass
# Gotify notification implementation
class GotifyNotification(NotificationProxy):
"""
Notification class for sending notifications to a Gotify server.
"""
def __init__(self, url: str, token: str):
self.url = url
self.token = token
def send_notification(self, title: str, message: str, priority: int = 5):
"""
Send a notification to a Gotify server.
Args:
title (str): The title of the notification.
message (str): The body of the notification.
priority (int): The priority level of the notification.
"""
payload = {'title': title, 'message': message, 'priority': priority}
headers = {'X-Gotify-Key': self.token}
try:
response = requests.post(f"{self.url}/message", json=payload, headers=headers, timeout=10)
response.raise_for_status()
logging.info(f"Gotify notification sent: {title} - {message}")
except Exception as e:
logging.error(f"Gotify notification failed: {e}")
# Email notification implementation
class EmailNotification(NotificationProxy):
"""
Notification class for sending notifications via email.
"""
def __init__(self, smtp_server: str, port: int, username: str, password: str, from_addr: str, to_addrs: list):
self.smtp_server = smtp_server
self.port = port
self.username = username
self.password = password
self.from_addr = from_addr
self.to_addrs = to_addrs
def send_notification(self, title: str, message: str, priority: int = 5):
"""
Send a notification via email.
Args:
title (str): The subject of the email.
message (str): The body of the email.
priority (int): Unused, but kept for interface consistency.
"""
msg = MIMEText(message)
msg['Subject'] = title
msg['From'] = self.from_addr
msg['To'] = ', '.join(self.to_addrs)
try:
with smtplib.SMTP(self.smtp_server, self.port, timeout=10) as server:
server.starttls() # Encrypt the connection
server.login(self.username, self.password) # Authenticate with the SMTP server
server.sendmail(self.from_addr, self.to_addrs, msg.as_string()) # Send the email
logging.info(f"Email sent: {title} - {message}")
except Exception as e:
logging.error(f"Failed to send email: {e}")
# Uptime Kuma notification implementation
class UptimeKumaNotification(NotificationProxy):
"""
Notification class for sending notifications to Uptime Kuma via a webhook.
"""
def __init__(self, webhook_url: str):
self.webhook_url = webhook_url
def send_notification(self, title: str, message: str, priority: int = 5):
"""
Send a notification to Uptime Kuma using a webhook.
Args:
title (str): The title of the notification (unused by Uptime Kuma but kept for consistency).
message (str): The body of the notification (unused by Uptime Kuma but kept for consistency).
priority (int): Unused, but kept for interface consistency.
"""
try:
response = requests.post(self.webhook_url, json={'title': title, 'message': message, 'priority': priority}, timeout=10)
response.raise_for_status()
logging.info("Uptime Kuma notification sent successfully")
except Exception as e:
logging.error(f"Failed to send Uptime Kuma notification: {e}")
# Send notification to all initialized notifiers
def send_notification(title, message, priority=5):
"""
Send a notification through all configured notifiers.
Args:
title (str): The title of the notification.
message (str): The body of the notification.
priority (int): The priority of the notification (if applicable).
"""
notifiers = initialize_notifiers()
if notifiers:
for notifier in notifiers:
try:
notifier.send_notification(title, message, priority)
except Exception as e:
logging.error(f"Failed to send notification using {notifier.__class__.__name__}: {e}")
else:
logging.warning("No notification system configured.")
# Initialize and return the list of configured notifiers
def initialize_notifiers():
"""
Initialize all available notification mechanisms based on the configuration.
Returns:
list: A list of instantiated notifier objects.
"""
notifiers = []
# Initialize email notifier if SMTP settings are available
if DEFAULTS.get('smtp_server') and DEFAULTS.get('smtp_username') and DEFAULTS.get('smtp_password'):
try:
email_notifier = EmailNotification(
smtp_server=DEFAULTS['smtp_server'],
port=DEFAULTS.get('smtp_port', 587), # Default SMTP port is 587
username=DEFAULTS['smtp_username'],
password=DEFAULTS['smtp_password'],
from_addr=DEFAULTS['smtp_from'],
to_addrs=DEFAULTS['smtp_to']
)
notifiers.append(email_notifier)
except Exception as e:
logging.error(f"Failed to initialize Email notifier: {e}")
# Initialize Gotify notifier if Gotify settings are available
if DEFAULTS.get('gotify_url') and DEFAULTS.get('gotify_token'):
try:
gotify_notifier = GotifyNotification(DEFAULTS['gotify_url'], DEFAULTS['gotify_token'])
notifiers.append(gotify_notifier)
except Exception as e:
logging.error(f"Failed to initialize Gotify notifier: {e}")
# Initialize Uptime Kuma notifier if webhook URL is available
if DEFAULTS.get('uptime_kuma_webhook_url'):
try:
uptime_kuma_notifier = UptimeKumaNotification(DEFAULTS['uptime_kuma_webhook_url'])
notifiers.append(uptime_kuma_notifier)
except Exception as e:
logging.error(f"Failed to initialize Uptime Kuma notifier: {e}")
return notifiers