<?php
// ============================================
// SEN RDV SANTÉ+ — Confirmation / Actions gérant sur un RDV
// POST /api/rdv/confirmer.php
// Headers: Authorization: Bearer {token}
// Body: {
//   "rdv_id": 1,
//   "action": "confirmer"        → confirme le RDV en attente
//           | "proposer_report"  → propose un autre créneau
//           | "appeler"          → passe statut_file = 'en_cours'
//           | "suivant"          → termine en_cours + notifie suivant
//           | "absent"           → remet le patient en fin de file + notifie
//           | "toggle_urgent"    → active/désactive le statut urgent
//   "date_proposee": "2025-03-21",  // uniquement si proposer_report
//   "heure_proposee": "10:00"       // uniquement si proposer_report
// }
// ============================================

require_once '../config/helpers.php';
require_once '../config/database.php';
require_once '../config/push.php';

if ($_SERVER['REQUEST_METHOD'] !== 'POST') {
    repondre(['erreur' => 'Méthode non autorisée'], 405);
}

$userConnecte = verifierToken();

if (!in_array($userConnecte['role'], ['gerant', 'admin_hopital'])) {
    repondre(['erreur' => 'Accès réservé au gérant de service'], 403);
}

$body = getBody();
validerChamps($body, ['rdv_id', 'action']);

$db = getDB();

$stmt = $db->prepare("
    SELECT r.*, s.nom AS service_nom, s.hopital_id,
           u.telephone AS patient_telephone, u.nom AS patient_nom_compte,
           u.push_token AS patient_push_token
    FROM rendez_vous r
    JOIN services s ON s.id = r.service_id
    JOIN utilisateurs u ON u.id = r.patient_id
    WHERE r.id = ?
");
$stmt->execute([$body['rdv_id']]);
$rdv = $stmt->fetch();

if (!$rdv) {
    repondre(['erreur' => 'Rendez-vous introuvable'], 404);
}

if ($userConnecte['role'] === 'gerant') {
    $serviceIds = $userConnecte['service_ids'] ?? [];
    if (!in_array($rdv['service_id'], $serviceIds)) {
        repondre(['erreur' => 'Ce rendez-vous n\'appartient pas à votre service'], 403);
    }
}

// ============================================================
// ACTION : toggle_urgent
// ============================================================
if ($body['action'] === 'toggle_urgent') {

    $nouvelEtat = $rdv['urgent'] ? 0 : 1;

    $db->prepare("UPDATE rendez_vous SET urgent = ? WHERE id = ?")
       ->execute([$nouvelEtat, $rdv['id']]);

    $db->prepare("
        INSERT INTO audit_log (utilisateur_id, action, table_cible, enregistrement_id, details)
        VALUES (?, 'toggle_urgent', 'rendez_vous', ?, ?)
    ")->execute([
        $userConnecte['utilisateur_id'], $rdv['id'],
        json_encode(['urgent' => $nouvelEtat, 'patient' => $rdv['patient_prenom'] . ' ' . $rdv['patient_nom']]),
    ]);

    repondre([
        'succes'  => true,
        'message' => $nouvelEtat ? '🔴 Patient marqué comme urgent' : 'Patient retiré des urgences',
        'urgent'  => (bool) $nouvelEtat,
        'rdv_id'  => $rdv['id'],
    ]);
}

// ============================================================
// ACTION : appeler
// ============================================================
if ($body['action'] === 'appeler') {

    if ($rdv['statut'] !== 'paye') {
        repondre(['erreur' => 'Seul un patient ayant payé peut être appelé en consultation'], 409);
    }
    if ($rdv['statut_file'] === 'en_cours') {
        repondre(['erreur' => 'Ce patient est déjà en cours de consultation'], 409);
    }

    $db->prepare("UPDATE rendez_vous SET statut_file = 'en_cours' WHERE id = ?")
       ->execute([$rdv['id']]);

    if (!empty($rdv['patient_push_token'])) {
        envoyerNotificationPush(
            $rdv['patient_id'],
            '🔔 C\'est votre tour !',
            'Veuillez vous présenter à l\'accueil — ' . $rdv['service_nom'] . '.',
            [
                'type'       => 'appel_consultation',
                'rdv_id'     => (int)$rdv['id'],
                'hopital_id' => (int)$rdv['hopital_id'],
            ]
        );
    }

    $db->prepare("
        INSERT INTO notifications (utilisateur_id, rdv_id, type, canal, message)
        VALUES (?, ?, 'appel_consultation', 'push', ?)
    ")->execute([
        $rdv['patient_id'], $rdv['id'],
        'C\'est votre tour ! Présentez-vous à l\'accueil — ' . $rdv['service_nom'] . '.',
    ]);

    $db->prepare("
        INSERT INTO audit_log (utilisateur_id, action, table_cible, enregistrement_id, details)
        VALUES (?, 'appeler_patient', 'rendez_vous', ?, ?)
    ")->execute([
        $userConnecte['utilisateur_id'], $rdv['id'],
        json_encode(['numero_file' => $rdv['numero_file'], 'service' => $rdv['service_nom']]),
    ]);

    repondre([
        'succes'  => true,
        'message' => 'Patient appelé en consultation',
        'rdv_id'  => $rdv['id'],
        'patient' => [
            'nom'         => $rdv['patient_nom'],
            'prenom'      => $rdv['patient_prenom'],
            'numero_file' => $rdv['numero_file'],
        ],
    ]);
}

