﻿import React from 'react';
import { useNavigate, useLocation } from 'react-router-dom';
import { useTranslation } from 'react-i18next';
import {
  CalendarDays,
  Camera,
  AlertTriangle,
  Sparkles,
  Users,
  Plus,
  Settings,
  QrCode,
  ClipboardList,
  Package as PackageIcon,
} from 'lucide-react';
import toast from 'react-hot-toast';

import { Alert, AlertDescription, AlertTitle } from '@/components/ui/alert';
import { Badge } from '@/components/ui/badge';
import { Button } from '@/components/ui/button';
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from '@/components/ui/card';
import { Progress } from '@/components/ui/progress';
import {
  TenantHeroCard,
  TenantOnboardingChecklistCard,
  FrostedSurface,
  tenantHeroPrimaryButtonClass,
  SectionCard,
  SectionHeader,
  StatCarousel,
  ActionGrid,
} from '../components/tenant';
import type { ChecklistStep } from '../components/tenant';

import { AdminLayout } from '../components/AdminLayout';
import {
  DashboardSummary,
  getDashboardSummary,
  getEvents,
  getTenantPackagesOverview,
  TenantEvent,
  TenantPackageSummary,
} from '../api';
import { isAuthError } from '../auth/tokens';
import { useAuth } from '../auth/context';
import {
  adminPath,
  ADMIN_HOME_PATH,
  ADMIN_EVENT_VIEW_PATH,
  ADMIN_EVENTS_PATH,
  ADMIN_EVENT_PHOTOS_PATH,
  ADMIN_EVENT_INVITES_PATH,
  ADMIN_EVENT_TASKS_PATH,
  ADMIN_BILLING_PATH,
  ADMIN_SETTINGS_PATH,
  ADMIN_WELCOME_BASE_PATH,
  ADMIN_EVENT_CREATE_PATH,
  buildEngagementTabPath,
} from '../constants';
import { useOnboardingProgress } from '../onboarding';
import { buildLimitWarnings } from '../lib/limitWarnings';
import type { LimitUsageSummary, GallerySummary } from '../lib/limitWarnings';

interface DashboardState {
  summary: DashboardSummary | null;
  events: TenantEvent[];
  activePackage: TenantPackageSummary | null;
  loading: boolean;
  errorKey: string | null;
}

type ReadinessState = {
  hasEvent: boolean;
  hasTasks: boolean;
  hasQrInvites: boolean;
  hasPackage: boolean;
  primaryEventSlug: string | null;
  primaryEventName: string | null;
  loading: boolean;
};

