<?php
namespace App\Controllers;

require_once BASE_PATH . '/app/helpers/permissions.php';

require_once BASE_PATH . '/app/helpers/conference_scope.php';

use App\Core\Database;
use App\Services\TrackChairScope;

class AdminReviewerController
{
    private function startSession(): void
    {
        if (session_status() !== PHP_SESSION_ACTIVE) {
            session_start();
        }
    }

    private function requireAdmin(): void
    {
        $this->startSession();

        if (empty($_SESSION['user_id'])) {
            header("Location: /easychair/login");
            exit;
        }

        $role = $_SESSION['conference_role'] ?? $_SESSION['role'] ?? $_SESSION['user_role'] ?? '';

        $allowed = [
            'superadmin',
            'conference_chair',
            'track_chair',
            'org_admin',
            'admin'
        ];

        if (!in_array($role, $allowed, true)) {
            http_response_code(403);
            exit("Access denied.");
        }
    }

    private function currentConferenceId(): int
    {
        return (int)($_SESSION['conference_id'] ?? $_SESSION['current_conference_id'] ?? 0);
    }

    private function currentOrgId(): int
    {
        return (int)($_SESSION['org_id'] ?? 0);
    }

    private function isSuperAdmin(): bool
    {
        return (($_SESSION['role'] ?? $_SESSION['user_role'] ?? '') === 'superadmin');
    }