// ============================================================
// ACTION : absent
// ============================================================
if ($body['action'] === 'absent') {

    if ($rdv['statut_file'] !== 'en_cours') {
        repondre(['erreur' => 'Ce patient n\'est pas en cours d\'appel'], 409);
    }

    $stmtMax = $db->prepare("
        SELECT MAX(numero_file) AS max_file
        FROM rendez_vous
        WHERE service_id = ?
          AND date_rdv   = ?
          AND statut NOT IN ('annule', 'expire', 'consomme')
    ");
    $stmtMax->execute([$rdv['service_id'], $rdv['date_rdv']]);
    $maxFile         = (int)($stmtMax->fetch(PDO::FETCH_ASSOC)['max_file'] ?? 0);
    $nouveauNumero   = $maxFile + 1;
    $ancienNumero    = (int)$rdv['numero_file'];

    $db->prepare("
        UPDATE rendez_vous
        SET statut_file = 'en_attente', numero_file = ?
        WHERE id = ?
    ")->execute([$nouveauNumero, $rdv['id']]);

    if (!empty($rdv['patient_push_token'])) {
        envoyerNotificationPush(
            $rdv['patient_id'],
            '⏳ Remis en file d\'attente',
            'Vous n\'étiez pas présent lors de l\'appel. Vous avez été remis en fin de file — N°' . $nouveauNumero . '.',
            [
                'type'       => 'remise_file',
                'rdv_id'     => (int)$rdv['id'],
                'hopital_id' => (int)$rdv['hopital_id'],
            ]
        );
    }

    $db->prepare("
        INSERT INTO notifications (utilisateur_id, rdv_id, type, canal, message)
        VALUES (?, ?, 'remise_file', 'push', ?)
    ")->execute([
        $rdv['patient_id'], $rdv['id'],
        'Vous avez été remis en file d\'attente — N°' . $nouveauNumero . ' au ' . $rdv['service_nom'] . '.',
    ]);

    $stmtSuivant = $db->prepare("
        SELECT r.id AS rdv_id, r.patient_id, r.patient_nom, r.patient_prenom,
               r.numero_file, u.push_token
        FROM rendez_vous r
        JOIN utilisateurs u ON u.id = r.patient_id
        WHERE r.service_id = ?
          AND r.date_rdv   = ?
          AND r.numero_file = ?
          AND r.statut NOT IN ('annule', 'expire', 'consomme')
          AND r.id != ?
        LIMIT 1
    ");
    $stmtSuivant->execute([
        $rdv['service_id'],
        $rdv['date_rdv'],
        $ancienNumero + 1,
        $rdv['id'],
    ]);
    $patientSuivant = $stmtSuivant->fetch();

    if ($patientSuivant) {
        $db->prepare("UPDATE rendez_vous SET statut_file = 'en_cours' WHERE id = ?")
           ->execute([$patientSuivant['rdv_id']]);

        if (!empty($patientSuivant['push_token'])) {
            envoyerNotificationPush(
                $patientSuivant['patient_id'],
                '🔔 C\'est votre tour !',
                'Présentez-vous à l\'accueil — ' . $rdv['service_nom'] . '.',
                [
                    'type'       => 'appel_consultation',
                    'rdv_id'     => (int)$patientSuivant['rdv_id'],
                    'hopital_id' => (int)$rdv['hopital_id'],
                ]
            );
        }

        $db->prepare("
            INSERT INTO notifications (utilisateur_id, rdv_id, type, canal, message)
            VALUES (?, ?, 'appel_consultation', 'push', ?)
        ")->execute([
            $patientSuivant['patient_id'], $patientSuivant['rdv_id'],
            'C\'est votre tour ! Présentez-vous à l\'accueil — ' . $rdv['service_nom'] . '.',
        ]);
    }

    $db->prepare("
        INSERT INTO audit_log (utilisateur_id, action, table_cible, enregistrement_id, details)
        VALUES (?, 'patient_absent', 'rendez_vous', ?, ?)
    ")->execute([
        $userConnecte['utilisateur_id'], $rdv['id'],
        json_encode([
            'ancien_numero'  => $ancienNumero,
            'nouveau_numero' => $nouveauNumero,
            'service'        => $rdv['service_nom'],
        ]),
    ]);

    repondre([
        'succes'          => true,
        'message'         => 'Patient remis en fin de file (N°' . $nouveauNumero . ')',
        'nouveau_numero'  => $nouveauNumero,
        'suivant'         => $patientSuivant ? [
            'rdv_id'      => $patientSuivant['rdv_id'],
            'nom'         => $patientSuivant['patient_nom'],
            'prenom'      => $patientSuivant['patient_prenom'],
            'numero_file' => $patientSuivant['numero_file'],
        ] : null,
    ]);
}

