import { useMemo } from "react";
import { useQuery } from "@tanstack/react-query";
import { useNavigate, useParams } from "react-router-dom";
import {
  Alert,
  Badge,
  Box,
  Button,
  Grid,
  Group,
  Loader,
  Paper,
  Progress,
  RingProgress,
  Stack,
  Text,
  ThemeIcon,
} from "@mantine/core";
import {
  AlertCircle,
  ArrowRight,
  CheckCircle2,
  Clock,
  PackageCheck,
  PackagePlus,
  RotateCcw,
  ShieldCheck,
} from "lucide-react";
import type { Freight } from "@edr/types";

import { ClearanceOpsTabs } from "@/components/contracts/ClearanceOpsTabs";
import { PageContainer } from "@/components/page/PageContainer";
import { PageHeader } from "@/components/page/PageHeader";
import { SectionCard } from "@/components/bookings/detail";
import { ClearanceReviewSection } from "@/components/bookings/detail/ClearanceReviewSection";
import { ClearancePhaseStepper } from "@/components/contracts/ClearancePhaseStepper";
import { PhasedClearanceActionPanel } from "@/components/contracts/PhasedClearanceActionPanel";
import { ClearanceMilestoneTimeline } from "@/components/contracts/ClearanceMilestoneTimeline";
import { useFileViewer } from "@/hooks/useFileViewer";
import { useBookingMilestones } from "@/hooks/contracts/useContracts";
import { bookingsService } from "@/services/bookings.service";
import { contractsService } from "@/services/contracts.service";
import { downloadBookingFile } from "@/services/files.service";
import { useBookingDetail } from "@/hooks/bookings/useBookings";
import { useAuth } from "@/auth/useAuth";
import { FREIGHT_PERMS, hasPermission, isDjiboutiGl } from "@/lib/permissions";
import { RequestedCargoChips } from "@/features/clearance/requestedCargo";

