API-KA — plateforme centrale : collecte quotidienne des 8 services KA, historisation append-only et API publique sur www.api-ka.com
Python 60.9%
HTML 21%
TypeScript 7.3%
JavaScript 5.2%
CSS 4.8%
Shell 0.8%
1# ============================================2# Projet : API-KA3# Fichier : src/api/middleware/logging.py4# Node : m3u96b5# Author : Simon-Pierre Boucher6# Contact : contact@spboucher.ai7# Date : 2026-08-168# ============================================9"""Middleware de journalisation : chaque requête HTTP est loggée en JSON."""1011from __future__ import annotations1213import datetime14import time1516from starlette.middleware.base import BaseHTTPMiddleware, RequestResponseEndpoint17from starlette.requests import Request18from starlette.responses import Response1920from src.api import reqstats21from src.utils.logger import get_logger222324class RequestLoggingMiddleware(BaseHTTPMiddleware):25 """Logge méthode, chemin, statut, durée et IP client de chaque requête."""2627 async def dispatch(28 self, request: Request, call_next: RequestResponseEndpoint29 ) -> Response:30 start = time.perf_counter()31 response = await call_next(request)32 duration_ms = round((time.perf_counter() - start) * 1000, 2)33 # Journalisation légère pour /stats : simple append en mémoire (O(1),34 # aucune I/O ici) — la persistance se fait en lot par la tâche de fond.35 try:36 reqstats.record(37 ts=datetime.datetime.now(tz=datetime.UTC),38 method=request.method,39 path=request.url.path,40 status=response.status_code,41 duration_ms=duration_ms,42 )43 except Exception: # pragma: no cover — jamais bloquant pour l'API44 pass45 get_logger("apika.api").info(46 "http_request",47 extra={48 "method": request.method,49 "path": request.url.path,50 "status_code": response.status_code,51 "duration_ms": duration_ms,52 "client_ip": request.client.host if request.client else "unknown",53 },54 )55 return response56