Observed since 21 Oct, 09:19 UTC
No superseded metadata states collected. Unchanged observations do not create new revisions.
Production-grade unsupervised anomaly detection for drone telemetry
Production-grade unsupervised anomaly detection for drone telemetry
Agomax is a Python package that detects anomalies in drone flight data using unsupervised machine learning. Train once on normal flights, then identify deviations in real-time or batch processing—no labeled anomalies required.
Drone operations generate high-dimensional telemetry where anomalies are rare and unlabeled. Supervised approaches fail due to insufficient failure examples. Agomax solves this by:
git clone https://github.com/shaguntembhurne/Agomax.git
cd Agomax
pip install -e .
Requirements: Python 3.8+, NumPy, Pandas, Scikit-learn, SciPy, Joblib
import pandas as pd
from agomax import AgoMaxDetector
# 1. Load normal flight data (no anomalies)
train_df = pd.read_csv("normal_flights.csv")
# 2. Train detector
detector = AgoMaxDetector()
detector.fit(train_df)
# 3. Save for deployment
detector.save("models/drone_detector")
# 4. Load and detect anomalies
detector = AgoMaxDetector.load("models/drone_detector")
test_df = pd.read_csv("new_flight.csv")
result = detector.predict(test_df)
# 5. Access results
print(f"Anomalies detected: {result.labels.sum()}")
print(f"Mean anomaly score: {result.scores.mean():.3f}")
Agomax uses an ensemble of five unsupervised models to characterize normal behavior:
| Model | Type | Purpose |
|---|---|---|
| KMeans | Clustering | Distance to normal clusters |
| LOF | Density | Local outlier detection |
| One-Class SVM | Margin | Decision boundary around normal data |
| DBSCAN | Clustering | Structural outlier context |
| OPTICS | Clustering | Handles varying densities |
Raw Data → Preprocessing → Hyperparameter Tuning → Ensemble Fit → Threshold Learning → Save
New Data → Transform → Score (per-model) → Threshold → Vote → Anomaly + Confidence
from agomax import AgoMaxDetector
import pandas as pd
# Train
detector = AgoMaxDetector()
detector.fit(train_df)
detector.save("models/")
# Predict
detector = AgoMaxDetector.load("models/")
result = detector.predict(test_df)
print(result.scores) # Continuous anomaly scores [0-1]
print(result.labels) # Binary labels: 0=normal, 1=anomaly
print(result.events) # Confirmed events after temporal filtering
result = detector.predict(test_df, explain=True)
for i, detail in enumerate(result.details):
if detail['is_anomaly']:
print(f"\nSample {i}:")
print(f" Anomaly Score: {detail['anomaly_score']:.3f}")
print(f" Vote Ratio: {detail['vote_ratio']:.3f}")
print(f" Top Contributors: {detail['top_contributors']}")
print(f" Model Scores: {detail['model_scores']}")
from agomax import AgoMaxDetector, DetectorConfig, EnsembleConfig
config = DetectorConfig(
vote_threshold=0.6, # 60% of models must agree
confirmation_steps=5, # Require 5 consecutive anomalies
cooldown_steps=15, # Wait 15 steps after event
ensemble=EnsembleConfig(
kmeans_n_clusters=3,
lof_n_neighbors=30,
ocsvm_nu=0.02,
),
auto_tune=False,
)
detector = AgoMaxDetector(config)
detector.fit(train_df)
detector = AgoMaxDetector.load("models/")
while True:
sample = get_telemetry_sample()
sample_df = pd.DataFrame([sample])
result = detector.predict(sample_df)
if result.labels[0]:
print(f"ANOMALY: score={result.scores[0]:.3f}")
if result.events[0]:
print(f"CONFIRMED EVENT - Take action!")
Methods
fit(data, auto_tune=True) — Train on normal datapredict(data, explain=False) — Detect anomalies, returns AnomalyResultsave(directory) — Persist trained detectorload(directory) — Load from disk (classmethod)reset_state() — Reset adaptive thresholdsAttributes
scores (ndarray) — Continuous anomaly scores [0-1]labels (ndarray) — Binary labels: 0=normal, 1=anomalyevents (ndarray) — Confirmed events after temporal filteringdetails (list, optional) — Per-sample explanationsDetectorConfig
DetectorConfig(
vote_threshold=0.5, # Fraction of models that must agree
confirmation_steps=3, # Consecutive anomalies for event
cooldown_steps=10, # Wait period after event
auto_tune=True, # Auto-tune hyperparameters
)
EnsembleConfig
EnsembleConfig(
kmeans_n_clusters=2,
lof_n_neighbors=20,
ocsvm_nu=0.01,
dbscan_eps=1.2,
optics_min_samples=20,
random_state=42,
)
High false positives:
vote_threshold (0.6-0.7)confirmation_steps (5-10)Missing anomalies:
vote_threshold (0.3-0.4)Noisy alerts:
confirmation_stepscooldown_stepsagomax/
├── __init__.py # Public API exports
├── detector.py # AgoMaxDetector (main class)
├── config.py # Configuration dataclasses
├── exceptions.py # Custom exceptions
├── utils.py # Data loading utilities
└── core/
├── preprocessing.py # Data preprocessing
├── ensemble.py # Model ensemble
├── threshold.py # Adaptive thresholds
└── tuning.py # Hyperparameter tuning
Contributions are welcome. Please:
git checkout -b feature/name)MIT License - see LICENSE file for details.
@software{agomax2024,
title={Agomax: Production-Grade Anomaly Detection for Drone Telemetry},
author={Tembhurne, Shagun},
year={2024},
url={https://github.com/shaguntembhurne/Agomax}
}
Shagun Tembhurne
GitHub: @shaguntembhurne
Repository: github.com/shaguntembhurne/Agomax
Built with scikit-learn, pandas, and NumPy.
Download counts and popularity will appear here as the collector receives them.
| Version | Published | Direct dependencies | Open version |
|---|---|---|---|
| 0.2.3 | 14 Dec 2025 | 13 |
This describes our collected data; it is not a security assessment.
Observed since 21 Oct, 09:19 UTC
No superseded metadata states collected. Unchanged observations do not create new revisions.
package:ddff58388036eb83e58ff57ab195f94ef6eb844047b9b9ab8d3facdc4388d57d