export default function DocumentClearanceDetailPage() {
  const params = useParams<{ id?: string; bookingId?: string }>();
  const id = params.id ?? params.bookingId;
  const navigate = useNavigate();
  const { user } = useAuth();
  const { view, viewer } = useFileViewer();

  const { data: booking } = useBookingDetail(id);
  const {
    data: clearance,
    isLoading,
    isError,
    refetch,
  } = useQuery({
    queryKey: ["clearance", id],
    queryFn: () => bookingsService.getClearance(id!),
    enabled: Boolean(id),
  });

  const { data: bookingMilestones } = useBookingMilestones(id);

  // The originating shipment request carries the quantities the customer asked
  // for (per container type, or bulk weight/items). The bare instance itself has
  // no cargo until GL completes the booking, so surface the request here.
  const { data: contractRequests } = useQuery({
    queryKey: ["shipment-requests-for-contract", booking?.contractId],
    queryFn: () => contractsService.listBookingRequests(booking!.contractId!),
    enabled: Boolean(booking?.contractId),
  });
  const requestedLines = useMemo(
    () =>
      (contractRequests ?? []).find((r) => r.createdBookingId === id)
        ?.requestedLines ?? null,
    [contractRequests, id],
  );

  const stats = useMemo(() => {
    const docs = (clearance?.documents ?? []).filter(
      (d) => d.uploadedBy === "customer",
    );
    const total = docs.length;
    const approved = docs.filter((d) => d.reviewStatus === "APPROVED").length;
    const queried = docs.filter((d) => d.reviewStatus === "QUERIED").length;
    const pending = total - approved - queried;
    const pct = total === 0 ? 0 : Math.round((approved / total) * 100);
    return { total, approved, queried, pending, pct };
  }, [clearance]);

  const reference = booking?.reference ?? "Clearance";
  const isPhasedGeneral =
    Boolean(booking?.customsClearingEnabled) &&
    booking?.contractKind === "GENERAL" &&
    Boolean(clearance?.phase);

  // Bare initiated instance whose clearance is done: GL completes the booking
  // (container numbers, VGM, shipment day) via the completion form.
  // Creating the booking is a GL Ethiopia action — never available to Djibouti GL.
  const canCompleteBooking =
    booking?.status === "CLEARANCE_READY" &&
    Boolean(booking?.contractId) &&
    Boolean(booking?.customsClearingEnabled) &&
    !(Number(booking?.totalAmount ?? 0) > 0) &&
    hasPermission(user, FREIGHT_PERMS.contracts.createBooking) &&
    !isDjiboutiGl(user);

  // The completed booking expired unpaid at train dispatch. Its per-booking
  // clearance is finished, so GL rebooks it onto a new day — the customer never
  // re-requests the shipment or pays the clearance fee again.
  const canRebookExpired =
    booking?.status === "EXPIRED" &&
    Boolean(booking?.contractId) &&
    Number(booking?.totalAmount ?? 0) > 0 &&
    hasPermission(user, FREIGHT_PERMS.contracts.createBooking) &&
    !isDjiboutiGl(user);

  const docsPhaseComplete =
    clearance?.milestones?.some(
      (m) => m.milestoneCode === "DOCUMENTS_APPROVED" && m.status === "COMPLETED",
    ) ?? false;
  const queriesLocked = Boolean(
    (clearance as Freight.ContractClearanceView | undefined)?.preClearanceFinalized,
  );
  const workflowFiles =
    (clearance as Freight.ContractClearanceView | undefined)?.workflowFiles ?? [];

  if (isLoading) {
    return (
      <PageContainer>
        <Group justify="center" py={80} gap={10}>
          <Loader color="edr-green" />
          <Text c="dimmed">Loading clearance…</Text>
        </Group>
      </PageContainer>
    );
  }

  if (isError || !clearance) {
    return (
      <PageContainer>
        <PageHeader
          title="Clearance not found"
          backTo="/dashboard/contracts/clearance"
          breadcrumbs={[
            { label: "Document Clearance", href: "/dashboard/contracts/clearance" },
            { label: "Not found" },
          ]}
        />
        <Alert color="red" radius="md" icon={<AlertCircle size={16} />}>
          We couldn’t load this booking’s clearance.
        </Alert>
      </PageContainer>
    );
  }

  return (
    <PageContainer>
      <Stack gap="lg">
        <PageHeader
          title={reference}
          backTo="/dashboard/contracts/clearance"
          breadcrumbs={[
            { label: "Document Clearance", href: "/dashboard/contracts/clearance" },
            { label: reference },
          ]}
          meta={
            clearance.allApproved ? (
              <Badge
                variant="light"
                color="edr-green"
                radius="sm"
                leftSection={<CheckCircle2 size={13} />}
              >
                All approved
              </Badge>
            ) : (
              <Badge
                variant="light"
                color="gray"
                radius="sm"
                leftSection={<Clock size={13} />}
              >
                Review pending
              </Badge>
            )
          }
          action={
            canCompleteBooking ? (
              <Button
                color="edr-green"
                radius="md"
                leftSection={<PackagePlus size={16} />}
                onClick={() =>
                  navigate(
                    `/dashboard/contracts/${booking!.contractId}/bookings/${id}/complete`,
                  )
                }
              >
                Create booking
              </Button>
            ) : canRebookExpired ? (
              <Button
                color="edr-green"
                radius="md"
                leftSection={<RotateCcw size={16} />}
                onClick={() =>
                  navigate(
                    `/dashboard/contracts/${booking!.contractId}/bookings/${id}/complete?copyFrom=${id}`,
                  )
                }
              >
                Rebook shipment
              </Button>
            ) : undefined
          }
        />

        <ClearanceHero
          booking={booking}
          clearance={clearance}
          stats={stats}
          requestedLines={requestedLines}
        />

        {isPhasedGeneral ? (
          <Paper withBorder radius="md" p="lg">
            <ClearancePhaseStepper
              clearance={clearance as Freight.ContractClearanceView}
              tradeDirection={booking?.tradeDirection ?? "IMPORT"}
            />
          </Paper>
        ) : null}

        <ClearanceOpsTabs
          bookingId={id}
          milestones={bookingMilestones}
          showOpsTabs={Boolean(id)}
          showWorkflowFilesTab={isPhasedGeneral}
          tradeDirection={booking?.tradeDirection ?? "IMPORT"}
          workflowFiles={workflowFiles}
          onViewFile={view}
          onDownloadFile={(f) => void downloadBookingFile(f.id, f.name)}
          clearanceTab={
            <Grid gap="lg">
              <Grid.Col span={{ base: 12, lg: isPhasedGeneral ? 7 : 8 }}>
                <ClearanceReviewSection
                  bookingId={id!}
                  hideSummary
                  approvalsLocked={isPhasedGeneral && docsPhaseComplete}
                  queriesLocked={queriesLocked}
                  phasedCustoms={isPhasedGeneral}
                  onChanged={() => void refetch()}
                />
              </Grid.Col>

              <Grid.Col span={{ base: 12, lg: isPhasedGeneral ? 5 : 4 }}>
                {isPhasedGeneral ? (
                  <PhasedClearanceActionPanel
                    bookingId={id!}
                    clearance={clearance}
                    tradeDirection={booking?.tradeDirection ?? "IMPORT"}
                    workflowFiles={workflowFiles}
                    roleMode="ET"
                    // A bare initiated instance still has no cargo/price — the
                    // stepper's "Create booking" step must read as NOT-yet-created
                    // so it never claims the booking is done before GL completes it.
                    bookingCreated={Number(booking?.totalAmount ?? 0) > 0}
                    bookingMilestones={bookingMilestones ?? []}
                    onChanged={() => void refetch()}
                    onViewFile={view}
                    onDownloadFile={(f) => void downloadBookingFile(f.id, f.name)}
                  />
                ) : (
                  <Box style={{ position: "sticky", top: 24 }}>
                    <SectionCard
                      icon={PackageCheck}
                      title="Review progress"
                      accent="edr-green"
                    >
                      <Stack align="center" gap="sm">
                        <RingProgress
                          size={140}
                          thickness={12}
                          roundCaps
                          sections={[{ value: stats.pct, color: "edr-green" }]}
                          label={
                            <Stack gap={0} align="center">
                              <Text fw={800} fz={26} lh={1}>
                                {stats.pct}%
                              </Text>
                              <Text size="xs" c="dimmed">
                                approved
                              </Text>
                            </Stack>
                          }
                        />
                        <Group gap="lg" justify="center">
                          <ProgressStat
                            color="edr-green"
                            label="Approved"
                            value={stats.approved}
                          />
                          <ProgressStat
                            color="red"
                            label="Queried"
                            value={stats.queried}
                          />
                          <ProgressStat
                            color="gray"
                            label="Pending"
                            value={stats.pending}
                          />
                        </Group>
                      </Stack>
                    </SectionCard>
                  </Box>
                )}
              </Grid.Col>
            </Grid>
          }
        />

        {isPhasedGeneral && clearance.milestones && clearance.milestones.length > 0 ? (
          <ClearanceMilestoneTimeline milestones={clearance.milestones} />
        ) : null}
      </Stack>
      {viewer}
    </PageContainer>
  );
}

