Initial commit: Bot Detector Dashboard for SOC Incident Response

🛡️ Dashboard complet pour l'analyse et la classification des menaces

Fonctionnalités principales:
- Visualisation des détections en temps réel (24h)
- Investigation multi-entités (IP, JA4, ASN, Host, User-Agent)
- Analyse de corrélation pour classification SOC
- Clustering automatique par subnet/JA4/UA
- Export des classifications pour ML

Composants:
- Backend: FastAPI (Python) + ClickHouse
- Frontend: React + TypeScript + TailwindCSS
- 6 routes API: metrics, detections, variability, attributes, analysis, entities
- 7 types d'entités investigables

Documentation ajoutée:
- NAVIGATION_GRAPH.md: Graph complet de navigation
- SOC_OPTIMIZATION_PROPOSAL.md: Proposition d'optimisation pour SOC
  • Réduction de 7 à 2 clics pour classification
  • Nouvelle vue /incidents clusterisée
  • Panel latéral d'investigation
  • Quick Search (Cmd+K)
  • Timeline interactive
  • Graph de corrélations

Sécurité:
- .gitignore configuré (exclut .env, secrets, node_modules)
- Credentials dans .env (à ne pas committer)

⚠️ Audit sécurité réalisé - Voir recommandations dans SOC_OPTIMIZATION_PROPOSAL.md

Co-authored-by: Qwen-Coder <qwen-coder@alibabacloud.com>
This commit is contained in:
SOC Analyst
2026-03-14 21:33:55 +01:00
commit a61828d1e7
55 changed files with 11189 additions and 0 deletions

119
backend/main.py Normal file
View File

@ -0,0 +1,119 @@
"""
Bot Detector Dashboard - API Backend
FastAPI application pour servir le dashboard web
"""
import logging
from contextlib import asynccontextmanager
from fastapi import FastAPI
from fastapi.middleware.cors import CORSMiddleware
from fastapi.staticfiles import StaticFiles
from fastapi.responses import FileResponse
import os
from .config import settings
from .database import db
from .routes import metrics, detections, variability, attributes, analysis, entities
# Configuration logging
logging.basicConfig(
level=logging.INFO,
format='%(asctime)s - %(name)s - %(levelname)s - %(message)s'
)
logger = logging.getLogger(__name__)
@asynccontextmanager
async def lifespan(app: FastAPI):
"""Gestion du cycle de vie de l'application"""
# Startup
logger.info("Démarrage du Bot Detector Dashboard API...")
logger.info(f"ClickHouse: {settings.CLICKHOUSE_HOST}:{settings.CLICKHOUSE_PORT}")
logger.info(f"Database: {settings.CLICKHOUSE_DB}")
# Tester la connexion ClickHouse
try:
client = db.connect()
client.ping()
logger.info("Connexion ClickHouse établie avec succès")
except Exception as e:
logger.error(f"Échec de connexion ClickHouse: {e}")
raise
yield
# Shutdown
logger.info("Arrêt du Bot Detector Dashboard API...")
db.close()
# Création de l'application FastAPI
app = FastAPI(
title="Bot Detector Dashboard API",
description="API pour le dashboard de visualisation des détections Bot Detector",
version="1.0.0",
lifespan=lifespan
)
# Configuration CORS
app.add_middleware(
CORSMiddleware,
allow_origins=settings.CORS_ORIGINS,
allow_credentials=True,
allow_methods=["*"],
allow_headers=["*"],
)
# Enregistrement des routes
app.include_router(metrics.router)
app.include_router(detections.router)
app.include_router(variability.router)
app.include_router(attributes.router)
app.include_router(analysis.router)
app.include_router(entities.router)
# Route pour servir le frontend
@app.get("/")
async def serve_frontend():
"""Sert l'application React"""
frontend_path = os.path.join(os.path.dirname(__file__), "..", "frontend", "dist", "index.html")
if os.path.exists(frontend_path):
return FileResponse(frontend_path)
return {"message": "Dashboard API - Frontend non construit. Voir /docs pour l'API."}
# Servir les assets statiques
assets_path = os.path.join(os.path.dirname(__file__), "..", "frontend", "dist", "assets")
if os.path.exists(assets_path):
app.mount("/assets", StaticFiles(directory=assets_path), name="assets")
# Health check
@app.get("/health")
async def health_check():
"""Endpoint de santé pour le health check Docker"""
try:
db.connect().ping()
return {"status": "healthy", "clickhouse": "connected"}
except Exception as e:
return {"status": "unhealthy", "clickhouse": "disconnected", "error": str(e)}
# Route catch-all pour le routing SPA (React Router) - DOIT ÊTRE EN DERNIER
@app.get("/{full_path:path}")
async def serve_spa(full_path: str):
"""Redirige toutes les routes vers index.html pour le routing React"""
frontend_path = os.path.join(os.path.dirname(__file__), "..", "frontend", "dist", "index.html")
if os.path.exists(frontend_path):
return FileResponse(frontend_path)
return {"message": "Dashboard API - Frontend non construit"}
if __name__ == "__main__":
import uvicorn
uvicorn.run(
"main:app",
host=settings.API_HOST,
port=settings.API_PORT,
reload=True
)