<?php

use MintyPHP\Module\Helpdesk\HelpdeskAuthorizationPolicy;
use MintyPHP\Module\Helpdesk\Service\DebitorCacheControl;
use MintyPHP\Module\Helpdesk\Service\DebitorDetailService;
use MintyPHP\Http\SessionStoreInterface;
use MintyPHP\Router;
use MintyPHP\Support\Guard;

Guard::requireLogin();
Guard::requireAbilityOrForbidden(HelpdeskAuthorizationPolicy::ABILITY_ACCESS);

gridRequireGetRequest();

$filters = gridParseFiltersFromSchemaFile(__DIR__ . '/debitor-tickets-filter-schema.php');
$request = requestInput();

$customerNo = (string) ($filters['customerNo'] ?? '');
$customerName = (string) ($filters['customerName'] ?? '');
$refreshRequested = DebitorCacheControl::parseRefreshFlag($request->query('refresh', ''));

if ($customerNo === '' || $customerName === '') {
    Router::json([
        'data' => [],
        'total' => 0,
        'meta' => [
            'cache_used' => false,
            'cache_bypassed' => $refreshRequested,
            'cache_refreshed' => false,
        ],
    ]);

    return;
}

// --- Session cache (lazy TTL = 120s) ---

$sessionStore = app(SessionStoreInterface::class);
$session = $sessionStore->all();
$tenantScope = DebitorCacheControl::resolveTenantScope($session);
if ($refreshRequested) {
    DebitorCacheControl::invalidateDebitorCaches($sessionStore, $tenantScope, $customerNo, true);
}

$cacheKey = DebitorCacheControl::ticketsKey($tenantScope, $customerNo);
$cacheTtl = DebitorCacheControl::TTL_STANDARD_SECONDS;
$cached = $sessionStore->get($cacheKey);
$allTickets = null;
$cacheUsed = false;
$serviceMeta = [
    'source' => 'primary.company_contact_name',
    'fallback_used' => false,
    'fallback_reason' => '',
];

if (!$refreshRequested && is_array($cached) && isset($cached['fetched_at']) && (time() - (int) $cached['fetched_at']) < $cacheTtl) {
    $allTickets = $cached['tickets'] ?? [];
    $cacheUsed = true;
    if (is_array($cached['service_meta'] ?? null)) {
        $serviceMeta = [
            'source' => (string) ($cached['service_meta']['source'] ?? $serviceMeta['source']),
            'fallback_used' => (bool) ($cached['service_meta']['fallback_used'] ?? false),
            'fallback_reason' => (string) ($cached['service_meta']['fallback_reason'] ?? ''),
        ];
    }
}

if ($allTickets === null) {
    $service = app(DebitorDetailService::class);
    $result = $service->loadTickets($customerNo, $customerName);

    if (!($result['ok'] ?? false)) {
        $resultMeta = is_array($result['meta'] ?? null) ? $result['meta'] : [];
        Router::json([
            'data' => [],
            'total' => 0,
            'meta' => [
                'cache_used' => $cacheUsed,
                'cache_bypassed' => $refreshRequested,
                'cache_refreshed' => $refreshRequested,
                'source' => (string) ($resultMeta['source'] ?? $serviceMeta['source']),
                'fallback_used' => (bool) ($resultMeta['fallback_used'] ?? false),
                'fallback_reason' => (string) ($resultMeta['fallback_reason'] ?? ''),
            ],
        ]);

        return;
    }

    $allTickets = $result['tickets'] ?? [];
    $resultMeta = is_array($result['meta'] ?? null) ? $result['meta'] : [];
    $serviceMeta = [
        'source' => (string) ($resultMeta['source'] ?? $serviceMeta['source']),
        'fallback_used' => (bool) ($resultMeta['fallback_used'] ?? false),
        'fallback_reason' => (string) ($resultMeta['fallback_reason'] ?? ''),
    ];

    $sessionStore->set($cacheKey, [
        'tickets' => $allTickets,
        'service_meta' => $serviceMeta,
        'fetched_at' => time(),
    ]);
}

// --- PHP-side filtering ---

$search = trim((string) ($filters['search'] ?? ''));
$status = trim((string) ($filters['status'] ?? ''));
$category = trim((string) ($filters['category'] ?? ''));
$supportUser = trim((string) ($filters['support'] ?? ''));
$contact = trim((string) ($filters['contact'] ?? ''));
$period = trim((string) ($filters['period'] ?? ''));
$order = (string) ($filters['order'] ?? 'Created_On');
$dir = (string) ($filters['dir'] ?? 'desc');
$limit = (int) ($filters['limit'] ?? 10);
$offset = (int) ($filters['offset'] ?? 0);

$filtered = $allTickets;

// Search: stripos on No + Description + Current_Contact_Name + Support_User_Name
if ($search !== '') {
    $searchLower = mb_strtolower($search);
    $filtered = array_values(array_filter($filtered, static function (array $ticket) use ($searchLower): bool {
        $haystack = mb_strtolower(
            ($ticket['No'] ?? '') . ' '
            . ($ticket['Description'] ?? '') . ' '
            . ($ticket['Current_Contact_Name'] ?? '') . ' '
            . ($ticket['Support_User_Name'] ?? '')
        );

        return str_contains($haystack, $searchLower);
    }));
}