function ClearanceHero({
  booking,
  clearance,
  stats,
  requestedLines,
}: {
  booking: ReturnType<typeof useBookingDetail>["data"];
  clearance: Freight.ClearanceView;
  stats: { pct: number; approved: number; total: number };
  requestedLines?: Freight.RequestedShipmentLines | null;
}) {
  const direction = booking?.tradeDirection ?? "—";
  const origin =
    booking?.originYard?.label ?? booking?.originYard?.code ?? "Origin";
  const destination =
    booking?.destinationYard?.label ??
    booking?.destinationYard?.code ??
    "Destination";

  return (
    <Paper withBorder radius="md" p="lg">
      <Group justify="space-between" align="flex-start" wrap="wrap" gap="lg">
        <Group gap="md" wrap="nowrap" style={{ minWidth: 0 }}>
          <ThemeIcon variant="light" color="edr-green" radius="md" size={52}>
            <ShieldCheck size={26} />
          </ThemeIcon>
          <Box style={{ minWidth: 0 }}>
            <Group gap={8} wrap="nowrap">
              <Text fw={800} fz={20} c="edr-text" truncate>
                {booking?.reference ?? "Clearance"}
              </Text>
              <Badge
                size="sm"
                variant="light"
                color={direction === "IMPORT" ? "edr-green" : "gray"}
                radius="sm"
              >
                {direction}
              </Badge>
              {clearance.includesCustoms ? (
                <Badge
                  size="sm"
                  variant="light"
                  color="edr-green"
                  radius="sm"
                  leftSection={<ShieldCheck size={12} />}
                >
                  Customs
                </Badge>
              ) : null}
            </Group>
            <Group gap={8} mt={6} wrap="nowrap">
              <Text size="sm" fw={600} truncate maw={160}>
                {origin}
              </Text>
              <ArrowRight size={15} className="shrink-0 text-muted-foreground" />
              <Text size="sm" fw={600} truncate maw={160}>
                {destination}
              </Text>
            </Group>
          </Box>
        </Group>

        <Box style={{ minWidth: 200, flex: 1, maxWidth: 320 }}>
          <Group justify="space-between" mb={6}>
            <Text size="xs" c="dimmed" fw={600}>
              Document review
            </Text>
            <Text size="xs" c="dimmed">
              {stats.approved}/{stats.total}
            </Text>
          </Group>
          <Progress value={stats.pct} color="edr-green" radius="xl" size="md" />
        </Box>
      </Group>

      {requestedLines ? (
        <>
          <Box my="md" h={1} bg="var(--mantine-color-default-border)" />
          <Group gap={10} align="center" wrap="wrap">
            <Text size="xs" fw={700} tt="uppercase" c="dimmed" lts="0.05em">
              Requested cargo
            </Text>
            <RequestedCargoChips lines={requestedLines} size="sm" />
          </Group>
        </>
      ) : null}
    </Paper>
  );
}

function ProgressStat({
  color,
  label,
  value,
}: {
  color: string;
  label: string;
  value: number;
}) {
  return (
    <Stack gap={2} align="center">
      <Text fw={700} fz={18} c="edr-text">
        {value}
      </Text>
      <Group gap={4} wrap="nowrap">
        <Box
          style={{
            width: 7,
            height: 7,
            borderRadius: 999,
            background: `var(--mantine-color-${color}-6)`,
          }}
        />
        <Text fz="11px" c="dimmed">
          {label}
        </Text>
      </Group>
    </Stack>
  );
}