export default function DashboardPage() {
  const navigate = useNavigate();
  const location = useLocation();
  const { user } = useAuth();
  const { progress, markStep } = useOnboardingProgress();
  const { t, i18n } = useTranslation('dashboard', { keyPrefix: 'dashboard' });
  const { t: tc } = useTranslation('common');

  const translate = React.useCallback(
    (key: string, optionsOrFallback?: Record<string, unknown> | string, explicitFallback?: string) => {
      const hasOptions = typeof optionsOrFallback === 'object' && optionsOrFallback !== null;
      const options = hasOptions ? (optionsOrFallback as Record<string, unknown>) : undefined;
      const fallback = typeof optionsOrFallback === 'string' ? optionsOrFallback : explicitFallback;

      const value = t(key, { defaultValue: fallback, ...(options ?? {}) });
      if (value === `dashboard.${key}`) {
        const fallbackValue = i18n.t(`dashboard:${key}`, { defaultValue: fallback, ...(options ?? {}) });
        if (fallbackValue !== `dashboard:${key}`) {
          return fallbackValue;
        }

        if (fallback !== undefined) {
          return fallback;
        }
      }

      return value;
    },
    [t, i18n],
  );
  const [state, setState] = React.useState<DashboardState>({
    summary: null,
    events: [],
    activePackage: null,
    loading: true,
    errorKey: null,
  });

  const [readiness, setReadiness] = React.useState<ReadinessState>({
    hasEvent: false,
    hasTasks: false,
    hasQrInvites: false,
    hasPackage: false,
    primaryEventSlug: null,
    primaryEventName: null,
    loading: false,
  });

  React.useEffect(() => {
    let cancelled = false;
    (async () => {
      try {
        const [summary, events, packages] = await Promise.all([
          getDashboardSummary().catch(() => null),
          getEvents().catch(() => [] as TenantEvent[]),
          getTenantPackagesOverview().catch(() => ({ packages: [], activePackage: null })),
        ]);

        if (cancelled) {
          return;
        }

        const fallbackSummary = buildSummaryFallback(events, packages.activePackage);
        const primaryEvent = events[0] ?? null;
        const primaryEventName = primaryEvent ? resolveEventName(primaryEvent.name, primaryEvent.slug) : null;

        setReadiness({
          hasEvent: events.length > 0,
          hasTasks: primaryEvent ? (Number(primaryEvent.tasks_count ?? 0) > 0) : false,
          hasQrInvites: primaryEvent
            ? Number(
                primaryEvent.active_invites_count ??
                  primaryEvent.active_join_tokens_count ??
                  0
              ) > 0
            : false,
          hasPackage: Boolean(packages.activePackage),
          primaryEventSlug: primaryEvent?.slug ?? null,
          primaryEventName,
          loading: false,
        });

        setState({
          summary: summary ?? fallbackSummary,
          events,
          activePackage: packages.activePackage,
          loading: false,
          errorKey: null,
        });

        if (!primaryEvent && !cancelled) {
          setReadiness((prev) => ({
            ...prev,
            hasTasks: false,
            hasQrInvites: false,
            loading: false,
          }));
        }
      } catch (error) {
        if (!isAuthError(error)) {
          setState((prev) => ({
            ...prev,
            errorKey: 'loadFailed',
            loading: false,
          }));
        }
      }
    })();

    return () => {
      cancelled = true;
    };
  }, []);

  const { summary, events, activePackage, loading, errorKey } = state;

  React.useEffect(() => {
    if (loading) {
      return;
    }
    if (!progress.eventCreated && events.length === 0 && !location.pathname.startsWith(ADMIN_WELCOME_BASE_PATH)) {
      navigate(ADMIN_WELCOME_BASE_PATH, { replace: true });
      return;
    }
    if (events.length > 0 && !progress.eventCreated) {
      const primary = events[0];
      markStep({
        eventCreated: true,
        serverStep: 'event_created',
        meta: primary ? { event_id: primary.id } : undefined,
      });
    }
  }, [loading, events, events.length, progress.eventCreated, navigate, location.pathname, markStep]);

  const greetingName = user?.name ?? translate('welcome.fallbackName');
  const greetingTitle = translate('welcome.greeting', { name: greetingName });
  const subtitle = translate('welcome.subtitle');
  const errorMessage = errorKey ? translate(`errors.${errorKey}`) : null;
  const dateLocale = i18n.language?.startsWith('en') ? 'en-GB' : 'de-DE';

  const upcomingEvents = getUpcomingEvents(events);
  const publishedEvents = events.filter((event) => event.status === 'published');
  const primaryEvent = events[0] ?? null;
  const primaryEventName = primaryEvent ? resolveEventName(primaryEvent.name, primaryEvent.slug) : null;
  const singleEvent = events.length === 1 ? events[0] : null;
  const singleEventName = singleEvent ? resolveEventName(singleEvent.name, singleEvent.slug) : null;
  const singleEventDateLabel = singleEvent?.event_date ? formatDate(singleEvent.event_date, dateLocale) : null;
  const primaryEventLimits = primaryEvent?.limits ?? null;

  const limitTranslate = React.useCallback(
    (key: string, options?: Record<string, unknown>) => tc(`limits.${key}`, options),
    [tc],
  );

  const limitWarnings = React.useMemo(
    () => buildLimitWarnings(primaryEventLimits, limitTranslate),
    [primaryEventLimits, limitTranslate],
  );

  const shownToastsRef = React.useRef<Set<string>>(new Set());

  React.useEffect(() => {
    limitWarnings.forEach((warning) => {
      const toastKey = `${warning.id}-${warning.message}`;
      if (shownToastsRef.current.has(toastKey)) {
        return;
      }

      shownToastsRef.current.add(toastKey);
      toast(warning.message, {
        icon: warning.tone === 'danger' ? '🚨' : '⚠️',
        id: toastKey,
      });
    });
  }, [limitWarnings]);

  const limitScopeLabels = React.useMemo(
    () => ({
      photos: tc('limits.photosTitle'),
      guests: tc('limits.guestsTitle'),
      gallery: tc('limits.galleryTitle'),
    }),
    [tc],
  );

  const hasPhotos = React.useMemo(() => {
    if ((summary?.new_photos ?? 0) > 0) {
      return true;
    }

    return events.some((event) => Number(event.photo_count ?? 0) > 0 || Number(event.pending_photo_count ?? 0) > 0);
  }, [summary, events]);

  const primaryEventSlug = readiness.primaryEventSlug;
  const liveEvents = React.useMemo(() => {
    const now = Date.now();
    const windowLengthMs = 2 * 24 * 60 * 60 * 1000; // event day + following day
    return events.filter((event) => {
      if (!event.slug) {
        return false;
      }

      const isActivated = Boolean(event.is_active || event.status === 'published');
      if (!isActivated) {
        return false;
      }

      if (!event.event_date) {
        return true;
      }

      const eventStart = new Date(event.event_date).getTime();
      if (Number.isNaN(eventStart)) {
        return true;
      }

      return now >= eventStart && now <= eventStart + windowLengthMs;
    });
  }, [events]);
  const statItems = React.useMemo(
    () => ([
      {
        key: 'activeEvents',
        label: translate('overview.stats.activeEvents'),
        value: summary?.active_events ?? publishedEvents.length,
        hint: translate('overview.stats.publishedHint', { count: publishedEvents.length }),
        icon: <CalendarDays className="h-4 w-4" />,
      },
      {
        key: 'newPhotos',
        label: translate('overview.stats.newPhotos'),
        value: summary?.new_photos ?? 0,
        icon: <Camera className="h-4 w-4" />,
      },
      {
        key: 'taskProgress',
        label: translate('overview.stats.taskProgress'),
        value: `${Math.round(summary?.task_progress ?? 0)}%`,
        icon: <Users className="h-4 w-4" />,
      },
      activePackage
        ? {
            key: 'package',
            label: translate('overview.stats.activePackage', 'Aktives Paket'),
            value: activePackage.package_name,
            icon: <PackageIcon className="h-4 w-4" />,
          }
        : null,
    ].filter(Boolean) as {
      key: string;
      label: string;
      value: string | number;
      hint?: string;
      icon?: React.ReactNode;
    }[]),
    [summary, publishedEvents.length, translate, activePackage],
  );

  const onboardingChecklist = React.useMemo<ChecklistStep[]>(() => {
    const steps: ChecklistStep[] = [
      {
        key: 'admin_app',
        title: translate('onboarding.admin_app.title', 'Admin-App öffnen'),
        description: translate(
          'onboarding.admin_app.description',
          'Verwalte Events, Uploads und Gäste direkt in der Admin-App.'
        ),
        done: Boolean(progress.adminAppOpenedAt),
        ctaLabel: translate('onboarding.admin_app.cta', 'Admin-App starten'),
        onAction: () => navigate(ADMIN_HOME_PATH),
        icon: Sparkles,
      },
      {
        key: 'event_setup',
        title: translate('onboarding.event_setup.title', 'Erstes Event vorbereiten'),
        description: translate(
          'onboarding.event_setup.description',
          'Lege in der Admin-App Name, Datum und Aufgaben fest.'
        ),
        done: readiness.hasEvent,
        ctaLabel: translate('onboarding.event_setup.cta', 'Event anlegen'),
        onAction: () => navigate(ADMIN_EVENT_CREATE_PATH),
        icon: CalendarDays,
      },
      {
        key: 'invite_guests',
        title: translate('onboarding.invite_guests.title', 'Gäste einladen'),
        description: translate(
          'onboarding.invite_guests.description',
          'Teile QR-Codes oder Links, damit Gäste sofort starten.'
        ),
        done: readiness.hasQrInvites || progress.inviteCreated,
        ctaLabel: translate('onboarding.invite_guests.cta', 'QR-Links öffnen'),
        onAction: () => {
          if (primaryEventSlug) {
            navigate(`${ADMIN_EVENT_VIEW_PATH(primaryEventSlug)}#qr-invites`);
            return;
          }
          navigate(ADMIN_EVENTS_PATH);
        },
        icon: QrCode,
      },
      {
        key: 'collect_photos',
        title: translate('onboarding.collect_photos.title', 'Erste Fotos einsammeln'),
        description: translate(
          'onboarding.collect_photos.description',
          'Sobald Uploads eintreffen, moderierst du sie in der Admin-App.'
        ),
        done: hasPhotos,
        ctaLabel: translate('onboarding.collect_photos.cta', 'Uploads prüfen'),
        onAction: () => {
          if (primaryEventSlug) {
            navigate(ADMIN_EVENT_PHOTOS_PATH(primaryEventSlug));
            return;
          }
          navigate(ADMIN_EVENTS_PATH);
        },
        icon: Camera,
      },
      {
        key: 'branding',
        title: translate('onboarding.branding.title', 'Branding & Aufgaben verfeinern'),
        description: translate(
          'onboarding.branding.description',
          'Passt Farbwelt und Aufgabenpakete an euren Anlass an.'
        ),
        done: (progress.brandingConfigured || readiness.hasTasks) && (readiness.hasPackage || progress.packageSelected),
        ctaLabel: translate('onboarding.branding.cta', 'Branding öffnen'),
        onAction: () => {
          if (primaryEventSlug) {
            navigate(ADMIN_EVENT_INVITES_PATH(primaryEventSlug));
            return;
          }
          navigate(ADMIN_EVENTS_PATH);
        },
        icon: ClipboardList,
      },
    ];

    return steps;
  }, [
    translate,
    progress.adminAppOpenedAt,
    progress.inviteCreated,
    progress.brandingConfigured,
    progress.packageSelected,
    readiness.hasEvent,
    readiness.hasQrInvites,
    readiness.hasTasks,
    readiness.hasPackage,
    hasPhotos,
    navigate,
    primaryEventSlug,
  ]);

  const completedOnboardingSteps = React.useMemo(
    () => onboardingChecklist.filter((step) => step.done).length,
    [onboardingChecklist]
  );

  const onboardingCompletion = React.useMemo(() => {
    if (onboardingChecklist.length === 0) {
      return 0;
    }
    return Math.round((completedOnboardingSteps / onboardingChecklist.length) * 100);
  }, [completedOnboardingSteps, onboardingChecklist]);

  const onboardingCardTitle = translate('onboarding.card.title', 'Dein Start in fünf Schritten');
  const onboardingCardDescription = translate(
    'onboarding.card.description',
    'Bearbeite die Schritte in der Admin-App – das Dashboard zeigt dir den Status.'
  );
  const onboardingCompletedCopy = translate(
    'onboarding.card.completed',
    'Alle Schritte abgeschlossen – großartig! Du kannst jederzeit zur Admin-App wechseln.'
  );
  const onboardingFallbackCta = translate('onboarding.card.cta_fallback', 'Jetzt starten');

  const heroBadge = singleEvent
    ? translate('overview.eventHero.badge', 'Aktives Event')
    : translate('overview.title', 'Kurzer Überblick');

  const heroDescription = singleEvent
    ? translate('overview.eventHero.description', { defaultValue: 'Alles richtet sich nach {{event}}. Nächster Termin: {{date}}.', event: singleEventName ?? '', date: singleEventDateLabel ?? translate('overview.eventHero.noDate', 'Noch kein Datum festgelegt') })
    : translate('overview.description', 'Wichtigste Kennzahlen deines Tenants auf einen Blick.');

  const heroSupportingCopy = onboardingCompletion === 100 ? onboardingCompletedCopy : onboardingCardDescription;
  const heroSupporting = singleEvent
    ? [
        translate('overview.eventHero.supporting.status', {
          defaultValue: 'Status: {{status}}',
          status: formatEventStatus(singleEvent.status ?? null, tc),
        }),
        singleEventDateLabel
          ? translate('overview.eventHero.supporting.date', singleEventDateLabel ?? 'Noch kein Datum festgelegt.')
          : translate('overview.eventHero.noDate', 'Noch kein Datum festgelegt.'),
      ].filter(Boolean)
    : [heroSupportingCopy];

  const heroPrimaryAction = (() => {
    if (onboardingCompletion < 100) {
      return (
        <Button
          size="sm"
          className={tenantHeroPrimaryButtonClass}
          onClick={() => {
            if (readiness.hasEvent) {
              navigate(ADMIN_EVENTS_PATH);
            } else {
              navigate(ADMIN_EVENT_CREATE_PATH);
            }
          }}
        >
          {translate('onboarding.hero.cta', 'Setup fortsetzen')}
        </Button>
      );
    }

    if (singleEvent?.slug) {
      return (
        <Button
          size="sm"
          className={tenantHeroPrimaryButtonClass}
          onClick={() => navigate(ADMIN_EVENT_VIEW_PATH(singleEvent.slug))}
        >
          {translate('actions.openEvent', 'Event öffnen')}
        </Button>
      );
    }

    if (readiness.hasEvent) {
      return (
        <Button size="sm" className={tenantHeroPrimaryButtonClass} onClick={() => navigate(ADMIN_EVENTS_PATH)}>
          {translate('quickActions.moderatePhotos.label', 'Fotos moderieren')}
        </Button>
      );
    }

    return (
      <Button size="sm" className={tenantHeroPrimaryButtonClass} onClick={() => navigate(ADMIN_EVENT_CREATE_PATH)}>
        {translate('actions.newEvent')}
      </Button>
    );
  })();

  const heroAside = onboardingCompletion < 100 ? (
    <FrostedSurface className="w-full rounded-2xl border-slate-200 bg-white p-5 text-slate-900 shadow-lg shadow-rose-300/20 dark:border-white/20 dark:bg-white/10">
      <div className="flex items-center justify-between text-sm font-medium text-slate-700">
        <span>{onboardingCardTitle}</span>
        <span>
          {completedOnboardingSteps}/{onboardingChecklist.length}
        </span>
      </div>
      <Progress value={onboardingCompletion} className="mt-4 h-2 bg-rose-100" />
      <p className="mt-3 text-xs text-slate-600">{onboardingCardDescription}</p>
    </FrostedSurface>
  ) : singleEvent ? (
    <FrostedSurface className="w-full rounded-2xl border-slate-200 bg-white p-5 text-slate-900 shadow-lg shadow-rose-300/20 dark:border-white/20 dark:bg-white/10">
      <div className="space-y-3 text-sm">
        <div>
          <p className="text-xs uppercase tracking-[0.35em] text-rose-500">
            {translate('overview.eventHero.stats.title', 'Momentaufnahme')}
          </p>
          <p className="text-lg font-semibold text-slate-900 dark:text-white">
            {formatEventStatus(singleEvent.status ?? null, tc)}
          </p>
        </div>
        <dl className="space-y-2">
          <div className="flex items-center justify-between">
            <dt className="text-xs text-slate-500">{translate('overview.eventHero.stats.date', 'Eventdatum')}</dt>
            <dd className="text-sm font-semibold text-slate-900 dark:text-white">
              {singleEventDateLabel ?? translate('overview.eventHero.noDate', 'Nicht gesetzt')}
            </dd>
          </div>
          <div className="flex items-center justify-between">
            <dt className="text-xs text-slate-500">{translate('overview.eventHero.stats.uploads', 'Uploads gesamt')}</dt>
            <dd className="text-sm font-semibold text-slate-900 dark:text-white">
              {Number(singleEvent.photo_count ?? 0).toLocaleString(i18n.language)}
            </dd>
          </div>
          <div className="flex items-center justify-between">
            <dt className="text-xs text-slate-500">{translate('overview.eventHero.stats.tasks', 'Offene Aufgaben')}</dt>
            <dd className="text-sm font-semibold text-slate-900 dark:text-white">
              {Number(singleEvent.tasks_count ?? 0).toLocaleString(i18n.language)}
            </dd>
          </div>
        </dl>
      </div>
    </FrostedSurface>
  ) : null;
  const readinessCompleteLabel = translate('readiness.complete', 'Erledigt');
  const readinessPendingLabel = translate('readiness.pending', 'Noch offen');
  const hasEventContext = readiness.hasEvent;

  const quickActionItems = React.useMemo(
    () => [
      {
        key: 'create',
        label: translate('quickActions.createEvent.label'),
        description: translate('quickActions.createEvent.description'),
        icon: <Plus className="h-5 w-5" />,
        onClick: () => navigate(ADMIN_EVENT_CREATE_PATH),
      },
      {
        key: 'photos',
        label: translate('quickActions.moderatePhotos.label'),
        description: translate('quickActions.moderatePhotos.description'),
        icon: <Camera className="h-5 w-5" />,
        onClick: () => navigate(ADMIN_EVENTS_PATH),
        disabled: !hasEventContext,
      },
      {
        key: 'tasks',
        label: translate('quickActions.organiseTasks.label'),
        description: translate('quickActions.organiseTasks.description'),
        icon: <ClipboardList className="h-5 w-5" />,
        onClick: () => navigate(buildEngagementTabPath('tasks')),
        disabled: !hasEventContext,
      },
      {
        key: 'packages',
        label: translate('quickActions.managePackages.label'),
        description: translate('quickActions.managePackages.description'),
        icon: <Sparkles className="h-5 w-5" />,
        onClick: () => navigate(ADMIN_BILLING_PATH),
      },
    ],
    [translate, navigate, hasEventContext],
  );

  const layoutActions = singleEvent ? (
    <Button
      className="rounded-full bg-brand-rose px-4 text-white shadow-lg shadow-rose-400/40 hover:bg-[var(--brand-rose-strong)]"
      onClick={() => {
        if (singleEvent.slug) {
          navigate(ADMIN_EVENT_VIEW_PATH(singleEvent.slug));
        } else {
          navigate(ADMIN_EVENTS_PATH);
        }
      }}
    >
      {translate('actions.openEvent', 'Event öffnen')}
    </Button>
  ) : (
    <Button
      className="rounded-full bg-brand-rose px-4 text-white shadow-lg shadow-rose-400/40 hover:bg-[var(--brand-rose-strong)]"
      onClick={() => navigate(ADMIN_EVENT_CREATE_PATH)}
    >
      <Plus className="h-4 w-4" /> {translate('actions.newEvent')}
    </Button>
  );

  const adminTitle = singleEventName ?? greetingTitle;
  const adminSubtitle = singleEvent
    ? translate('overview.eventHero.subtitle', {
      defaultValue: 'Alle Funktionen konzentrieren sich auf dieses Event.',
      date: singleEventDateLabel ?? translate('overview.eventHero.noDate', 'Noch kein Datum festgelegt'),
    })
    : subtitle;

  const heroTitle = adminTitle;
  const liveNowTitle = t('liveNow.title', { defaultValue: 'Während des Events' });
  const liveNowDescription = t('liveNow.description', {
    defaultValue: 'Direkter Zugriff, solange dein Event läuft.',
    count: liveEvents.length,
  });
  const liveActionLabels = React.useMemo(() => ({
    photos: t('liveNow.actions.photos', { defaultValue: 'Uploads' }),
    invites: t('liveNow.actions.invites', { defaultValue: 'QR & Einladungen' }),
    tasks: t('liveNow.actions.tasks', { defaultValue: 'Aufgaben' }),
  }), [t]);
  const liveStatusLabel = t('liveNow.status', { defaultValue: 'Live' });
  const liveNoDate = t('liveNow.noDate', { defaultValue: 'Kein Datum' });

  return (
    <AdminLayout title={adminTitle} subtitle={adminSubtitle} actions={layoutActions}>
      {errorMessage && (
        <Alert variant="destructive">
          <AlertTitle>{t('dashboard.alerts.errorTitle')}</AlertTitle>
          <AlertDescription>{errorMessage}</AlertDescription>
        </Alert>
      )}

      {loading ? (
        <DashboardSkeleton />
      ) : (
        <>
          <TenantHeroCard
            badge={heroBadge}
            title={heroTitle}
            description={heroDescription}
            supporting={heroSupporting}
            primaryAction={heroPrimaryAction}
            aside={heroAside}
          />

          {liveEvents.length > 0 && (
            <Card className="border border-rose-200 bg-rose-50/80 shadow-lg shadow-rose-200/40">
              <CardHeader className="space-y-1">
                <CardTitle className="text-base font-semibold text-rose-900">{liveNowTitle}</CardTitle>
                <CardDescription className="text-sm text-rose-700">{liveNowDescription}</CardDescription>
              </CardHeader>
              <CardContent className="grid gap-4 sm:grid-cols-2">
                {liveEvents.map((event) => {
                  const name = resolveEventName(event.name, event.slug);
                  const dateLabel = event.event_date ? formatDate(event.event_date, dateLocale) : liveNoDate;
                  return (
                    <div
                      key={event.id}
                      className="rounded-2xl border border-white/70 bg-white/80 p-4 shadow-sm shadow-rose-100/50"
                    >
                      <div className="flex items-start justify-between gap-3">
                        <div>
                          <p className="text-sm font-semibold text-slate-900">{name}</p>
                          <p className="text-xs text-slate-500">{dateLabel}</p>
                        </div>
                        <Badge className="bg-rose-600/90 text-white">{liveStatusLabel}</Badge>
                      </div>
                      <div className="mt-3 flex flex-wrap gap-2">
                        <Button
                          type="button"
                          size="sm"
                          variant="outline"
                          className="flex flex-1 items-center gap-2 border-rose-200 text-rose-700 hover:border-rose-400 hover:text-rose-800"
                          onClick={() => navigate(ADMIN_EVENT_PHOTOS_PATH(event.slug))}
                        >
                          <Camera className="h-4 w-4" />
                          {liveActionLabels.photos}
                        </Button>
                        <Button
                          type="button"
                          size="sm"
                          variant="outline"
                          className="flex flex-1 items-center gap-2 border-rose-200 text-rose-700 hover:border-rose-400 hover:text-rose-800"
                          onClick={() => navigate(ADMIN_EVENT_INVITES_PATH(event.slug))}
                        >
                          <QrCode className="h-4 w-4" />
                          {liveActionLabels.invites}
                        </Button>
                        <Button
                          type="button"
                          size="sm"
                          variant="outline"
                          className="flex flex-1 items-center gap-2 border-rose-200 text-rose-700 hover:border-rose-400 hover:text-rose-800"
                          onClick={() => navigate(ADMIN_EVENT_TASKS_PATH(event.slug))}
                        >
                          <ClipboardList className="h-4 w-4" />
                          {liveActionLabels.tasks}
                        </Button>
                      </div>
                    </div>
                  );
                })}
              </CardContent>
            </Card>
          )}

          {events.length === 0 && (
            <Card className="border-none bg-white/90 shadow-lg shadow-rose-100/50">
              <CardHeader className="space-y-2">
                <CardTitle className="flex items-center gap-2 text-base font-semibold text-slate-900">
                  <Sparkles className="h-5 w-5 text-brand-rose" />
                  {translate('welcomeCard.title')}
                </CardTitle>
                <CardDescription className="text-sm text-slate-600">
                  {translate('welcomeCard.summary')}
                </CardDescription>
              </CardHeader>
              <CardContent className="flex flex-col gap-3 text-sm text-slate-600">
                <p>{translate('welcomeCard.body1')}</p>
                <p>{translate('welcomeCard.body2')}</p>
                <Button
                  size="sm"
                  className="self-start rounded-full bg-brand-rose px-5 text-white shadow-md shadow-rose-300/40"
                  onClick={() => navigate(ADMIN_WELCOME_BASE_PATH)}
                >
                  {translate('welcomeCard.cta')}
                </Button>
              </CardContent>
            </Card>
          )}

          <SectionCard className="space-y-3">
            <SectionHeader
              eyebrow={translate('overview.title')}
              title={translate('overview.title')}
              description={translate('overview.description')}
              endSlot={(
                <Badge className="bg-brand-rose-soft text-brand-rose">
                  {activePackage?.package_name ?? translate('overview.noPackage')}
                </Badge>
              )}
            />
            <StatCarousel items={statItems} />
          </SectionCard>

          {primaryEventLimits ? (
            <Card className="border-0 bg-brand-card shadow-brand-primary">
              <CardHeader className="flex flex-col gap-2 md:flex-row md:items-center md:justify-between">
                <div>
                  <CardTitle className="flex items-center gap-2 text-xl text-slate-900">
                    <PackageIcon className="h-5 w-5 text-brand-rose" />
                    {translate('limitsCard.title')}
                  </CardTitle>
                  <CardDescription className="text-sm text-slate-600">
                    {primaryEventName
                      ? translate('limitsCard.description', { name: primaryEventName })
                      : translate('limitsCard.descriptionFallback')}
                  </CardDescription>
                </div>
                <Badge className="bg-brand-rose-soft text-brand-rose">
                  {primaryEventName ?? translate('limitsCard.descriptionFallback')}
                </Badge>
              </CardHeader>
              <CardContent className="space-y-4">
                {limitWarnings.length > 0 && (
                  <div className="space-y-2">
                    {limitWarnings.map((warning) => (
                      <Alert
                        key={warning.id}
                        variant={warning.tone === 'danger' ? 'destructive' : 'default'}
                        className={warning.tone === 'warning' ? 'border-amber-400/50 bg-amber-50 text-amber-900' : undefined}
                      >
                        <AlertTitle className="flex items-center gap-2 text-sm font-semibold">
                          <AlertTriangle className="h-4 w-4" />
                          {limitScopeLabels[warning.scope]}
                        </AlertTitle>
                        <AlertDescription className="text-sm">
                          {warning.message}
                        </AlertDescription>
                      </Alert>
                    ))}
                  </div>
                )}

                <div className="grid gap-4 md:grid-cols-2">
                  <LimitUsageRow
                    label={translate('limitsCard.photosLabel')}
                    summary={primaryEventLimits.photos}
                    unlimitedLabel={tc('limits.unlimited')}
                    usageLabel={translate('limitsCard.usageLabel')}
                    remainingLabel={translate('limitsCard.remainingLabel')}
                  />
                  <LimitUsageRow
                    label={translate('limitsCard.guestsLabel')}
                    summary={primaryEventLimits.guests}
                    unlimitedLabel={tc('limits.unlimited')}
                    usageLabel={translate('limitsCard.usageLabel')}
                    remainingLabel={translate('limitsCard.remainingLabel')}
                  />
                </div>

                <GalleryStatusRow
                  label={translate('limitsCard.galleryLabel')}
                  summary={primaryEventLimits.gallery}
                  locale={dateLocale}
                  messages={{
                    expired: tc('limits.galleryExpired'),
                    noExpiry: translate('limitsCard.galleryNoExpiry'),
                    expires: translate('limitsCard.galleryExpires'),
                  }}
                />
              </CardContent>
            </Card>
          ) : null}

          <SectionCard className="space-y-3">
            <SectionHeader
              eyebrow={translate('quickActions.title')}
              title={translate('quickActions.title')}
              description={translate('quickActions.description')}
            />
            <ActionGrid items={quickActionItems} />
          </SectionCard>

          <TenantOnboardingChecklistCard
            title={onboardingCardTitle}
            description={onboardingCardDescription}
            steps={onboardingChecklist}
            completedLabel={readinessCompleteLabel}
            pendingLabel={readinessPendingLabel}
            completionPercent={onboardingCompletion}
            completedCount={completedOnboardingSteps}
            totalCount={onboardingChecklist.length}
            emptyCopy={onboardingCompletedCopy}
            fallbackActionLabel={onboardingFallbackCta}
          />

          <section className="space-y-4 rounded-3xl border border-slate-200 bg-white p-5 shadow-sm dark:border-white/10 dark:bg-white/5 dark:shadow-inner">
            <div className="flex flex-col gap-2 sm:flex-row sm:items-center sm:justify-between">
              <div>
                <p className="text-xs uppercase tracking-[0.35em] text-rose-500 dark:text-rose-200">
                  {translate('upcoming.title')}
                </p>
                <p className="text-sm text-slate-600 dark:text-slate-300">{translate('upcoming.description')}</p>
              </div>
              <Button variant="outline" size="sm" onClick={() => navigate(ADMIN_SETTINGS_PATH)}>
                <Settings className="h-4 w-4" />
                {translate('upcoming.settings')}
              </Button>
            </div>
            <div className="space-y-3">
              {upcomingEvents.length === 0 ? (
                <EmptyState
                  message={translate('upcoming.empty.message')}
                  ctaLabel={translate('upcoming.empty.cta')}
                  onCta={() => navigate(adminPath('/events/new'))}
                />
              ) : (
                upcomingEvents.map((event) => (
                  <UpcomingEventRow
                    key={event.id}
                    event={event}
                    onView={() => navigate(ADMIN_EVENT_VIEW_PATH(event.slug))}
                    locale={dateLocale}
                    labels={{
                      live: translate('upcoming.status.live'),
                      planning: translate('upcoming.status.planning'),
                      open: tc('actions.open'),
                      noDate: translate('upcoming.status.noDate'),
                    }}
                  />
                ))
              )}
            </div>
          </section>
        </>
      )}
    </AdminLayout>
  );
}

