// === System Health ===
export interface SystemHealth {
  cpuUsagePercent: number;
  memoryUsedMB: number;
  memoryTotalMB: number;
  memoryUsagePercent: number;
  diskUsedGB: number;
  diskTotalGB: number;
  diskUsagePercent: number;
  loadAvg1: number;
  loadAvg5: number;
  uptime: number; // seconds
}

// === Service Statuses ===
export type ServiceStatusType = "online" | "warning" | "offline";

export interface ProcessStatus {
  status: ServiceStatusType;
  pid: number;
  memoryMB: number;
  uptimeSeconds: number;
  restarts: number;
}

export interface PostgresqlStatus {
  status: ServiceStatusType;
  connections: number;
  maxConnections: number;
  latencyMs: number;
}

export interface PgBouncerStatus {
  status: ServiceStatusType;
  activeConnections: number;
  waitingClients: number;
  poolSize: number;
}

export interface RedisStatus {
  status: ServiceStatusType;
  memoryUsedMB: number;
  connectedClients: number;
  opsPerSec: number;
}

export interface ServiceStatuses {
  payload: ProcessStatus;
  queueWorker: ProcessStatus;
  postgresql: PostgresqlStatus;
  pgbouncer: PgBouncerStatus;
  redis: RedisStatus;
}

// === External Statuses ===
export interface SmtpStatus {
  status: ServiceStatusType;
  lastCheck: string; // ISO date
  responseTimeMs: number;
}

export type OAuthStatusType = "ok" | "expiring_soon" | "expired" | "error";

export interface OAuthTokenStatus {
  status: OAuthStatusType;
  tokensTotal: number;
  tokensExpiringSoon: number;
  tokensExpired: number;
}

export interface CronJobStatus {
  lastRun: string; // ISO date
  status: "ok" | "failed" | "unknown";
}

export interface CronStatuses {
  communitySync: CronJobStatus;
  tokenRefresh: CronJobStatus;
  youtubeSync: CronJobStatus;
}

export interface SecretExpiringSoon {
  name: string;
  expiresAt: string;
  daysRemaining: number;
}

export interface SecretExpired {
  name: string;
  expiresAt: string;
}

export interface SecretRotationOverdue {
  name: string;
  rotatedAt: string;
  ageDays: number;
}

export interface SecretsHealthStatus {
  status: "ok" | "warning" | "critical";
  checkedAt: string;
  missing: string[];
  expiringSoon: SecretExpiringSoon[];
  expired: SecretExpired[];
  rotationOverdue: SecretRotationOverdue[];
}

export interface SecurityMetricsStatus {
  windowMs: number;
  counters: Array<{
    eventType: string;
    count: number;
    windowStart: string;
  }>;
}

export interface ExternalStatuses {
  smtp: SmtpStatus;
  metaOAuth: OAuthTokenStatus;
  youtubeOAuth: OAuthTokenStatus;
  cronJobs: CronStatuses;
  secrets: SecretsHealthStatus;
  securityEvents: SecurityMetricsStatus;
}

// === Performance ===
export interface PerformanceMetrics {
  avgResponseTimeMs: number;
  p95ResponseTimeMs: number;
  p99ResponseTimeMs: number;
  errorRate: number; // 0-1
  requestsPerMinute: number;
}

// === Full Snapshot ===
export interface SystemMetrics {
  timestamp: string; // ISO date
  system: SystemHealth;
  services: ServiceStatuses;
  external: ExternalStatuses;
  performance: PerformanceMetrics;
}

// === SSE Events (discriminated union) ===
export type MonitoringEvent =
  | { type: "health"; data: SystemHealth }
  | { type: "service"; data: Partial<ServiceStatuses> }
  | { type: "alert"; data: AlertEvent }
  | { type: "log"; data: LogEvent }
  | { type: "performance"; data: PerformanceMetrics };

export interface AlertEvent {
  id: string;
  ruleId: string;
  metric: string;
  value: number;
  threshold: number;
  severity: AlertSeverity;
  message: string;
  timestamp: string;
}

export interface LogEvent {
  id: string;
  level: LogLevel;
  source: LogSource;
  message: string;
  timestamp: string;
  context?: Record<string, unknown>;
}

// === Enums as union types ===
export type AlertCondition = "gt" | "lt" | "eq" | "gte" | "lte";
export type AlertSeverity = "warning" | "error" | "critical";
export type LogLevel = "debug" | "info" | "warn" | "error" | "fatal";
export type LogSource = "payload" | "queue-worker" | "cron" | "email" | "oauth" | "sync" | "security";

// === Performance Tracker Entry ===
export interface PerformanceEntry {
  timestamp: number; // Date.now()
  method: string;
  path: string;
  statusCode: number;
  durationMs: number;
}
