adding ai summary - default is disabled

This commit is contained in:
2026-01-26 17:13:11 -06:00
parent 2820944ec6
commit 921b6a81a4
13 changed files with 1357 additions and 43 deletions

View File

@@ -1,8 +1,8 @@
"""State management models for alert deduplication."""
"""State management models for alert deduplication and change detection."""
from dataclasses import dataclass, field
from datetime import datetime
from typing import Any
from typing import Any, Optional
@dataclass
@@ -41,12 +41,59 @@ class SentAlertRecord:
)
@dataclass
class AlertSnapshot:
"""Snapshot of an alert for change detection between runs."""
alert_type: str
extreme_value: float
threshold: float
start_time: str
end_time: str
hour_count: int
captured_at: datetime = field(default_factory=datetime.now)
def to_dict(self) -> dict[str, Any]:
"""Convert to dictionary for JSON serialization."""
return {
"alert_type": self.alert_type,
"extreme_value": self.extreme_value,
"threshold": self.threshold,
"start_time": self.start_time,
"end_time": self.end_time,
"hour_count": self.hour_count,
"captured_at": self.captured_at.isoformat(),
}
@classmethod
def from_dict(cls, data: dict[str, Any]) -> "AlertSnapshot":
"""Create from dictionary.
Args:
data: The serialized snapshot dict.
Returns:
An AlertSnapshot instance.
"""
return cls(
alert_type=data["alert_type"],
extreme_value=data["extreme_value"],
threshold=data["threshold"],
start_time=data["start_time"],
end_time=data["end_time"],
hour_count=data["hour_count"],
captured_at=datetime.fromisoformat(data["captured_at"]),
)
@dataclass
class AlertState:
"""State container for tracking sent alerts."""
"""State container for tracking sent alerts and change detection."""
sent_alerts: dict[str, SentAlertRecord] = field(default_factory=dict)
last_updated: datetime = field(default_factory=datetime.now)
previous_alert_snapshots: dict[str, AlertSnapshot] = field(default_factory=dict)
last_ai_summary_sent: Optional[datetime] = None
def is_duplicate(self, dedup_key: str) -> bool:
"""Check if an alert with this dedup key has already been sent.
@@ -106,6 +153,15 @@ class AlertState:
key: record.to_dict() for key, record in self.sent_alerts.items()
},
"last_updated": self.last_updated.isoformat(),
"previous_alert_snapshots": {
key: snapshot.to_dict()
for key, snapshot in self.previous_alert_snapshots.items()
},
"last_ai_summary_sent": (
self.last_ai_summary_sent.isoformat()
if self.last_ai_summary_sent
else None
),
}
@classmethod
@@ -130,4 +186,21 @@ class AlertState:
else datetime.now()
)
return cls(sent_alerts=sent_alerts, last_updated=last_updated)
previous_alert_snapshots = {
key: AlertSnapshot.from_dict(snapshot_data)
for key, snapshot_data in data.get("previous_alert_snapshots", {}).items()
}
last_ai_summary_str = data.get("last_ai_summary_sent")
last_ai_summary_sent = (
datetime.fromisoformat(last_ai_summary_str)
if last_ai_summary_str
else None
)
return cls(
sent_alerts=sent_alerts,
last_updated=last_updated,
previous_alert_snapshots=previous_alert_snapshots,
last_ai_summary_sent=last_ai_summary_sent,
)