function formatDate(value: string | null, locale: string): string | null {
  if (!value) {
    return null;
  }

  const date = new Date(value);
  if (Number.isNaN(date.getTime())) {
    return null;
  }

  try {
    return new Intl.DateTimeFormat(locale, {
      day: '2-digit',
      month: 'short',
      year: 'numeric',
    }).format(date);
  } catch {
    return date.toISOString().slice(0, 10);
  }
}

function formatEventStatus(status: TenantEvent['status'] | null, translateFn: (key: string, options?: Record<string, unknown>) => string): string {
  const map: Record<string, { key: string; fallback: string }> = {
    published: { key: 'events.status.published', fallback: 'Veröffentlicht' },
    draft: { key: 'events.status.draft', fallback: 'Entwurf' },
    archived: { key: 'events.status.archived', fallback: 'Archiviert' },
  };

  const target = map[status ?? 'draft'] ?? map.draft;
  return translateFn(target.key, { defaultValue: target.fallback });
}

function resolveEventName(name: TenantEvent['name'], fallbackSlug: string): string {
  if (typeof name === 'string' && name.trim().length > 0) {
    return name;
  }

  if (name && typeof name === 'object') {
    if (typeof name.de === 'string' && name.de.trim().length > 0) {
      return name.de;
    }
    if (typeof name.en === 'string' && name.en.trim().length > 0) {
      return name.en;
    }
    const first = Object.values(name).find((value) => typeof value === 'string' && value.trim().length > 0);
    if (typeof first === 'string') {
      return first;
    }
  }

  return fallbackSlug || 'Event';
}

