mirror of
https://github.com/jokob-sk/NetAlertX.git
synced 2026-04-03 00:31:35 -07:00
Keep all local changes while resolving conflicts
This commit is contained in:
133
server/messaging/notification_sections.py
Normal file
133
server/messaging/notification_sections.py
Normal file
@@ -0,0 +1,133 @@
|
||||
# -------------------------------------------------------------------------------
|
||||
# notification_sections.py — Single source of truth for notification section
|
||||
# metadata: titles, SQL templates, datetime fields, and section ordering.
|
||||
#
|
||||
# Both reporting.py and notification_instance.py import from here.
|
||||
# -------------------------------------------------------------------------------
|
||||
|
||||
# Canonical processing order
|
||||
SECTION_ORDER = [
|
||||
"new_devices",
|
||||
"down_devices",
|
||||
"down_reconnected",
|
||||
"events",
|
||||
"plugins",
|
||||
]
|
||||
|
||||
# Section display titles (used in text + HTML notifications)
|
||||
SECTION_TITLES = {
|
||||
"new_devices": "🆕 New devices",
|
||||
"down_devices": "🔴 Down devices",
|
||||
"down_reconnected": "🔁 Reconnected down devices",
|
||||
"events": "⚡ Events",
|
||||
"plugins": "🔌 Plugins",
|
||||
}
|
||||
|
||||
# Which column(s) contain datetime values per section (for timezone conversion)
|
||||
DATETIME_FIELDS = {
|
||||
"new_devices": ["eve_DateTime"],
|
||||
"down_devices": ["eve_DateTime"],
|
||||
"down_reconnected": ["eve_DateTime"],
|
||||
"events": ["eve_DateTime"],
|
||||
"plugins": ["DateTimeChanged"],
|
||||
}
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# SQL templates
|
||||
#
|
||||
# All device sections use unified DB column names so the JSON output
|
||||
# has consistent field names across new_devices, down_devices,
|
||||
# down_reconnected, and events.
|
||||
#
|
||||
# Placeholders:
|
||||
# {condition} — optional WHERE clause appended by condition builder
|
||||
# {alert_down_minutes} — runtime value, only used by down_devices
|
||||
# ---------------------------------------------------------------------------
|
||||
SQL_TEMPLATES = {
|
||||
"new_devices": """
|
||||
SELECT
|
||||
devName,
|
||||
eve_MAC,
|
||||
devVendor,
|
||||
devLastIP as eve_IP,
|
||||
eve_DateTime,
|
||||
eve_EventType,
|
||||
devComments
|
||||
FROM Events_Devices
|
||||
WHERE eve_PendingAlertEmail = 1
|
||||
AND eve_EventType = 'New Device' {condition}
|
||||
ORDER BY eve_DateTime
|
||||
""",
|
||||
"down_devices": """
|
||||
SELECT
|
||||
devName,
|
||||
eve_MAC,
|
||||
devVendor,
|
||||
eve_IP,
|
||||
eve_DateTime,
|
||||
eve_EventType,
|
||||
devComments
|
||||
FROM Events_Devices AS down_events
|
||||
WHERE eve_PendingAlertEmail = 1
|
||||
AND down_events.eve_EventType = 'Device Down'
|
||||
AND eve_DateTime < datetime('now', '-{alert_down_minutes} minutes')
|
||||
AND NOT EXISTS (
|
||||
SELECT 1
|
||||
FROM Events AS connected_events
|
||||
WHERE connected_events.eve_MAC = down_events.eve_MAC
|
||||
AND connected_events.eve_EventType = 'Connected'
|
||||
AND connected_events.eve_DateTime > down_events.eve_DateTime
|
||||
)
|
||||
ORDER BY down_events.eve_DateTime
|
||||
""",
|
||||
"down_reconnected": """
|
||||
SELECT
|
||||
devName,
|
||||
eve_MAC,
|
||||
devVendor,
|
||||
eve_IP,
|
||||
eve_DateTime,
|
||||
eve_EventType,
|
||||
devComments
|
||||
FROM Events_Devices AS reconnected_devices
|
||||
WHERE reconnected_devices.eve_EventType = 'Down Reconnected'
|
||||
AND reconnected_devices.eve_PendingAlertEmail = 1
|
||||
ORDER BY reconnected_devices.eve_DateTime
|
||||
""",
|
||||
"events": """
|
||||
SELECT
|
||||
devName,
|
||||
eve_MAC,
|
||||
devVendor,
|
||||
devLastIP as eve_IP,
|
||||
eve_DateTime,
|
||||
eve_EventType,
|
||||
devComments
|
||||
FROM Events_Devices
|
||||
WHERE eve_PendingAlertEmail = 1
|
||||
AND eve_EventType IN ('Connected', 'Down Reconnected', 'Disconnected','IP Changed') {condition}
|
||||
ORDER BY eve_DateTime
|
||||
""",
|
||||
"plugins": """
|
||||
SELECT
|
||||
Plugin,
|
||||
Object_PrimaryId,
|
||||
Object_SecondaryId,
|
||||
DateTimeChanged,
|
||||
Watched_Value1,
|
||||
Watched_Value2,
|
||||
Watched_Value3,
|
||||
Watched_Value4,
|
||||
Status
|
||||
FROM Plugins_Events
|
||||
""",
|
||||
}
|
||||
|
||||
# Sections that support user-defined condition filters
|
||||
SECTIONS_WITH_CONDITIONS = {"new_devices", "events"}
|
||||
|
||||
# Legacy setting key mapping for condition filters
|
||||
SECTION_CONDITION_MAP = {
|
||||
"new_devices": "NTFPRCS_new_dev_condition",
|
||||
"events": "NTFPRCS_event_condition",
|
||||
}
|
||||
@@ -25,20 +25,20 @@ from helper import ( # noqa: E402 [flake8 lint suppression]
|
||||
from logger import mylog # noqa: E402 [flake8 lint suppression]
|
||||
from db.sql_safe_builder import create_safe_condition_builder # noqa: E402 [flake8 lint suppression]
|
||||
from utils.datetime_utils import format_date_iso # noqa: E402 [flake8 lint suppression]
|
||||
from messaging.notification_sections import ( # noqa: E402 [flake8 lint suppression]
|
||||
SECTION_ORDER,
|
||||
SECTION_TITLES,
|
||||
DATETIME_FIELDS,
|
||||
SQL_TEMPLATES,
|
||||
SECTIONS_WITH_CONDITIONS,
|
||||
SECTION_CONDITION_MAP,
|
||||
)
|
||||
import conf # noqa: E402 [flake8 lint suppression]
|
||||
|
||||
# ===============================================================================
|
||||
# Timezone conversion
|
||||
# ===============================================================================
|
||||
|
||||
DATETIME_FIELDS = {
|
||||
"new_devices": ["Datetime"],
|
||||
"down_devices": ["eve_DateTime"],
|
||||
"down_reconnected": ["eve_DateTime"],
|
||||
"events": ["Datetime"],
|
||||
"plugins": ["DateTimeChanged"],
|
||||
}
|
||||
|
||||
|
||||
def get_datetime_fields_from_columns(column_names):
|
||||
return [
|
||||
@@ -155,6 +155,7 @@ def get_notifications(db):
|
||||
|
||||
return ""
|
||||
|
||||
<<<<<<< Updated upstream
|
||||
# -------------------------
|
||||
# SQL templates
|
||||
# -------------------------
|
||||
@@ -245,13 +246,17 @@ def get_notifications(db):
|
||||
|
||||
# Sections that support dynamic conditions
|
||||
sections_with_conditions = {"new_devices", "events"}
|
||||
=======
|
||||
# SQL templates with placeholders for runtime values
|
||||
# {condition} and {alert_down_minutes} are formatted at query time
|
||||
>>>>>>> Stashed changes
|
||||
|
||||
# Initialize final structure
|
||||
final_json = {}
|
||||
for section in ["new_devices", "down_devices", "down_reconnected", "events", "plugins"]:
|
||||
for section in SECTION_ORDER:
|
||||
final_json[section] = []
|
||||
final_json[f"{section}_meta"] = {
|
||||
"title": section_titles.get(section, section),
|
||||
"title": SECTION_TITLES.get(section, section),
|
||||
"columnNames": []
|
||||
}
|
||||
|
||||
@@ -260,17 +265,8 @@ def get_notifications(db):
|
||||
# -------------------------
|
||||
# Main loop
|
||||
# -------------------------
|
||||
condition_builder = create_safe_condition_builder()
|
||||
|
||||
SECTION_CONDITION_MAP = {
|
||||
"new_devices": "NTFPRCS_new_dev_condition",
|
||||
"events": "NTFPRCS_event_condition",
|
||||
}
|
||||
|
||||
sections_with_conditions = set(SECTION_CONDITION_MAP.keys())
|
||||
|
||||
for section in sections:
|
||||
template = sql_templates.get(section)
|
||||
template = SQL_TEMPLATES.get(section)
|
||||
|
||||
if not template:
|
||||
mylog("verbose", ["[Notification] Unknown section: ", section])
|
||||
@@ -280,7 +276,7 @@ def get_notifications(db):
|
||||
parameters = {}
|
||||
|
||||
try:
|
||||
if section in sections_with_conditions:
|
||||
if section in SECTIONS_WITH_CONDITIONS:
|
||||
condition_key = SECTION_CONDITION_MAP.get(section)
|
||||
condition_setting = get_setting_value(condition_key)
|
||||
|
||||
@@ -289,11 +285,18 @@ def get_notifications(db):
|
||||
condition_setting
|
||||
)
|
||||
|
||||
sqlQuery = template.format(condition=safe_condition)
|
||||
# Format template with runtime placeholders
|
||||
format_vars = {"condition": safe_condition}
|
||||
if section == "down_devices":
|
||||
format_vars["alert_down_minutes"] = alert_down_minutes
|
||||
sqlQuery = template.format(**format_vars)
|
||||
|
||||
except Exception as e:
|
||||
mylog("verbose", [f"[Notification] Error building condition for {section}: ", e])
|
||||
sqlQuery = template.format(condition="")
|
||||
fallback_vars = {"condition": ""}
|
||||
if section == "down_devices":
|
||||
fallback_vars["alert_down_minutes"] = alert_down_minutes
|
||||
sqlQuery = template.format(**fallback_vars)
|
||||
parameters = {}
|
||||
|
||||
mylog("debug", [f"[Notification] {section} SQL query: ", sqlQuery])
|
||||
@@ -307,7 +310,7 @@ def get_notifications(db):
|
||||
|
||||
final_json[section] = json_obj.json.get("data", [])
|
||||
final_json[f"{section}_meta"] = {
|
||||
"title": section_titles.get(section, section),
|
||||
"title": SECTION_TITLES.get(section, section),
|
||||
"columnNames": getattr(json_obj, "columnNames", [])
|
||||
}
|
||||
|
||||
|
||||
@@ -16,6 +16,7 @@ from helper import (
|
||||
getBuildTimeStampAndVersion,
|
||||
)
|
||||
from messaging.in_app import write_notification
|
||||
from messaging.notification_sections import SECTION_ORDER
|
||||
from utils.datetime_utils import timeNowUTC, timeNowTZ, get_timezone_offset
|
||||
|
||||
|
||||
@@ -60,12 +61,7 @@ class NotificationInstance:
|
||||
write_file(logPath + "/report_output.json", json.dumps(JSON))
|
||||
|
||||
# Check if nothing to report, end
|
||||
if (
|
||||
JSON["new_devices"] == [] and JSON["down_devices"] == [] and JSON["events"] == [] and JSON["plugins"] == [] and JSON["down_reconnected"] == []
|
||||
):
|
||||
self.HasNotifications = False
|
||||
else:
|
||||
self.HasNotifications = True
|
||||
self.HasNotifications = any(JSON.get(s, []) for s in SECTION_ORDER)
|
||||
|
||||
self.GUID = str(uuid.uuid4())
|
||||
self.DateTimeCreated = timeNowUTC()
|
||||
@@ -129,47 +125,13 @@ class NotificationInstance:
|
||||
mail_text = mail_text.replace("REPORT_DASHBOARD_URL", self.serverUrl)
|
||||
mail_html = mail_html.replace("REPORT_DASHBOARD_URL", self.serverUrl)
|
||||
|
||||
# Start generating the TEXT & HTML notification messages
|
||||
# new_devices
|
||||
# ---
|
||||
html, text = construct_notifications(self.JSON, "new_devices")
|
||||
|
||||
mail_text = mail_text.replace("NEW_DEVICES_TABLE", text + "\n")
|
||||
mail_html = mail_html.replace("NEW_DEVICES_TABLE", html)
|
||||
mylog("verbose", ["[Notification] New Devices sections done."])
|
||||
|
||||
# down_devices
|
||||
# ---
|
||||
html, text = construct_notifications(self.JSON, "down_devices")
|
||||
|
||||
mail_text = mail_text.replace("DOWN_DEVICES_TABLE", text + "\n")
|
||||
mail_html = mail_html.replace("DOWN_DEVICES_TABLE", html)
|
||||
mylog("verbose", ["[Notification] Down Devices sections done."])
|
||||
|
||||
# down_reconnected
|
||||
# ---
|
||||
html, text = construct_notifications(self.JSON, "down_reconnected")
|
||||
|
||||
mail_text = mail_text.replace("DOWN_RECONNECTED_TABLE", text + "\n")
|
||||
mail_html = mail_html.replace("DOWN_RECONNECTED_TABLE", html)
|
||||
mylog("verbose", ["[Notification] Reconnected Down Devices sections done."])
|
||||
|
||||
# events
|
||||
# ---
|
||||
html, text = construct_notifications(self.JSON, "events")
|
||||
|
||||
mail_text = mail_text.replace("EVENTS_TABLE", text + "\n")
|
||||
mail_html = mail_html.replace("EVENTS_TABLE", html)
|
||||
mylog("verbose", ["[Notification] Events sections done."])
|
||||
|
||||
# plugins
|
||||
# ---
|
||||
html, text = construct_notifications(self.JSON, "plugins")
|
||||
|
||||
mail_text = mail_text.replace("PLUGINS_TABLE", text + "\n")
|
||||
mail_html = mail_html.replace("PLUGINS_TABLE", html)
|
||||
|
||||
mylog("verbose", ["[Notification] Plugins sections done."])
|
||||
# Generate TEXT & HTML for each notification section
|
||||
for section in SECTION_ORDER:
|
||||
html, text = construct_notifications(self.JSON, section)
|
||||
placeholder = f"{section.upper()}_TABLE"
|
||||
mail_text = mail_text.replace(placeholder, text + "\n")
|
||||
mail_html = mail_html.replace(placeholder, html)
|
||||
mylog("verbose", [f"[Notification] {section} section done."])
|
||||
|
||||
final_text = removeDuplicateNewLines(mail_text)
|
||||
|
||||
|
||||
Reference in New Issue
Block a user