// Status filter
if ($status !== '') {
    $statusMap = [
        'open' => ['Offen', 'Open'],
        'in_progress' => ['In Bearbeitung', 'In Progress'],
        'closed' => ['Erledigt', 'Resolved', 'Closed', 'Geschlossen'],
    ];
    $allowedStates = $statusMap[$status] ?? [];
    if ($allowedStates !== []) {
        $filtered = array_values(array_filter($filtered, static function (array $ticket) use ($allowedStates): bool {
            return in_array((string) ($ticket['Ticket_State'] ?? ''), $allowedStates, true);
        }));
    }
}

// Category filter
if ($category !== '') {
    $filtered = array_values(array_filter($filtered, static function (array $ticket) use ($category): bool {
        return trim((string) ($ticket['Category_1_Description'] ?? '')) === $category;
    }));
}

// Support user filter
if ($supportUser !== '') {
    $filtered = array_values(array_filter($filtered, static function (array $ticket) use ($supportUser): bool {
        return trim((string) ($ticket['Support_User_Name'] ?? '')) === $supportUser;
    }));
}

// Contact filter
if ($contact !== '') {
    $filtered = array_values(array_filter($filtered, static function (array $ticket) use ($contact): bool {
        return trim((string) ($ticket['Current_Contact_Name'] ?? '')) === $contact;
    }));
}

// Period filter (days from today)
if ($period !== '' && ctype_digit($period)) {
    $cutoff = (new DateTimeImmutable('now'))->modify('-' . $period . ' days')->format('Y-m-d\TH:i:s\Z');
    $filtered = array_values(array_filter($filtered, static function (array $ticket) use ($cutoff): bool {
        $created = (string) ($ticket['Created_On'] ?? '');
        if ($created === '' || $created === '0001-01-01T00:00:00Z') {
            return false;
        }

        return $created >= $cutoff;
    }));
}

// --- Sorting ---

$total = count($filtered);

usort($filtered, static function (array $a, array $b) use ($order, $dir): int {
    $va = (string) ($a[$order] ?? '');
    $vb = (string) ($b[$order] ?? '');
    $cmp = strnatcasecmp($va, $vb);

    return $dir === 'desc' ? -$cmp : $cmp;
});

// --- Pagination ---

$rows = array_slice($filtered, $offset, $limit);

// --- Row preparation ---

$stateVariantMap = [
    'Offen' => 'warning',
    'Open' => 'warning',
    'In Bearbeitung' => 'warning',
    'In Progress' => 'warning',
    'Erledigt' => 'success',
    'Resolved' => 'success',
    'Closed' => 'success',
    'Geschlossen' => 'success',
];

$ticketBaseUrl = lurl('helpdesk/ticket/');

$preparedRows = [];
foreach ($rows as $ticket) {
    $ticketNo = (string) ($ticket['No'] ?? '');
    $state = (string) ($ticket['Ticket_State'] ?? '');
    $createdRaw = (string) ($ticket['Created_On'] ?? '');
    $lastActivityRaw = (string) ($ticket['Last_Activity_Date'] ?? '');

    $createdFormatted = '';
    if ($createdRaw !== '' && $createdRaw !== '0001-01-01T00:00:00Z') {
        try {
            $createdFormatted = (new DateTimeImmutable($createdRaw))->format('d.m.Y H:i');
        } catch (\Throwable) {
            $createdFormatted = $createdRaw;
        }
    }

    $lastActivityFormatted = '';
    if ($lastActivityRaw !== '' && $lastActivityRaw !== '0001-01-01T00:00:00Z') {
        try {
            $lastActivityFormatted = (new DateTimeImmutable($lastActivityRaw))->format('d.m.Y H:i');
        } catch (\Throwable) {
            $lastActivityFormatted = $lastActivityRaw;
        }
    }

    $preparedRows[] = [
        'No' => $ticketNo,
        'Description' => (string) ($ticket['Description'] ?? ''),
        'Ticket_State' => $state,
        'state_variant' => $stateVariantMap[$state] ?? 'neutral',
        'Category_1_Description' => (string) ($ticket['Category_1_Description'] ?? ''),
        'Support_User_Name' => (string) ($ticket['Support_User_Name'] ?? ''),
        'Current_Contact_Name' => (string) ($ticket['Current_Contact_Name'] ?? ''),
        'Created_On' => $createdRaw,
        'Last_Activity_Date' => $lastActivityRaw,
        'created_formatted' => $createdFormatted,
        'last_activity_formatted' => $lastActivityFormatted,
        'ticket_url' => $ticketBaseUrl . rawurlencode($ticketNo) . '?from=' . rawurlencode($customerNo),
    ];
}

Router::json([
    'data' => $preparedRows,
    'total' => max(0, $total),
    'meta' => [
        'cache_used' => $cacheUsed,
        'cache_bypassed' => $refreshRequested,
        'cache_refreshed' => $refreshRequested,
        'source' => $serviceMeta['source'],
        'fallback_used' => $serviceMeta['fallback_used'],
        'fallback_reason' => $serviceMeta['fallback_reason'],
    ],
]);