function buildSummaryFallback(
  events: TenantEvent[],
  activePackage: TenantPackageSummary | null
): DashboardSummary {
  const activeEvents = events.filter((event) => Boolean(event.is_active || event.status === 'published'));
  const totalPhotos = events.reduce((sum, event) => sum + Number(event.photo_count ?? 0), 0);

  return {
    active_events: activeEvents.length,
    new_photos: totalPhotos,
    task_progress: 0,
    upcoming_events: activeEvents.length,
    active_package: activePackage
      ? {
          name: activePackage.package_name,
          remaining_events: activePackage.remaining_events,
          expires_at: activePackage.expires_at,
        }
      : null,
  };
}

function getUpcomingEvents(events: TenantEvent[]): TenantEvent[] {
  const now = new Date();
  return events
    .filter((event) => {
      if (!event.event_date) return false;
      const date = new Date(event.event_date);
      return !Number.isNaN(date.getTime()) && date >= now;
    })
    .sort((a, b) => {
      const dateA = a.event_date ? new Date(a.event_date).getTime() : 0;
      const dateB = b.event_date ? new Date(b.event_date).getTime() : 0;
      return dateA - dateB;
    })
    .slice(0, 4);
}

function LimitUsageRow({
  label,
  summary,
  unlimitedLabel,
  usageLabel,
  remainingLabel,
}: {
  label: string;
  summary: LimitUsageSummary | null;
  unlimitedLabel: string;
  usageLabel: string;
  remainingLabel: string;
}) {
  if (!summary) {
    return (
      <div className="rounded-2xl border border-slate-200 bg-white/70 p-4">
        <div className="flex items-center justify-between text-sm font-medium text-slate-700">
          <span>{label}</span>
          <span className="text-xs text-slate-500 dark:text-slate-400">{unlimitedLabel}</span>
        </div>
        <p className="mt-2 text-xs text-slate-500 dark:text-slate-400">{unlimitedLabel}</p>
      </div>
    );
  }

  const limit = typeof summary.limit === 'number' && summary.limit > 0 ? summary.limit : null;
  const percent = limit ? Math.min(100, Math.round((summary.used / limit) * 100)) : 0;
  const remaining = typeof summary.remaining === 'number' ? summary.remaining : null;

  const barClass = summary.state === 'limit_reached'
    ? 'bg-rose-500'
    : summary.state === 'warning'
      ? 'bg-amber-500'
      : 'bg-emerald-500';

  return (
    <div className="rounded-2xl border border-slate-200 bg-white/70 p-4 dark:border-slate-800/70 dark:bg-slate-950/80">
      <div className="flex items-center justify-between text-sm font-medium text-slate-700 dark:text-slate-200">
        <span>{label}</span>
        <span className="text-xs text-slate-500 dark:text-slate-400">
          {limit ? usageLabel.replace('{{used}}', `${summary.used}`).replace('{{limit}}', `${limit}`) : unlimitedLabel}
        </span>
      </div>
      {limit ? (
        <>
          <div className="mt-3 h-2 rounded-full bg-slate-200 dark:bg-slate-800">
            <div
              className={`h-2 rounded-full transition-all ${barClass}`}
              style={{ width: `${Math.max(6, percent)}%` }}
            />
          </div>
          {remaining !== null ? (
            <p className="mt-2 text-xs text-slate-500 dark:text-slate-400">
              {remainingLabel
                .replace('{{remaining}}', `${Math.max(0, remaining)}`)
                .replace('{{limit}}', `${limit}`)}
            </p>
          ) : null}
        </>
      ) : (
        <p className="mt-2 text-xs text-slate-500 dark:text-slate-400">{unlimitedLabel}</p>
      )}
    </div>
  );
}

