import {
  Badge,
  Group,
  Pagination,
  Paper,
  Stack,
  Text,
  ThemeIcon,
  Timeline,
} from "@mantine/core";
import { useQuery } from "@tanstack/react-query";
import { useState } from "react";
import {
  ArrowLeftRight,
  History,
  MapPin,
  Minus,
  PackageCheck,
  PackageMinus,
  PackageOpen,
  Plus,
  User,
} from "lucide-react";

import { api } from "@/services/api";
import type { ScheduleHistoryEntry } from "@/services/trainBuilder.service";

const ACTION_META: Record<
  ScheduleHistoryEntry["action"],
  { label: string; color: string; icon: typeof Plus }
> = {
  ADD: { label: "Wagon coupled", color: "edr-green", icon: Plus },
  REMOVE: { label: "Wagon trimmed", color: "red", icon: Minus },
  SWITCH: { label: "Wagon switched", color: "blue", icon: ArrowLeftRight },
  BOOKING_REMOVED: { label: "Booking removed", color: "orange", icon: PackageMinus },
  BOOKING_LOADED: { label: "Booking loaded", color: "edr-green", icon: PackageCheck },
  BOOKING_UNLOADED: { label: "Booking unloaded", color: "blue", icon: PackageOpen },
};

/**
 * "History" tab: every change made to the train after it was scheduled —
 * wagons coupled/trimmed/switched (with the stop where it happened) and
 * bookings removed from the composition — newest first.
 */
export default function ScheduleHistoryPanel({ scheduleId }: { scheduleId: string }) {
  const [page, setPage] = useState(1);
  const historyQuery = useQuery(
    api.trainScheduling.scheduleHistory.queryOptions({
      input: { scheduleId, page, pageSize: 20 },
      enabled: Boolean(scheduleId),
      // Keep the previous page on screen while the next one loads.
      placeholderData: (prev) => prev,
    }),
  );
  const entries = historyQuery.data?.items ?? [];
  const totalPages = Math.max(1, historyQuery.data?.meta.totalPages ?? 1);
  const total = historyQuery.data?.meta.total ?? 0;

  return (
    <Paper radius="xl" p="lg">
      <Stack gap="lg">
        <Group gap="md" align="center" wrap="nowrap">
          <ThemeIcon size={44} radius="md" variant="light" color="edr-green">
            <History size={22} />
          </ThemeIcon>
          <Stack gap={2}>
            <Text fw={700} fz="lg">
              Change history
            </Text>
            <Text size="sm" c="dimmed">
              Wagons coupled, trimmed or switched, bookings loaded/unloaded per
              yard, and bookings removed — after this train was scheduled,
              newest first.
            </Text>
          </Stack>
        </Group>

        {historyQuery.isLoading ? (
          <Text size="sm" c="dimmed" ta="center" py="md">
            Loading history…
          </Text>
        ) : entries.length === 0 ? (
          <Text size="sm" c="dimmed" ta="center" py="md">
            No changes recorded yet — the consist and composition are as
            scheduled.
          </Text>
        ) : (
          <Timeline bulletSize={26} lineWidth={2} color="edr-green">
            {entries.map((entry) => {
              const meta = ACTION_META[entry.action] ?? ACTION_META.ADD;
              const Icon = meta.icon;
              return (
                <Timeline.Item
                  key={`${entry.kind}-${entry.id}`}
                  bullet={<Icon size={13} />}
                  color={meta.color}
                  title={
                    <Group gap="xs" wrap="nowrap">
                      <Badge size="sm" variant="light" color={meta.color}>
                        {meta.label}
                      </Badge>
                      {entry.subject ? (
                        <Text size="sm" fw={600} ff="monospace">
                          {entry.subject}
                        </Text>
                      ) : null}
                    </Group>
                  }
                >
                  <Group gap="md" mt={2}>
                    <Text size="xs" c="dimmed">
                      {new Date(entry.occurredAt).toLocaleString()}
                    </Text>
                    {entry.yardLabel ? (
                      <Group gap={4} wrap="nowrap">
                        <MapPin size={12} />
                        <Text size="xs" c="dimmed">
                          at {entry.yardLabel}
                        </Text>
                      </Group>
                    ) : null}
                    {entry.actor ? (
                      <Group gap={4} wrap="nowrap">
                        <User size={12} />
                        <Text size="xs" c="dimmed">
                          {entry.actor}
                        </Text>
                      </Group>
                    ) : null}
                  </Group>
                  {entry.note ? (
                    <Text size="xs" c="dimmed" mt={2} fs="italic">
                      {entry.note}
                    </Text>
                  ) : null}
                </Timeline.Item>
              );
            })}
          </Timeline>
        )}

        {totalPages > 1 ? (
          <Group justify="space-between">
            <Text size="xs" c="dimmed">
              {total} change(s)
            </Text>
            <Pagination size="sm" value={page} onChange={setPage} total={totalPages} />
          </Group>
        ) : null}
      </Stack>
    </Paper>
  );
}
