<?php
declare(strict_types=1);

session_start();
require_once __DIR__ . '/session-guard.php';
ignore_user_abort(true);
date_default_timezone_set('Europe/Paris');
header('Content-Type: application/json; charset=utf-8');

require_active_client_session(false);

function clean_csv(string $value): string
{
    return str_replace(["\"", ';', "\n", "\r"], '', $value);
}

function safe_substr(string $value, int $maxLength): string
{
    $value = trim($value);

    if (function_exists('mb_substr')) {
        return mb_substr($value, 0, $maxLength, 'UTF-8');
    }

    return substr($value, 0, $maxLength);
}

function ensure_directory(string $path): bool
{
    return is_dir($path) || mkdir($path, 0755, true);
}

function is_public_ip(string $ip): bool
{
    return (bool) filter_var(
        $ip,
        FILTER_VALIDATE_IP,
        FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE
    );
}

function first_valid_ip_from_header(?string $value): ?string
{
    if (!$value) {
        return null;
    }

    foreach (explode(',', $value) as $candidate) {
        $candidate = trim($candidate);
        if (filter_var($candidate, FILTER_VALIDATE_IP)) {
            return $candidate;
        }
    }

    return null;
}

function resolve_tracked_ip(): string
{
    $remoteAddr = trim((string) ($_SERVER['REMOTE_ADDR'] ?? ''));
    if ($remoteAddr !== '' && is_public_ip($remoteAddr)) {
        return $remoteAddr;
    }

    $forwardedCandidates = [
        $_SERVER['HTTP_CF_CONNECTING_IP'] ?? null,
        $_SERVER['HTTP_X_REAL_IP'] ?? null,
        $_SERVER['HTTP_X_FORWARDED_FOR'] ?? null,
    ];

    foreach ($forwardedCandidates as $candidate) {
        $ip = first_valid_ip_from_header($candidate);
        if ($ip !== null) {
            return $ip;
        }
    }

    if ($remoteAddr !== '' && filter_var($remoteAddr, FILTER_VALIDATE_IP)) {
        return $remoteAddr;
    }

    return 'ip-inconnue';
}

function load_client_label(): array
{
    $configFile = dirname(__DIR__) . '/privatedata/client-config.php';
    $fallback = [
        'client_id' => 'client-inconnu',
        'client_name' => 'Client inconnu'
    ];

    if (!is_file($configFile)) {
        return $fallback;
    }

    $config = require $configFile;
    if (!is_array($config)) {
        return $fallback;
    }

    $clientId = preg_replace('/[^a-zA-Z0-9-]/', '', (string) ($config['client_id'] ?? 'client-inconnu'));

    return [
        'client_id' => $clientId !== '' ? $clientId : 'client-inconnu',
        'client_name' => trim((string) ($config['client_name'] ?? 'Client inconnu')) ?: 'Client inconnu'
    ];
}

$raw = file_get_contents('php://input');
$data = json_decode($raw ?: '', true);
if (!is_array($data)) {
    $data = [];
}

$clientInfo = load_client_label();
$client = $clientInfo['client_id'];
$ip = resolve_tracked_ip();
$action = safe_substr((string) ($data['action'] ?? 'inconnue'), 80);
$details = safe_substr((string) ($data['details'] ?? ''), 2000);
$page = safe_substr((string) ($data['page'] ?? ''), 255);
$sessionDir = __DIR__ . '/sessions';
$statsFile = __DIR__ . '/stats.csv';
$errors = [];

if (!ensure_directory($sessionDir)) {
    $errors[] = 'sessions_unavailable';
} else {
    $sessionFile = $sessionDir . '/' . $client . '.txt';
    $sessionLine = date('Y-m-d H:i:s') . ' | client=' . $client . ' | ip=' . $ip;
    if (file_put_contents($sessionFile, $sessionLine, LOCK_EX) === false) {
        $errors[] = 'session_write_failed';
    }

    $ipSafe = preg_replace('/[^a-zA-Z0-9\.\:\-]/', '_', $ip);
    $ipLogFile = $sessionDir . '/ip-' . $ipSafe . '.txt';
    $ipLogLine = date('Y-m-d H:i:s') . ' | client=' . $client . ' | ip=' . $ip . PHP_EOL;
    if (file_put_contents($ipLogFile, $ipLogLine, FILE_APPEND | LOCK_EX) === false) {
        $errors[] = 'ip_log_write_failed';
    }
}

if (!is_file($statsFile)) {
    $header = "\xEF\xBB\xBF\"date\";\"heure\";\"client\";\"action\";\"details\";\"page\";\"ip\"\n";
    if (file_put_contents($statsFile, $header, LOCK_EX) === false) {
        $errors[] = 'stats_init_failed';
    }
}

$line = sprintf(
    '"%s";"%s";"%s";"%s";"%s";"%s";"%s"' . PHP_EOL,
    date('Y-m-d'),
    date('H:i:s'),
    clean_csv($client),
    clean_csv($action),
    clean_csv($details),
    clean_csv($page),
    clean_csv($ip)
);

if (file_put_contents($statsFile, $line, FILE_APPEND | LOCK_EX) === false) {
    $errors[] = 'stats_write_failed';
}

echo json_encode([
    'status' => $errors ? 'partial' : 'success',
    'client' => $clientInfo['client_name'],
    'trackedIp' => $ip,
    'errors' => $errors
], JSON_UNESCAPED_UNICODE | JSON_UNESCAPED_SLASHES);