function GalleryStatusRow({
  label,
  summary,
  locale,
  messages,
}: {
  label: string;
  summary: GallerySummary | null;
  locale: string;
  messages: { expired: string; noExpiry: string; expires: string };
}) {
  const expiresAt = summary?.expires_at ? formatDate(summary.expires_at, locale) : null;

  let statusLabel = messages.noExpiry;
  let badgeClass = 'bg-emerald-500/20 text-emerald-700';

  if (summary?.state === 'expired') {
    statusLabel = messages.expired;
    badgeClass = 'bg-rose-500/20 text-rose-700';
  } else if (summary?.state === 'warning') {
    const days = Math.max(0, summary.days_remaining ?? 0);
    statusLabel = `${messages.expires.replace('{{date}}', expiresAt ?? '')} (${days}d)`;
    badgeClass = 'bg-amber-500/20 text-amber-700';
  } else if (summary?.state === 'ok' && expiresAt) {
    statusLabel = messages.expires.replace('{{date}}', expiresAt);
  }

  return (
    <div className="rounded-2xl border border-slate-200 bg-white/70 p-4 dark:border-slate-800/70 dark:bg-slate-950/80">
      <div className="flex items-center justify-between text-sm font-medium text-slate-700 dark:text-slate-200">
        <span>{label}</span>
        <span className={`rounded-full px-3 py-1 text-xs font-semibold ${badgeClass} dark:text-slate-100`}>{statusLabel}</span>
      </div>
    </div>
  );
}

