/**
 * Security-Monitor: zentrale `emit()`-Funktion für sicherheitsrelevante
 * Events. Schreibt in die `SecurityEvent`-Tabelle (nicht im AuditLog,
 * weil hier andere Anforderungen gelten: schnelles Filtern, Threshold-
 * Detection, Realtime-Alerting statt forensischer Hash-Chain).
 *
 * Hooks für die wichtigsten Klassen:
 *   - LOGIN_FAILED            → Login mit falschem Passwort
 *   - LOGIN_SUCCESS           → erfolgreicher Login (informativ)
 *   - RATE_LIMIT_HIT          → express-rate-limit hat zugeschlagen
 *   - ACCESS_DENIED           → 403 von canAccess* (versuchter IDOR)
 *   - SSRF_BLOCKED            → ssrfGuard hat geblockt
 *   - PASSWORD_RESET_REQUEST  → Reset angefordert
 *   - PASSWORD_RESET_CONFIRM  → Reset abgeschlossen
 *   - LOGOUT                  → expliziter Logout
 *   - TOKEN_REJECTED          → JWT verify-Failure
 *   - PERMISSION_CHANGED      → Rolle/Permission-Update
 *
 * Sofort-Alert für CRITICAL+HIGH-Events (wenn `monitoringAlertEmail`
 * konfiguriert), sonst Sammlung im stündlichen Digest.
 */
import prisma from '../lib/prisma.js';
import type { SecurityEventType, SecuritySeverity } from '@prisma/client';

export interface SecurityEventInput {
  type: SecurityEventType;
  severity: SecuritySeverity;
  message: string;
  ipAddress?: string | null;
  userId?: number | null;
  customerId?: number | null;
  userEmail?: string | null;
  endpoint?: string | null;
  details?: Record<string, unknown>;
}

/**
 * Schreibt ein SecurityEvent. Fehler beim Schreiben werden geschluckt,
 * damit ein kaputtes Monitoring nicht den Login-Flow stoppt.
 */
export async function emit(event: SecurityEventInput): Promise<void> {
  try {
    await prisma.securityEvent.create({
      data: {
        type: event.type,
        severity: event.severity,
        message: event.message,
        ipAddress: event.ipAddress || null,
        userId: event.userId || null,
        customerId: event.customerId || null,
        userEmail: event.userEmail || null,
        endpoint: event.endpoint || null,
        details: event.details ? (event.details as any) : undefined,
      },
    });
  } catch (err) {
    console.error('[securityMonitor] emit failed:', err);
  }
}

/**
 * Helper: aus einem Express-Request die wichtigsten Kontextfelder extrahieren.
 * Funktioniert sowohl mit AuthRequest (eingeloggt) als auch mit anonymen
 * Requests (Login-Versuch etc.).
 */
export function contextFromRequest(req: any): {
  ipAddress: string;
  userId?: number;
  customerId?: number;
  userEmail?: string;
  endpoint: string;
} {
  const user = req?.user;
  return {
    ipAddress: req?.ip || req?.socket?.remoteAddress || 'unknown',
    userId: user?.userId,
    customerId: user?.customerId,
    userEmail: user?.email,
    endpoint: `${req?.method || ''} ${req?.path || req?.originalUrl || ''}`.trim(),
  };
}
