fastapi-alertengine 1.0.3__tar.gz → 1.0.4__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/PKG-INFO +1 -1
- fastapi_alertengine-1.0.4/fastapi_alertengine/engine.py +114 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine.egg-info/PKG-INFO +1 -1
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/pyproject.toml +1 -1
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/setup.cfg +1 -1
- fastapi_alertengine-1.0.3/fastapi_alertengine/engine.py +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/README.md +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine/__init__.py +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine/app_main.py +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine/client.py +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine/config.py +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine/middleware.py +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine/storage.py.py +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine.egg-info/SOURCES.txt +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine.egg-info/dependency_links.txt +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine.egg-info/requires.txt +0 -0
- {fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: fastapi-alertengine
|
|
3
|
-
Version: 1.0.
|
|
3
|
+
Version: 1.0.4
|
|
4
4
|
Summary: FastAPI AlertEngine: fintech-grade request monitoring (p95 latency + error rate) without Prometheus.
|
|
5
5
|
Author: Tandem Media
|
|
6
6
|
Project-URL: Homepage, https://github.com/Tandem-Media/fastapi-alertengine
|
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
# fastapi_alertengine/engine.py
|
|
2
|
+
|
|
3
|
+
import time
|
|
4
|
+
from typing import Dict, Any
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
STREAM_KEY = "anchorflow:request_metrics"
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
class AlertEngine:
|
|
11
|
+
"""
|
|
12
|
+
Real-time SLO / latency alert engine.
|
|
13
|
+
|
|
14
|
+
Uses rolling window analysis over Redis Stream data.
|
|
15
|
+
"""
|
|
16
|
+
|
|
17
|
+
def __init__(self, redis):
|
|
18
|
+
self.redis = redis
|
|
19
|
+
|
|
20
|
+
def _fetch_recent(self, last_n: int = 200):
|
|
21
|
+
raw = self.redis.xrevrange(STREAM_KEY, count=last_n)
|
|
22
|
+
|
|
23
|
+
events = []
|
|
24
|
+
for _, fields in raw:
|
|
25
|
+
try:
|
|
26
|
+
events.append({
|
|
27
|
+
"latency_ms": float(fields.get("latency_ms", 0)),
|
|
28
|
+
"type": fields.get("type", "api"),
|
|
29
|
+
"status_code": int(fields.get("status_code", 0)),
|
|
30
|
+
"timestamp": int(fields.get("timestamp", 0)),
|
|
31
|
+
})
|
|
32
|
+
except Exception:
|
|
33
|
+
continue
|
|
34
|
+
|
|
35
|
+
return events
|
|
36
|
+
|
|
37
|
+
def _p95(self, values):
|
|
38
|
+
if not values:
|
|
39
|
+
return 0.0
|
|
40
|
+
|
|
41
|
+
values.sort()
|
|
42
|
+
idx = int(len(values) * 0.95)
|
|
43
|
+
return values[min(idx, len(values) - 1)]
|
|
44
|
+
|
|
45
|
+
def _anomaly_score(self, current, baseline):
|
|
46
|
+
if baseline == 0:
|
|
47
|
+
return 0
|
|
48
|
+
|
|
49
|
+
return abs(current - baseline) / baseline
|
|
50
|
+
|
|
51
|
+
def evaluate(self, window_size: int = 200) -> Dict[str, Any]:
|
|
52
|
+
events = self._fetch_recent(window_size)
|
|
53
|
+
|
|
54
|
+
if not events:
|
|
55
|
+
return {
|
|
56
|
+
"status": "ok",
|
|
57
|
+
"reason": "no_data"
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
all_lat = [e["latency_ms"] for e in events]
|
|
61
|
+
webhook_lat = [e["latency_ms"] for e in events if e["type"] == "webhook"]
|
|
62
|
+
api_lat = [e["latency_ms"] for e in events if e["type"] == "api"]
|
|
63
|
+
|
|
64
|
+
def p95(values):
|
|
65
|
+
if not values:
|
|
66
|
+
return 0.0
|
|
67
|
+
values.sort()
|
|
68
|
+
idx = int(len(values) * 0.95)
|
|
69
|
+
return values[min(idx, len(values) - 1)]
|
|
70
|
+
|
|
71
|
+
overall_p95 = p95(all_lat)
|
|
72
|
+
webhook_p95 = p95(webhook_lat)
|
|
73
|
+
api_p95 = p95(api_lat)
|
|
74
|
+
|
|
75
|
+
# Baseline (simple rolling heuristic)
|
|
76
|
+
baseline = sum(all_lat) / len(all_lat)
|
|
77
|
+
|
|
78
|
+
anomaly = self._anomaly_score(overall_p95, baseline)
|
|
79
|
+
|
|
80
|
+
# Alert thresholds
|
|
81
|
+
status = "ok"
|
|
82
|
+
|
|
83
|
+
if overall_p95 > 3000 or anomaly > 2.0:
|
|
84
|
+
status = "critical"
|
|
85
|
+
elif overall_p95 > 1000 or anomaly > 1.0:
|
|
86
|
+
status = "warning"
|
|
87
|
+
|
|
88
|
+
# Failure pressure signal
|
|
89
|
+
error_rate = sum(1 for e in events if e["status_code"] >= 500) / len(events)
|
|
90
|
+
|
|
91
|
+
if error_rate > 0.2:
|
|
92
|
+
status = "critical"
|
|
93
|
+
elif error_rate > 0.1 and status != "critical":
|
|
94
|
+
status = "warning"
|
|
95
|
+
|
|
96
|
+
return {
|
|
97
|
+
"status": status,
|
|
98
|
+
"metrics": {
|
|
99
|
+
"overall_p95_ms": overall_p95,
|
|
100
|
+
"webhook_p95_ms": webhook_p95,
|
|
101
|
+
"api_p95_ms": api_p95,
|
|
102
|
+
"error_rate": error_rate,
|
|
103
|
+
"anomaly_score": anomaly,
|
|
104
|
+
"sample_size": len(events),
|
|
105
|
+
},
|
|
106
|
+
"thresholds": {
|
|
107
|
+
"p95_warning": 1000,
|
|
108
|
+
"p95_critical": 3000,
|
|
109
|
+
"anomaly_warning": 1.0,
|
|
110
|
+
"anomaly_critical": 2.0,
|
|
111
|
+
"error_rate_critical": 0.2,
|
|
112
|
+
},
|
|
113
|
+
"timestamp": int(time.time()),
|
|
114
|
+
}
|
{fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine.egg-info/PKG-INFO
RENAMED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: fastapi-alertengine
|
|
3
|
-
Version: 1.0.
|
|
3
|
+
Version: 1.0.4
|
|
4
4
|
Summary: FastAPI AlertEngine: fintech-grade request monitoring (p95 latency + error rate) without Prometheus.
|
|
5
5
|
Author: Tandem Media
|
|
6
6
|
Project-URL: Homepage, https://github.com/Tandem-Media/fastapi-alertengine
|
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "fastapi-alertengine"
|
|
7
|
-
version = "1.0.
|
|
7
|
+
version = "1.0.4"
|
|
8
8
|
description = "FastAPI AlertEngine: fintech-grade request monitoring (p95 latency + error rate) without Prometheus."
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
requires-python = ">=3.10"
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine.egg-info/SOURCES.txt
RENAMED
|
File without changes
|
|
File without changes
|
{fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine.egg-info/requires.txt
RENAMED
|
File without changes
|
{fastapi_alertengine-1.0.3 → fastapi_alertengine-1.0.4}/fastapi_alertengine.egg-info/top_level.txt
RENAMED
|
File without changes
|