function UpcomingEventRow({
  event,
  onView,
  locale,
  labels,
}: {
  event: TenantEvent;
  onView: () => void;
  locale: string;
  labels: {
    live: string;
    planning: string;
    open: string;
    noDate: string;
  };
}) {
  const date = event.event_date ? new Date(event.event_date) : null;
  const formattedDate = date
    ? date.toLocaleDateString(locale, { day: '2-digit', month: 'short', year: 'numeric' })
    : labels.noDate;

  return (
    <div className="flex flex-col gap-2 rounded-2xl border border-slate-200 bg-white p-4 shadow-sm shadow-white/30 dark:border-white/10 dark:bg-white/5 sm:flex-row sm:items-center sm:justify-between">
      <div className="flex flex-col gap-1">
        <span className="text-xs font-medium uppercase tracking-wide text-slate-500">{formattedDate}</span>
        <div className="flex items-center gap-2">
          <Badge className={event.status === 'published' ? 'bg-sky-100 text-sky-700' : 'bg-slate-100 text-slate-600'}>
            {event.status === 'published' ? labels.live : labels.planning}
          </Badge>
          <Button
            size="sm"
            variant="outline"
            onClick={onView}
            className="rounded-full border-brand-rose-soft text-brand-rose hover:bg-brand-rose-soft/40"
          >
            {labels.open}
          </Button>
        </div>
      </div>
    </div>
  );
}

