<?php
declare(strict_types=1);
namespace App\Services;
use App\Core\Database;
final class SiemAnalyticsService
{
 /** @return array<string,mixed> */
 public function dashboard(array $input): array
 {
  [$where,$params,$filters]=$this->filters($input);
  $pdo=Database::connection();
  $scalar=function(string $sql)use($pdo,$params):int{$s=$pdo->prepare($sql);$s->execute($params);return (int)$s->fetchColumn();};
  $list=function(string $sql)use($pdo,$params):array{$s=$pdo->prepare($sql);$s->execute($params);return $s->fetchAll()?:[];};
  return ['filters'=>$filters,'kpis'=>[
   'events'=>$scalar("SELECT COUNT(*) FROM system_security_events e $where"),
   'critical'=>$scalar("SELECT COUNT(*) FROM system_security_events e $where".($where?' AND':' WHERE')." e.severity='critical'"),
   'incidents'=>(int)$pdo->query("SELECT COUNT(*) FROM system_security_incidents WHERE status IN ('open','investigating')")->fetchColumn(),
   'detections'=>(int)$pdo->query("SELECT COUNT(*) FROM system_security_detections WHERE status='open'")->fetchColumn(),
  ],
  'daily'=>$list("SELECT DATE(e.occurred_at) bucket,COUNT(*) total,SUM(e.severity='critical') critical FROM system_security_events e $where GROUP BY DATE(e.occurred_at) ORDER BY bucket"),
  'severity'=>$list("SELECT e.severity label,COUNT(*) total FROM system_security_events e $where GROUP BY e.severity ORDER BY total DESC"),
  'categories'=>$list("SELECT e.category label,COUNT(*) total FROM system_security_events e $where GROUP BY e.category ORDER BY total DESC LIMIT 10"),
  'modules'=>$list("SELECT e.module label,COUNT(*) total FROM system_security_events e $where GROUP BY e.module ORDER BY total DESC LIMIT 10"),
  'results'=>$list("SELECT e.result label,COUNT(*) total FROM system_security_events e $where GROUP BY e.result ORDER BY total DESC LIMIT 10"),
  'users'=>$list("SELECT COALESCE(e.user_id,0) label,COUNT(*) total FROM system_security_events e $where GROUP BY COALESCE(e.user_id,0) ORDER BY total DESC LIMIT 10"),
  'events'=>$this->events($input,200),
  'detections'=>$pdo->query("SELECT rule_name,entity_type,entity_id,score,severity,status,detected_at FROM system_security_detections ORDER BY detected_at DESC LIMIT 25")->fetchAll()?:[]];
 }
 /** @return list<array<string,mixed>> */
 public function events(array $input,int $limit=500): array{[$where,$params]=$this->filters($input);$limit=max(1,min(5000,$limit));$s=Database::connection()->prepare("SELECT occurred_at,severity,category,module,action,result,user_id,message FROM system_security_events e $where ORDER BY e.occurred_at DESC LIMIT $limit");$s->execute($params);return $s->fetchAll()?:[];}
 /** @return array{0:string,1:array<string,mixed>,2:array<string,string>} */
 private function filters(array $i): array
 {
  $to=(string)($i['to']??date('Y-m-d'));$from=(string)($i['from']??date('Y-m-d',strtotime('-29 days')));if(!preg_match('/^\d{4}-\d{2}-\d{2}$/',$from))$from=date('Y-m-d',strtotime('-29 days'));if(!preg_match('/^\d{4}-\d{2}-\d{2}$/',$to))$to=date('Y-m-d');
  $w=['e.occurred_at >= :from','e.occurred_at < DATE_ADD(:to, INTERVAL 1 DAY)'];$p=['from'=>$from.' 00:00:00','to'=>$to.' 00:00:00'];$f=['from'=>$from,'to'=>$to,'severity'=>'','module'=>'','category'=>'','q'=>''];
  foreach(['severity','module','category'] as $k){$v=trim((string)($i[$k]??''));if($v!==''&&strlen($v)<=80){$w[]="e.$k = :$k";$p[$k]=$v;$f[$k]=$v;}}
  $q=trim((string)($i['q']??''));if($q!==''&&strlen($q)<=120){$w[]='(e.message LIKE :q OR e.action LIKE :q OR e.result LIKE :q)';$p['q']='%'.$q.'%';$f['q']=$q;}
  return ['WHERE '.implode(' AND ',$w),$p,$f];
 }
}
