'use client';
import React, {useEffect, useState} from 'react';
import Link from 'next/link';
import {useTranslations} from 'next-intl';
import {Alert} from 'react-bootstrap';
import {useAuth} from '@/contexts/AuthContext';
import ContactModal from '@/components/community/ContactModal';
import CarpoolForm, {SAISIE_VIDE, type CarpoolSaisie} from '@/components/community/carpool/CarpoolForm';
import CarpoolItem from '@/components/community/carpool/CarpoolItem';
import {deleteCarpool, getCarpoolsAVenir, sendCarpoolContactMessage, updateCarpool, type Carpool, type CarpoolEvenement} from '@/services/covoiturageService';
import {evenementHref} from '@/utils/evenementHref';

interface CovoituragesBoardProps {
  locale: string;
}

interface GroupeEvenement {
  evenement: CarpoolEvenement | null;
  carpools: Carpool[];
}

/** Regroupe les covoiturages par événement en gardant l'ordre de l'API (événement le plus proche d'abord). */
function grouperParEvenement(carpools: Carpool[]): GroupeEvenement[] {
  const groupes = new Map<number | 'sans', GroupeEvenement>();
  for (const carpool of carpools) {
    const cle = carpool.evenement?.eveId ?? 'sans';
    const groupe = groupes.get(cle) ?? {evenement: carpool.evenement ?? null, carpools: []};
    groupe.carpools.push(carpool);
    groupes.set(cle, groupe);
  }
  return Array.from(groupes.values());
}

/**
 * Page covoiturage (spec L194, L195, L199, L200) : annonces des événements à venir groupées par
 * événement ; le membre connecté répond (contact) ou corrige / supprime les siennes ; le visiteur
 * est invité à se connecter.
 */
export default function CovoituragesBoard({locale}: CovoituragesBoardProps) {
  const t = useTranslations('Carpool');
  const {isAuthenticated, user} = useAuth();
  const [carpools, setCarpools] = useState<Carpool[]>([]);
  const [chargement, setChargement] = useState(true);
  const [erreur, setErreur] = useState<'error_load' | 'error_update' | 'error_delete' | null>(null);
  const [enEdition, setEnEdition] = useState<Carpool | null>(null);
  const [saisie, setSaisie] = useState<CarpoolSaisie>(SAISIE_VIDE);
  const [enregistrement, setEnregistrement] = useState(false);
  const [contact, setContact] = useState<Carpool | null>(null);

  useEffect(() => {
    getCarpoolsAVenir()
      .then(setCarpools)
      .catch(() => setErreur('error_load'))
      .finally(() => setChargement(false));
  }, []);

  const estAuteur = (carpool: Carpool) => isAuthenticated && !!user?.username && user.username === carpool.auteur?.pseudo;

  const commencerEdition = (carpool: Carpool) => {
    setEnEdition(carpool);
    setSaisie({ville: carpool.ville, nombre: carpool.nombre, heure: carpool.heure ?? '', propose: carpool.propose});
  };

  const annulerEdition = () => {
    setEnEdition(null);
    setSaisie(SAISIE_VIDE);
  };

  const enregistrer = async (event: React.FormEvent) => {
    event.preventDefault();
    if (!enEdition || !saisie.ville.trim()) return;
    setEnregistrement(true);
    setErreur(null);
    try {
      const corrige = await updateCarpool(enEdition.id, {
        ville: saisie.ville.trim(),
        nombre: saisie.nombre,
        heure: saisie.heure || null,
        propose: saisie.propose,
      });
      setCarpools((liste) => liste.map((c) => (c.id === corrige.id ? {...c, ...corrige} : c)));
      annulerEdition();
    } catch {
      setErreur('error_update');
    } finally {
      setEnregistrement(false);
    }
  };

  const supprimer = async (id: number) => {
    if (!confirm(t('delete_confirm'))) return;
    try {
      await deleteCarpool(id);
      setCarpools((liste) => liste.filter((c) => c.id !== id));
    } catch {
      setErreur('error_delete');
    }
  };

  const formatDate = (date: string | null) =>
    date ? new Date(date).toLocaleDateString(locale, {weekday: 'long', day: 'numeric', month: 'long', year: 'numeric'}) : '';

  return (
    <div className="tk-covoiturages" data-testid="covoiturages-board">
      {erreur && <Alert variant="danger" dismissible onClose={() => setErreur(null)}>{t(erreur)}</Alert>}

      {!isAuthenticated && (
        <p className="tk-covoiturages__connexion text-muted mb-4">
          <Link href={`/${locale}/connexion`}>{t('login_to_reply')}</Link>
        </p>
      )}

      {chargement ? (
        <p className="text-muted">…</p>
      ) : carpools.length === 0 ? (
        <p className="text-muted">{t('empty_upcoming')}</p>
      ) : (
        grouperParEvenement(carpools).map((groupe) => (
          <section key={groupe.evenement?.eveId ?? 'sans'} className="tk-covoiturages__evenement mb-5">
            {groupe.evenement && (
              <header className="mb-2">
                <h2 className="h4 mb-1">
                  <Link href={evenementHref(locale, groupe.evenement.eveId, groupe.evenement.libelle)} className="tk-profile-link">
                    {groupe.evenement.libelle}
                  </Link>
                </h2>
                <small className="tk-covoiturages__evenement-infos text-muted">
                  {formatDate(groupe.evenement.date)}
                  {groupe.evenement.vilNom && ` · ${groupe.evenement.vilNom}`}
                </small>
              </header>
            )}
            {groupe.carpools.map((carpool) => (
              <React.Fragment key={carpool.id}>
                {enEdition?.id === carpool.id ? (
                  <CarpoolForm
                    saisie={saisie}
                    onChange={setSaisie}
                    onSubmit={enregistrer}
                    onCancel={annulerEdition}
                    submitting={enregistrement}
                    editing
                  />
                ) : (
                  <CarpoolItem
                    carpool={carpool}
                    isOwner={estAuteur(carpool)}
                    canContact={isAuthenticated && !estAuteur(carpool)}
                    onContact={setContact}
                    onEdit={commencerEdition}
                    onDelete={supprimer}
                  />
                )}
              </React.Fragment>
            ))}
          </section>
        ))
      )}

      <ContactModal
        show={contact !== null}
        onHide={() => setContact(null)}
        onSend={async (message) => {
          if (contact) await sendCarpoolContactMessage(contact.id, message);
        }}
        recipientName={contact?.auteur?.pseudo ?? ''}
      />
    </div>
  );
}