function EmptyState({ message, ctaLabel, onCta }: { message: string; ctaLabel: string; onCta: () => void }) {
  return (
    <div className="flex flex-col items-center justify-center gap-3 rounded-2xl border border-dashed border-slate-200 bg-white/70 p-10 text-center">
      <div className="rounded-full bg-brand-rose-soft p-3 text-brand-rose shadow-inner shadow-pink-200/80">
        <Sparkles className="h-5 w-5" />
      </div>
      <p className="text-sm text-slate-600">{message}</p>
      <Button onClick={onCta} className="bg-brand-rose text-white shadow-lg shadow-rose-400/40 hover:bg-[var(--brand-rose-strong)]">
        {ctaLabel}
      </Button>
    </div>
  );
}

function DashboardSkeleton() {
  return (
    <div className="grid gap-6">
      {Array.from({ length: 3 }).map((_, index) => (
        <div key={index} className="space-y-4 rounded-2xl border border-white/60 bg-white/70 p-6 shadow-sm">
          <div className="h-6 w-48 animate-pulse rounded bg-gradient-to-r from-white/40 via-white/60 to-white/40" />
          <div className="grid gap-4 sm:grid-cols-2 lg:grid-cols-4">
            {Array.from({ length: 4 }).map((__ , cardIndex) => (
              <div
                key={cardIndex}
                className="h-24 animate-pulse rounded-2xl bg-gradient-to-r from-white/40 via-white/60 to-white/40"
              />
            ))}
          </div>
        </div>
      ))}
    </div>
  );
}