    private function selectedConference(): ?array
    {
        $conferenceId = $this->currentConferenceId();

        if ($conferenceId <= 0) {
            return null;
        }

        $db = Database::getInstance();

        $stmt = $db->prepare("
            SELECT id, org_id, title_ar, title_en, short_name, status
            FROM conferences
            WHERE id = ?
            LIMIT 1
        ");
        $stmt->execute([$conferenceId]);

        $conference = $stmt->fetch(\PDO::FETCH_ASSOC);

        if (!$conference) {
            http_response_code(404);
            exit("Conference not found.");
        }

        if (!$this->isSuperAdmin()) {
            $sessionOrgId = $this->currentOrgId();

            if ($sessionOrgId > 0 && (int)$conference['org_id'] !== $sessionOrgId) {
                http_response_code(403);
                exit("Conference does not belong to your organization.");
            }
        }

        return $conference;
    }

    public function index()
    {
$this->requireAdmin();

        $db = Database::getInstance();
        $conference = $this->selectedConference();

        $reviewers = [];
        $needsConferenceSelection = false;

        $pageData = [
            'conference' => $conference,
            'total_reviewers' => 0,
            'mapped_reviewers' => 0,
            'assignment_only_reviewers' => 0,
        ];

        if (!$conference) {
            $needsConferenceSelection = true;

            ob_start();
            require BASE_PATH . '/app/views/admin/reviewers/index.php';
            $content = ob_get_clean();

            require BASE_PATH . '/app/views/layouts/admin_layout.php';
            return;
        }

        $conferenceId = (int)$conference['id'];

error_log(
    'REVIEWER_PAGE_CONF=' .
    $conferenceId .
    ' SESSION_CONF=' .
    ($_SESSION['conference_id'] ?? 'NULL')
);


        $trackIds =
            TrackChairScope::trackIds();

        $isTrackChair =
            TrackChairScope::isTrackChair();

        error_log(
            'TRACK CHAIR DEBUG ' .
            json_encode([
                'role'=>($_SESSION['role']??null),
                'conference_role'=>($_SESSION['conference_role']??null),
                'user_id'=>($_SESSION['user_id']??null),
                'isTrackChair'=>$isTrackChair,
                'trackIds'=>$trackIds
            ])
        );

        /*
         * Correct schema:
         * users has no conference_id.
         * Reviewer membership is users -> user_conferences -> roles.
         * Fallback includes reviewers already assigned in review_assignments.
         */
        $stmt = $db->prepare("
            SELECT
                u.id,
                u.first_name,
                u.last_name,
                u.email,
                u.mobile,
                u.job_title,
                u.expertise,
                u.reviewer_score,
                u.is_active,
                'conference_role' AS source_type,
                COALESCE(stats.assigned_count, 0) AS assigned_count,
                COALESCE(stats.completed_count, 0) AS completed_count,
                COALESCE(stats.pending_count, 0) AS pending_count
            FROM user_conferences uc
            INNER JOIN roles r ON r.id = uc.role_id
            INNER JOIN users u ON u.id = uc.user_id
            LEFT JOIN (
                SELECT
                    reviewer_id,
                    COUNT(*) AS assigned_count,
                    SUM(CASE WHEN status='completed' THEN 1 ELSE 0 END) AS completed_count,
                    SUM(CASE WHEN status IN ('assigned','accepted','overdue') THEN 1 ELSE 0 END) AS pending_count
                FROM review_assignments
                WHERE conference_id = ?
                GROUP BY reviewer_id
            ) stats ON stats.reviewer_id = u.id
            WHERE uc.conference_id = ?
              AND r.code = 'reviewer'
              AND u.is_active = 1

            UNION ALL

            SELECT
                u.id,
                u.first_name,
                u.last_name,
                u.email,
                u.mobile,
                u.job_title,
                u.expertise,
                u.reviewer_score,
                u.is_active,
                'assignment_only' AS source_type,
                COALESCE(stats.assigned_count, 0) AS assigned_count,
                COALESCE(stats.completed_count, 0) AS completed_count,
                COALESCE(stats.pending_count, 0) AS pending_count
            FROM review_assignments ra
            INNER JOIN users u ON u.id = ra.reviewer_id
            LEFT JOIN (
                SELECT
                    reviewer_id,
                    COUNT(*) AS assigned_count,
                    SUM(CASE WHEN status='completed' THEN 1 ELSE 0 END) AS completed_count,
                    SUM(CASE WHEN status IN ('assigned','accepted','overdue') THEN 1 ELSE 0 END) AS pending_count
                FROM review_assignments
                WHERE conference_id = ?
                GROUP BY reviewer_id
            ) stats ON stats.reviewer_id = u.id
            WHERE ra.conference_id = ?
              AND u.is_active = 1
            ORDER BY last_name ASC, first_name ASC, email ASC
        ");

        $stmt->execute([
            $conferenceId,
            $conferenceId,
            $conferenceId,
            $conferenceId
        ]);

        $raw = $stmt->fetchAll(\PDO::FETCH_ASSOC);
        $dedup = [];

        foreach ($raw as $r) {
            $id = (int)$r['id'];

            if (!isset($dedup[$id])) {
                $dedup[$id] = $r;
                $dedup[$id]['source_label'] = $r['source_type'];
            } else {
                if ($dedup[$id]['source_label'] !== $r['source_type']) {
                    $dedup[$id]['source_label'] .= ' + ' . $r['source_type'];
                }

                $dedup[$id]['assigned_count'] = max((int)$dedup[$id]['assigned_count'], (int)$r['assigned_count']);
                $dedup[$id]['completed_count'] = max((int)$dedup[$id]['completed_count'], (int)$r['completed_count']);
                $dedup[$id]['pending_count'] = max((int)$dedup[$id]['pending_count'], (int)$r['pending_count']);
            }
        }

        $reviewers = array_values($dedup);

        if (
            $isTrackChair
            &&
            !empty($trackIds)
        ) {

            $allowed = [];

            $ph =
                implode(
                    ',',
                    array_fill(
                        0,
                        count($trackIds),
                        '?'
                    )
                );

            $sql = "
                SELECT DISTINCT
                    ra.reviewer_id
                FROM review_assignments ra
                INNER JOIN submissions s
                    ON s.id = ra.submission_id
                WHERE s.track_id IN ($ph)
            ";

            $st = $db->prepare($sql);

            $st->execute($trackIds);

            $allowed =
                array_map(
                    'intval',
                    $st->fetchAll(
                        \PDO::FETCH_COLUMN
                    )
                );

            $reviewers =
                array_values(
                    array_filter(
                        $reviewers,
                        function($r) use ($allowed)
                        {
                            return in_array(
                                (int)$r['id'],
                                $allowed,
                                true
                            );
                        }
                    )
                );
        }

        foreach ($reviewers as $r) {
            $pageData['total_reviewers']++;

            $source = (string)($r['source_label'] ?? '');

            if (strpos($source, 'conference_role') !== false) {
                $pageData['mapped_reviewers']++;
            }

            if ($source === 'assignment_only') {
                $pageData['assignment_only_reviewers']++;
            }
        }

        ob_start();
        require BASE_PATH . '/app/views/admin/reviewers/index.php';
        $content = ob_get_clean();

        require BASE_PATH . '/app/views/layouts/admin_layout.php';
    }
}
