// app/(app)/users/UsersCsvImportButton.tsx
'use client';

import { useRef, useState } from 'react';
import { useRouter } from 'next/navigation';
import Button from '@/components/ui/Button';

type SimpleGroup = {
  id: string;
  name: string;
};

type Props = {
  groups: SimpleGroup[];
};

type ParsedRow = {
  nwkennung: string;
  lastName: string;
  firstName: string;
  arbeitsname: string;
  groupName: string | null;
  rawLine: string;
  lineNumber: number;
};

export default function UsersCsvImportButton({ groups }: Props) {
  const router = useRouter();
  const fileInputRef = useRef<HTMLInputElement | null>(null);

  const [importing, setImporting] = useState(false);
  const [importError, setImportError] = useState<string | null>(null);
  const [importSummary, setImportSummary] = useState<string | null>(null);
  const [importProgress, setImportProgress] = useState<string | null>(null);

  async function handleImportCsv(
    e: React.ChangeEvent<HTMLInputElement>,
  ): Promise<void> {
    const file = e.target.files?.[0];
    if (!file) return;

    setImporting(true);
    setImportError(null);
    setImportSummary(null);
    setImportProgress('Lese Datei …');

    try {
      const text = await file.text();
      setImportProgress('Analysiere CSV …');

      const lines = text.split(/\r?\n/);

      const parsedRows: ParsedRow[] = [];
      let skippedCount = 0;

      for (let index = 0; index < lines.length; index++) {
        const raw = lines[index];
        const trimmed = raw.trim();

        if (!trimmed) continue;

        // erste Zeile = Header
        if (index === 0) continue;

        const parts = trimmed.split(';');
        if (parts.length < 4) {
          console.warn('Zeile übersprungen (falsches Format):', trimmed);
          skippedCount++;
          continue;
        }

        const [
          nwkennungRaw,
          lastNameRaw,
          firstNameRaw,
          arbeitsnameRaw,
          groupRaw,
        ] = parts;

        const nwkennung = (nwkennungRaw ?? '').trim().toLowerCase();
        const lastName = (lastNameRaw ?? '').trim();
        const firstName = (firstNameRaw ?? '').trim();
        const arbeitsname = (arbeitsnameRaw ?? '').trim();
        const groupNameRaw = (groupRaw ?? '').trim();
        const groupName = groupNameRaw ? groupNameRaw : null;

        if (!nwkennung || !lastName || !firstName || !arbeitsname) {
          console.warn(
            'Zeile übersprungen (Pflichtfelder leer):',
            trimmed,
          );
          skippedCount++;
          continue;
        }

        parsedRows.push({
          nwkennung,
          lastName,
          firstName,
          arbeitsname,
          groupName,
          rawLine: trimmed,
          lineNumber: index + 1,
        });
      }

      if (parsedRows.length === 0) {
        setImportError(
          'Keine gültigen Zeilen gefunden. Bitte CSV prüfen.',
        );
        return;
      }

      // 1) Gruppen vorbereiten: bestehende + neue
      setImportProgress('Ermittle Gruppen …');

      const groupCache = new Map<string, string>();
      for (const g of groups) {
        const name = g.name.trim();
        if (name) groupCache.set(name, g.id);
      }

      const knownGroupNames = new Set<string>(
        Array.from(groupCache.keys()),
      );
      const newGroupNamesSet = new Set<string>();

      for (const row of parsedRows) {
        if (!row.groupName) continue;
        const gName = row.groupName.trim();
        if (!gName) continue;
        if (!knownGroupNames.has(gName)) {
          newGroupNamesSet.add(gName);
        }
      }

      const newGroupNames = Array.from(newGroupNamesSet.values());

      // 2) Neue Gruppen in einem Rutsch anlegen
      if (newGroupNames.length > 0) {
        setImportProgress(
          `Lege ${newGroupNames.length} neue Gruppe(n) an …`,
        );

        const resGroups = await fetch('/api/user-groups', {
          method: 'POST',
          headers: { 'Content-Type': 'application/json' },
          body: JSON.stringify({ names: newGroupNames }),
        });

        if (!resGroups.ok) {
          const data = await resGroups.json().catch(() => null);
          console.error(
            'Fehler beim Bulk-Anlegen der Gruppen:',
            resGroups.status,
            data,
          );
          setImportError(
            'Fehler beim Anlegen der Gruppen. Import abgebrochen.',
          );
          return;
        }

        const data = await resGroups.json();
        const createdGroups = (data.groups ?? []) as SimpleGroup[];

        for (const g of createdGroups) {
          const name = g.name.trim();
          if (name) {
            groupCache.set(name, g.id);
            knownGroupNames.add(name);
          }
        }
      }

      // 3) Benutzer-Payload für Bulk-Import bauen
      setImportProgress('Bereite Benutzer-Daten für Import vor …');

      type UserPayload = {
        nwkennung: string;
        firstName: string;
        lastName: string;
        arbeitsname: string;
        groupId?: string | null;
      };

      const usersPayload: UserPayload[] = [];
      let skippedByGroup = 0;

      for (const row of parsedRows) {
        let groupId: string | null = null;

        if (row.groupName) {
          const gName = row.groupName.trim();
          if (gName) {
            const id = groupCache.get(gName);
            if (!id) {
              console.warn(
                'Zeile übersprungen (Gruppe nicht vorhanden):',
                row.rawLine,
              );
              skippedByGroup++;
              continue;
            }
            groupId = id;
          }
        }

        usersPayload.push({
          nwkennung: row.nwkennung,
          firstName: row.firstName,
          lastName: row.lastName,
          arbeitsname: row.arbeitsname,
          groupId: groupId ?? null,
        });
      }

      if (usersPayload.length === 0) {
        setImportError(
          'Keine gültigen Benutzer-Datensätze nach Gruppenzuordnung. Import abgebrochen.',
        );
        return;
      }

      // 4) Bulk-Import der Benutzer
      setImportProgress(
        `Importiere ${usersPayload.length} Benutzer …`,
      );

      const resUsers = await fetch('/api/users', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({ users: usersPayload }),
      });

      if (!resUsers.ok) {
        const data = await resUsers.json().catch(() => null);
        console.error(
          'Fehler beim Bulk-Import der Benutzer:',
          resUsers.status,
          data,
        );
        setImportError(
          'Fehler beim Import der Benutzer. Details siehe Konsole.',
        );
        return;
      }

      const result = await resUsers.json();
      const createdCount = result.createdCount ?? 0;
      const skippedServer = result.skippedCount ?? 0;

      const totalSkipped =
        skippedCount + skippedByGroup + skippedServer;

      setImportSummary(
        `Import abgeschlossen: ${createdCount} Personen importiert, ${totalSkipped} Zeilen übersprungen.`,
      );
      setImportProgress('Import abgeschlossen.');
      router.refresh();
    } catch (err: any) {
      console.error('Fehler beim CSV-Import', err);
      setImportError(
        err instanceof Error
          ? err.message
          : 'Fehler beim CSV-Import.',
      );
    } finally {
      setImporting(false);
      if (e.target) {
        e.target.value = '';
      }
    }
  }

  return (
    <div className="flex flex-col items-stretch gap-1">
      <Button
        type="button"
        variant="soft"
        tone="indigo"
        size="lg"
        disabled={importing}
        onClick={() => fileInputRef.current?.click()}
      >
        {importing ? 'Importiere …' : 'Import aus CSV'}
      </Button>

      <input
        ref={fileInputRef}
        type="file"
        accept=".csv,text/csv"
        className="hidden"
        onChange={handleImportCsv}
      />

      {importProgress && (
        <p className="text-[11px] text-gray-500 dark:text-gray-400">
          {importProgress}
        </p>
      )}

      {importSummary && (
        <p className="text-[11px] text-gray-600 dark:text-gray-300">
          {importSummary}
        </p>
      )}
      {importError && (
        <p className="text-[11px] text-red-600 dark:text-red-400">
          {importError}
        </p>
      )}
    </div>
  );
}
