import type { Freight } from "@edr/types";
import { Skeleton, Stack } from "@mantine/core";
import { MapPin } from "lucide-react";
import { useCallback, useEffect, useMemo } from "react";
import { Controller, type UseFormReturn } from "react-hook-form";
import { ContractFormInputValues, type ContractFormValues } from "./schema";
import { getRouteDirection } from "./helpers";
import { SelectField, StepLabel } from "./shared";

type ContractForm = UseFormReturn<
  ContractFormInputValues,
  any,
  ContractFormValues
>;

export function Step4Route({
  form,
  referenceData,
  isLoading,
}: {
  form: ContractForm;
  referenceData?: Freight.BookingReferenceData;
  isLoading?: boolean;
}) {
  const originYard = form.watch("originYard");
  const destinationYard = form.watch("destinationYard");
  const operationType = form.watch("operationType");

  const { originCountry, destinationCountry } = useMemo(() => {
    switch (operationType) {
      case "import":
      case "import_ff":
        return { originCountry: "Djibouti", destinationCountry: "Ethiopia" };
      case "export":
      case "export_ff":
        return { originCountry: "Ethiopia", destinationCountry: "Djibouti" };
      case "intercity":
        return { originCountry: "Ethiopia", destinationCountry: "Ethiopia" };
      default:
        return { originCountry: null, destinationCountry: null };
    }
  }, [operationType]);

  const yardOptions = useMemo(() => {
    if (!referenceData?.yard) return [];
    return referenceData.yard.map((y) => ({ value: y.id, label: y.name }));
  }, [referenceData]);

  const yardsForSide = useCallback(
    (country: string | null, excludeYardId: string) =>
      yardOptions
        .filter((o) => o.value !== excludeYardId)
        .filter((o) => {
          if (!country) return true;
          const yard = referenceData?.yard.find((y) => y.id === o.value);
          return yard?.country === country;
        }),
    [yardOptions, referenceData],
  );

  const originData = useMemo(
    () => yardsForSide(originCountry, destinationYard),
    [yardsForSide, originCountry, destinationYard],
  );
  const destData = useMemo(
    () => yardsForSide(destinationCountry, originYard),
    [yardsForSide, destinationCountry, originYard],
  );

  const origin = referenceData?.yard.find((y) => y.id === originYard);
  const dest = referenceData?.yard.find((y) => y.id === destinationYard);
  const direction = getRouteDirection(origin, dest);

  // Clear yards that no longer match the operation's required country.
  // Skipped right after a hydration `form.reset()` (edit mode) — a saved
  // contract's yards are trusted as-is until the customer changes something
  // live; `isDirty` is false only in that pristine post-hydration render.
  useEffect(() => {
    if (!form.formState.isDirty) return;
    if (originCountry && origin && origin.country !== originCountry) {
      form.setValue("originYard", "");
    }
  }, [originCountry, origin, form]);
  useEffect(() => {
    if (!form.formState.isDirty) return;
    if (destinationCountry && dest && dest.country !== destinationCountry) {
      form.setValue("destinationYard", "");
    }
  }, [destinationCountry, dest, form]);

  const directionStyle: Record<string, string> = {
    EXPORT: "bg-sky-50 text-sky-800 border-sky-200",
    IMPORT: "bg-amber-50 text-amber-800 border-amber-200",
    DOMESTIC: "bg-gray-100 text-gray-600 border-gray-200",
  };
  const directionLabel: Record<string, string> = {
    EXPORT: "Export workflow (inside country to outside country)",
    IMPORT: "Import workflow (outside country to inside country)",
    DOMESTIC: "Domestic corridor",
  };

  const stationSelectDisabled = yardOptions.length === 0;

  return (
    <Stack gap={16}>
      {isLoading ? (
        <LoadingSkeleton />
      ) : (
        <div className="space-y-3">
          <StepLabel>Route</StepLabel>
          <div className="grid gap-4 sm:grid-cols-2">
            <Controller
              name="originYard"
              control={form.control}
              render={({ field, fieldState }) => (
                <SelectField
                  field={field}
                  error={fieldState.error}
                  label="Origin Yard *"
                  placeholder="Select origin..."
                  disabled={stationSelectDisabled}
                  data={originData}
                />
              )}
            />
            <Controller
              name="destinationYard"
              control={form.control}
              render={({ field, fieldState }) => (
                <SelectField
                  field={field}
                  error={fieldState.error}
                  label="Destination Yard *"
                  placeholder="Select destination..."
                  disabled={stationSelectDisabled}
                  data={destData}
                />
              )}
            />
          </div>
          {direction && (
            <div
              className={`flex items-center gap-2 rounded-lg border px-3 py-2 text-xs font-medium ${directionStyle[direction]}`}
            >
              <MapPin className="h-3.5 w-3.5 shrink-0" />
              {directionLabel[direction]}
            </div>
          )}

        </div>
      )}
    </Stack>
  );
}

function LoadingSkeleton() {
  return (
    <div className="space-y-4 rounded-xl border border-gray-200 p-4">
      <div className="grid gap-3 sm:grid-cols-2">
        <Stack gap={8}>
          <Skeleton height={12} w={80} radius="sm" />
          <Skeleton height={40} radius="md" />
        </Stack>
        <Stack gap={8}>
          <Skeleton height={12} w={96} radius="sm" />
          <Skeleton height={40} radius="md" />
        </Stack>
      </div>
      <Skeleton height={32} radius="md" />
    </div>
  );
}