// ============================================================
// ACTION : suivant
// ============================================================
if ($body['action'] === 'suivant') {

    if ($rdv['statut_file'] !== 'en_cours') {
        repondre(['erreur' => 'Ce patient n\'est pas en cours de consultation'], 409);
    }

    $db->prepare("
        UPDATE rendez_vous SET statut_file = 'termine', statut = 'consomme' WHERE id = ?
    ")->execute([$rdv['id']]);

    $numeroActuel = (int)$rdv['numero_file'];

    $stmtSuivant = $db->prepare("
        SELECT r.id AS rdv_id, r.patient_id, r.patient_nom, r.patient_prenom,
               r.numero_file, u.push_token
        FROM rendez_vous r
        JOIN utilisateurs u ON u.id = r.patient_id
        WHERE r.service_id  = ?
          AND r.date_rdv    = ?
          AND r.numero_file = ?
          AND r.statut NOT IN ('annule', 'expire', 'consomme')
        LIMIT 1
    ");
    $stmtSuivant->execute([$rdv['service_id'], $rdv['date_rdv'], $numeroActuel + 1]);
    $patientSuivant = $stmtSuivant->fetch();

    $suivantNotifie = false;

    if ($patientSuivant) {
        $db->prepare("UPDATE rendez_vous SET statut_file = 'en_cours' WHERE id = ?")
           ->execute([$patientSuivant['rdv_id']]);

        if (!empty($patientSuivant['push_token'])) {
            envoyerNotificationPush(
                $patientSuivant['patient_id'],
                '🔔 C\'est votre tour !',
                'Présentez-vous à l\'accueil — ' . $rdv['service_nom'] . '.',
                [
                    'type'       => 'appel_consultation',
                    'rdv_id'     => (int)$patientSuivant['rdv_id'],
                    'hopital_id' => (int)$rdv['hopital_id'],
                ]
            );
        }

        $db->prepare("
            INSERT INTO notifications (utilisateur_id, rdv_id, type, canal, message)
            VALUES (?, ?, 'file_suivant', 'push', ?)
        ")->execute([
            $patientSuivant['patient_id'], $patientSuivant['rdv_id'],
            'C\'est votre tour ! Présentez-vous à l\'accueil — ' . $rdv['service_nom'] . '.',
        ]);

        $suivantNotifie = true;
    }

    $db->prepare("
        INSERT INTO audit_log (utilisateur_id, action, table_cible, enregistrement_id, details)
        VALUES (?, 'passer_suivant', 'rendez_vous', ?, ?)
    ")->execute([
        $userConnecte['utilisateur_id'], $rdv['id'],
        json_encode([
            'numero_termine'  => $numeroActuel,
            'suivant_numero'  => $numeroActuel + 1,
            'suivant_notifie' => $suivantNotifie,
        ]),
    ]);

    repondre([
        'succes'  => true,
        'message' => $suivantNotifie
            ? 'Patient suivant notifié'
            : 'Consultation terminée — plus de patients en attente',
        'termine' => ['rdv_id' => $rdv['id'], 'numero_file' => $numeroActuel],
        'suivant' => $patientSuivant ? [
            'rdv_id'      => $patientSuivant['rdv_id'],
            'nom'         => $patientSuivant['patient_nom'],
            'prenom'      => $patientSuivant['patient_prenom'],
            'numero_file' => $patientSuivant['numero_file'],
        ] : null,
    ]);
}

