<?php

declare(strict_types=1);

ini_set('display_errors', '0');

header('Content-Type: application/json');

require_once __DIR__ . '/../config/database.php';
require_once __DIR__ . '/../config/config.php';
require_once __DIR__ . '/../ai/form_generator_retry.php';
require_once __DIR__ . '/../ai/generator_batch_context.php';
require_once __DIR__ . '/../ai/combined_tutor_review_diagnostics.php';
require_once __DIR__ . '/../../prompts/sba_combined_tutor_reviewer_prompt.php';
require_once __DIR__ . '/../ai/form_generator_question_validation.php';

/**
 * @return never
 */
function combinedTutorReviewJsonResponse(array $payload, int $httpCode = 200): void
{
    http_response_code($httpCode);
    echo json_encode($payload, JSON_UNESCAPED_UNICODE);
    exit;
}

$questionId = trim((string) ($_POST['question_id'] ?? ''));

if ($questionId === '') {
    $failure = combinedTutorReviewFailureFromClientDetail('Missing question ID.', $questionId);
    combinedTutorReviewJsonResponse(combinedTutorReviewErrorJsonPayload($failure, 400), 400);
}

$sql = 'SELECT * FROM questions WHERE id = :question_id LIMIT 1';
$stmt = $pdo->prepare($sql);
$stmt->execute(['question_id' => $questionId]);
$question = $stmt->fetch(PDO::FETCH_ASSOC);

if (!$question) {
    $failure = combinedTutorReviewFailureFromClientDetail('Question not found.', $questionId);
    combinedTutorReviewJsonResponse(combinedTutorReviewErrorJsonPayload($failure, 404), 404);
}

if (($question['source_type'] ?? '') !== 'generated') {
    $failure = combinedTutorReviewFailureFromClientDetail(
        'Review is only available for generated SBA questions.',
        $questionId
    );
    combinedTutorReviewJsonResponse(combinedTutorReviewErrorJsonPayload($failure, 400), 400);
}

$question = formGeneratorApplyStyleRepairToQuestionRow($question);

$styleWarnings = [];
$warningsRaw = $_POST['style_warnings'] ?? '';
if (is_string($warningsRaw) && $warningsRaw !== '') {
    $decoded = json_decode($warningsRaw, true);
    if (is_array($decoded)) {
        $styleWarnings = $decoded;
    }
}

if ($styleWarnings === []) {
    $validatorPath = __DIR__ . '/../../validators/style_validator.php';
    if (is_readable($validatorPath)) {
        require_once $validatorPath;
        if (function_exists('validateSbaStyle')) {
            $qStyle = $question;
            $qStyle['_tutor_comments'] = (string) ($question['tutor_comments'] ?? '');
            $qStyle['_current_skill'] = (string) ($question['skill'] ?? '');
            $qStyle['_condition_name'] = (string) ($question['condition_name'] ?? '');
            $batchJobId = generatorParseBatchJobIdFromTags((string) ($question['tags'] ?? ''));
            $qStyle['_batch_prior_questions'] = [];
            if ($batchJobId > 0 && ($question['workspace_id'] ?? '') !== '') {
                $priors = fetchFormGeneratorPriorQuestionsInBatch(
                    $pdo,
                    (string) $question['workspace_id'],
                    $batchJobId
                );
                $qStyle['_batch_prior_questions'] = array_values(array_filter(
                    $priors,
                    static fn ($row) => is_array($row)
                ));
            }
            try {
                $validated = validateSbaStyle($qStyle);
                $styleWarnings = is_array($validated) ? $validated : [];
            } catch (Throwable $e) {
                $styleWarnings = [];
            }
        }
    }
}

$batchSiblings = [];
$batchJobId = generatorParseBatchJobIdFromTags((string) ($question['tags'] ?? ''));
if ($batchJobId > 0 && ($question['workspace_id'] ?? '') !== '') {
    $priors = fetchFormGeneratorPriorQuestionsInBatch(
        $pdo,
        (string) $question['workspace_id'],
        $batchJobId
    );
    foreach ($priors as $row) {
        if (!is_array($row)) {
            continue;
        }
        $batchSiblings[] = [
            'skill' => $row['skill'] ?? '',
            'correct_answer' => $row['correct_answer'] ?? '',
            'lead_in' => $row['lead_in'] ?? '',
            'title' => $row['title'] ?? '',
        ];
    }
}

try {
    $prompt = buildSbaCombinedTutorReviewerPrompt($question, $styleWarnings, $batchSiblings);
    $promptChars = strlen($prompt);
    $fetch = formGeneratorOpenAiChatJsonQuestion(
        $prompt,
        '',
        0,
        0.35,
        formGeneratorOpenAiSbaReviewModel()
    );

    if (!$fetch['ok'] || !is_array($fetch['data'])) {
        $failure = combinedTutorReviewFailureFromOpenAiFetch($fetch, $questionId);
        if (!empty($fetch['raw'])) {
            combinedTutorReviewLogFailure($questionId, $failure['error_code'], 'raw_response_excerpt', [
                'phase' => 'openai_raw',
                'prompt_chars' => $promptChars,
                'raw_excerpt' => mb_substr((string) $fetch['raw'], 0, 4000),
            ]);
        } else {
            combinedTutorReviewLogFailure($questionId, $failure['error_code'], $failure['detail'], [
                'phase' => 'openai',
                'prompt_chars' => $promptChars,
            ]);
        }
        combinedTutorReviewJsonResponse(combinedTutorReviewErrorJsonPayload($failure, 502), 502);
    }

    $normalized = normalizeSbaCombinedTutorReviewResponse($fetch['data'], $question);
    if (!$normalized['ok'] || !is_array($normalized['data'])) {
        $rawLen = is_string($fetch['raw'] ?? null) ? strlen((string) $fetch['raw']) : 0;
        $failure = combinedTutorReviewFailureFromNormalize(
            (string) ($normalized['error'] ?? ''),
            $questionId,
            $rawLen
        );
        combinedTutorReviewLogFailure($questionId, $failure['error_code'], $failure['detail'], [
            'phase' => 'normalize',
            'prompt_chars' => $promptChars,
            'raw_excerpt' => mb_substr((string) ($fetch['raw'] ?? ''), 0, 8000),
        ]);
        combinedTutorReviewJsonResponse(combinedTutorReviewErrorJsonPayload($failure, 502), 502);
    }

    combinedTutorReviewJsonResponse([
        'ok' => true,
        'error' => '',
        'error_code' => '',
        'tutor_message' => '',
        'detail' => '',
        'review' => $normalized['data'],
        'reviewed_at' => gmdate('c'),
        'status' => 'success',
        'message' => 'Review complete.',
    ]);
} catch (Throwable $e) {
    $failure = combinedTutorReviewFailureFromException($e, $questionId);
    combinedTutorReviewJsonResponse(combinedTutorReviewErrorJsonPayload($failure, 500), 500);
}
