<?php

require_once __DIR__ . '/../../core/bootstrap.php';
require_once __DIR__ . '/../../core/status_engine.php';
require_once __DIR__ . '/../../core/penalty.php';

/* ----------------------------------------------------------
   METHOD CHECK
---------------------------------------------------------- */

if ($_SERVER['REQUEST_METHOD'] !== 'POST') {
    json_response(false, 'Invalid request method.', [], 405);
}

/* ----------------------------------------------------------
   AUTH
---------------------------------------------------------- */

$user = authenticate($pdo);

if (!in_array($user['role'], ['sp_admin', 'artisan'], true)) {
    json_response(false, 'Access denied. SP role required.', [], 403);
}

$sp_company_id = (int)$user['company_id'];
$rsp_id        = (int)$user['rsp_id'];

if (!$sp_company_id) {
    json_response(false, 'Service provider not linked.', [], 403);
}

/* ----------------------------------------------------------
   INPUT VALIDATION
---------------------------------------------------------- */

$input = json_decode(file_get_contents('php://input'), true);

if (!is_array($input) || empty($input['breakdown_id'])) {
    json_response(false, 'Breakdown ID required.', [], 400);
}

$breakdown_id = (int)$input['breakdown_id'];

/* ----------------------------------------------------------
   TRANSACTION
---------------------------------------------------------- */

$pdo->beginTransaction();

try {

    /* ------------------------------------------------------
       FETCH BREAKDOWN
    ------------------------------------------------------ */

    $stmt = $pdo->prepare("
        SELECT
            b.id,
            b.status,
            b.accepted_company_id,
            b.broadcast_expires_at,
            f.rsp_id
        FROM breakdowns b
        JOIN companies f ON f.id = b.fleet_company_id
        WHERE b.id = ?
        LIMIT 1
    ");

    $stmt->execute([$breakdown_id]);
    $breakdown = $stmt->fetch(PDO::FETCH_ASSOC);

    if (!$breakdown) {
        $pdo->rollBack();
        json_response(false, 'Breakdown not found.', [], 404);
    }

    /* RSP isolation */

    if ((int)$breakdown['rsp_id'] !== $rsp_id) {
        $pdo->rollBack();
        json_response(false, 'Access denied.', [], 403);
    }

    /* Broadcast expiry check */

    if (strtotime($breakdown['broadcast_expires_at']) < time()) {
        $pdo->rollBack();
        json_response(false, 'Broadcast has already expired.', [], 409);
    }

    /* Must belong to this SP */

    if ((int)$breakdown['accepted_company_id'] !== $sp_company_id) {
        $pdo->rollBack();
        json_response(false, 'Job not assigned to your company.', [], 403);
    }

    /* Allowed cancellation stages */

    if (!in_array($breakdown['status'], ['accepted', 'allocated', 'enroute'], true)) {
        $pdo->rollBack();
        json_response(false, 'Job cannot be cancelled at this stage.', [], 409);
    }

    /* ------------------------------------------------------
       CANCEL & RE-BROADCAST
    ------------------------------------------------------ */

    $stmt = $pdo->prepare("
        UPDATE breakdowns
        SET
            status = 'broadcasting',
            accepted_company_id = NULL,
            accepted_at = NULL,
            allocated_artisan_id = NULL,
            allocated_at = NULL,
            started_at = NULL,
            last_broadcast_at = NOW()
        WHERE id = ?
    ");

    $stmt->execute([$breakdown_id]);

    /* ------------------------------------------------------
       PENALTY
    ------------------------------------------------------ */

    apply_penalty(
        $pdo,
        $sp_company_id,
        $breakdown_id,
        'Cancelled after accept',
        1
    );

    $pdo->commit();

    json_response(true, 'Job cancelled and re-broadcasted.', [
        'breakdown_id' => $breakdown_id,
        'status'       => 'broadcasting'
    ]);

} catch (Throwable $e) {

    $pdo->rollBack();

    json_response(false, 'Failed to cancel job.', [], 500);
}