// ============================================================
// ACTION : confirmer
// ============================================================
if ($body['action'] === 'confirmer') {

    if ($rdv['statut'] !== 'en_attente') {
        repondre(['erreur' => 'Ce rendez-vous n\'est plus en attente de confirmation'], 409);
    }

    $prixReservation = (float) getParametre('prix_reservation', 200);

    $db->prepare("
        UPDATE rendez_vous
        SET statut = 'confirme', confirme_par = ?, confirme_at = NOW()
        WHERE id = ?
    ")->execute([$userConnecte['utilisateur_id'], $rdv['id']]);

    $expireAt = date('Y-m-d H:i:s', strtotime('+3 hours'));

    $db->prepare("
        INSERT INTO paiements (rdv_id, montant, operateur, telephone_paiement, expire_at)
        VALUES (?, ?, 'wave', ?, ?)
    ")->execute([$rdv['id'], $prixReservation, $rdv['patient_telephone'], $expireAt]);

    if (!empty($rdv['patient_push_token'])) {
        envoyerNotificationPush(
            $rdv['patient_id'],
            '✅ RDV Confirmé !',
            'Votre RDV du ' . $rdv['date_rdv'] . ' à ' . substr($rdv['heure_rdv'], 0, 5) .
                ' — ' . $rdv['service_nom'] . '. Payez dans les 3h.',
            [
                'type'       => 'confirmation',
                'rdv_id'     => (int)$rdv['id'],
                'hopital_id' => (int)$rdv['hopital_id'],
            ]
        );
    }

    $db->prepare("
        INSERT INTO notifications (utilisateur_id, rdv_id, type, canal, message)
        VALUES (?, ?, 'confirmation', 'sms', ?)
    ")->execute([
        $rdv['patient_id'], $rdv['id'],
        'SEN RDV SANTÉ+ : Votre RDV du ' . $rdv['date_rdv'] . ' à ' . $rdv['heure_rdv'] .
            ' — ' . $rdv['service_nom'] . ' est confirmé. Payez ' . $prixReservation .
            ' FCFA via Mobile Money. Expire dans 3h.',
    ]);

    $db->prepare("
        INSERT INTO audit_log (utilisateur_id, action, table_cible, enregistrement_id, details)
        VALUES (?, 'confirmer_rdv', 'rendez_vous', ?, ?)
    ")->execute([
        $userConnecte['utilisateur_id'], $rdv['id'],
        json_encode(['service' => $rdv['service_nom'], 'date' => $rdv['date_rdv']]),
    ]);

    repondre([
        'succes'          => true,
        'message'         => 'RDV confirmé, le patient a été notifié pour le paiement',
        'rdv_id'          => $rdv['id'],
        'statut'          => 'confirme',
        'expire_paiement' => $expireAt,
    ]);
}

// ============================================================
// ACTION : proposer_report
// ============================================================
if ($body['action'] === 'proposer_report') {

    if ($rdv['statut'] !== 'en_attente') {
        repondre(['erreur' => 'Ce rendez-vous n\'est plus en attente'], 409);
    }

    validerChamps($body, ['date_proposee', 'heure_proposee']);

    $db->prepare("
        UPDATE rendez_vous SET date_proposee = ?, heure_proposee = ? WHERE id = ?
    ")->execute([$body['date_proposee'], $body['heure_proposee'], $rdv['id']]);

    $db->prepare("
        INSERT INTO notifications (utilisateur_id, rdv_id, type, canal, message)
        VALUES (?, ?, 'report', 'sms', ?)
    ")->execute([
        $rdv['patient_id'], $rdv['id'],
        'SEN RDV SANTÉ+ : Nouveau créneau proposé — ' . $body['date_proposee'] .
            ' à ' . $body['heure_proposee'] . '. Connectez-vous pour accepter ou refuser.',
    ]);

    repondre([
        'succes'         => true,
        'message'        => 'Proposition de report envoyée au patient',
        'date_proposee'  => $body['date_proposee'],
        'heure_proposee' => $body['heure_proposee'],
    ]);
}

repondre(['erreur' => 'Action invalide. Valeurs acceptées : confirmer, proposer_report, appeler, suivant, absent, toggle_urgent'], 422);