import {
  Alert,
  Badge,
  Button,
  Card,
  Group,
  SimpleGrid,
  Stack,
  Text,
  TextInput,
  Title,
} from "@mantine/core";
import { useForm } from "@mantine/form";
import { notifications } from "@mantine/notifications";
import { IconRefresh } from "@tabler/icons-react";
import { useNavigate } from "react-router";
import { updatePromoCode } from "@/lib/features/promo-codes/action";
import type {
  PromoCode,
  PromoCodeFormValues,
} from "@/lib/features/promo-codes/types";
import type { AccessScope } from "@/lib/features/types";
import {
  buildUpdatePayload,
  mapPromoToForm,
  validateUpdateForm,
} from "../form";
import { extractErrorMessage, extractFieldErrors } from "../errors";
import { PromoCodeForm } from "../PromoCodeForm";
import { PromoLogsPanel } from "./PromoLogsPanel";
import { useEffect, useState } from "react";
import { useRoleAccess } from "@/hooks/useRoleAccess";

interface PromoCodeDetailsSectionProps {
  promoId: string;
  promo: PromoCode;
  accessScope: AccessScope;
  onSaved?: () => void;
}

const getPromoId = (promo: PromoCode) =>
  promo.id || promo.promoCodeId || promo.promo_code_id || "";

const fmt = (raw: string) => {
  if (!raw) return "-";
  const d = new Date(raw);
  return Number.isFinite(d.getTime()) ? d.toLocaleString() : raw;
};

export const PromoCodeDetailsSection: React.FC<
  PromoCodeDetailsSectionProps
> = ({ promoId, promo, accessScope, onSaved }) => {
  const navigate = useNavigate();
  const [busy, setBusy] = useState(false);
  const [refreshing, setRefreshing] = useState(false);
  const { checkClientAccess } = useRoleAccess();
  const canViewAdminLogs = checkClientAccess("read", "admin-logs");
  const form = useForm<PromoCodeFormValues>({
    initialValues: mapPromoToForm(promo),
    validate: validateUpdateForm,
  });

  const createdAt =
    (promo as any)?.createdAt ?? (promo as any)?.created_at ?? "";
  const updatedAt =
    (promo as any)?.updatedAt ?? (promo as any)?.updated_at ?? "";
  const resolvedId = promoId || getPromoId(promo);
  const readOnly = !accessScope.update;
  const isActive =
    typeof promo.isActive === "boolean" ? promo.isActive : promo.is_active;

  // Re-sync the form when the server promo changes (load + after save).
  useEffect(() => {
    const next = mapPromoToForm(promo);
    form.setValues(next);
    form.resetDirty(next);
  }, [promo]);

  const handleRefresh = async () => {
    setRefreshing(true);
    try {
      if (onSaved) await onSaved();
      else navigate(".", { replace: true });
      form.setValues(mapPromoToForm(promo));
      form.resetDirty();
    } finally {
      setRefreshing(false);
    }
  };

  const handleSubmit = async (values: PromoCodeFormValues) => {
    if (!accessScope.update) return;
    if (!resolvedId.trim()) {
      notifications.show({
        color: "red",
        message: "Missing promo code ID; cannot update.",
      });
      return;
    }
    const payload = buildUpdatePayload(values, mapPromoToForm(promo));
    if (!Object.keys(payload).length) {
      notifications.show({
        color: "yellow",
        message: "No changes to save.",
      });
      return;
    }
    setBusy(true);
    try {
      const res = await updatePromoCode(resolvedId.trim(), payload);
      if (res.success) {
        notifications.show({
          color: "green",
          message: res.message || "Promo code updated successfully",
        });
        if (onSaved) onSaved();
        else navigate(".", { replace: true });
      } else {
        const message = extractErrorMessage(res, "Failed to update promo code");
        const fieldErrors = extractFieldErrors(res);
        if (Object.keys(fieldErrors).length) {
          form.setErrors(fieldErrors);
        } else {
          form.setErrors({ _form: message });
        }
        notifications.show({ color: "red", message });
      }
    } catch (e: any) {
      const message = extractErrorMessage(e, "Failed to update promo code");
      const fieldErrors = extractFieldErrors(e);
      if (Object.keys(fieldErrors).length) {
        form.setErrors(fieldErrors);
      } else {
        form.setErrors({ _form: message });
      }
      notifications.show({ color: "red", message });
    } finally {
      setBusy(false);
    }
  };

  const handleSubmitError = (errors: typeof form.errors) => {
    const firstError = Object.values(errors).find(
      (value): value is string => typeof value === "string" && value.length > 0,
    );
    notifications.show({
      color: "red",
      message: firstError || "Please fix the highlighted fields before saving.",
    });
  };

  return (
    <Stack gap="md">
      <Card
        withBorder
        radius="lg"
        p="md"
        style={{ position: "sticky", top: 0, zIndex: 5 }}
      >
        <Group justify="space-between" align="center" wrap="wrap">
          <Group gap="sm">
            <Title order={4}>Promo Code Details</Title>
            {typeof isActive === "boolean" && (
              <Badge color={isActive ? "green" : "gray"} variant="light">
                {isActive ? "Active" : "Inactive"}
              </Badge>
            )}
            {readOnly && (
              <Badge color="gray" variant="light">
                View only
              </Badge>
            )}
          </Group>
          <Group gap="xs">
            <Button
              variant="light"
              color="gray"
              leftSection={<IconRefresh size={16} />}
              onClick={handleRefresh}
              loading={refreshing}
            >
              Refresh
            </Button>
          </Group>
        </Group>
      </Card>

      <Card withBorder radius="lg" p="lg">
        <form onSubmit={form.onSubmit(handleSubmit, handleSubmitError)}>
          <Stack gap="md">
            {readOnly && (
              <Alert color="gray" variant="light">
                <Text size="xs">
                  View only — you do not have update permission.
                </Text>
              </Alert>
            )}

            <div>
              <Text size="xs" fw={600} c="dimmed" tt="uppercase" mb="xs">
                Metadata
              </Text>
              <SimpleGrid cols={{ base: 1, sm: 3 }} spacing="sm">
                <TextInput label="Created At" value={fmt(createdAt)} disabled />
                <TextInput label="Updated At" value={fmt(updatedAt)} disabled />
                <TextInput label="Promo Code ID" value={resolvedId} disabled />
              </SimpleGrid>
            </div>

            <PromoCodeForm form={form} isUpdate readOnly={readOnly} />

            {form.errors._form ? (
              <Alert color="red" variant="light">
                <Text size="sm">{form.errors._form}</Text>
              </Alert>
            ) : null}

            {!readOnly && (
              <Group justify="flex-end" mt="sm">
                <Button
                  type="submit"
                  loading={busy}
                  disabled={!form.isDirty()}
                  title={
                    form.isDirty() ? undefined : "Edit a field to enable saving"
                  }
                >
                  Save Changes
                </Button>
              </Group>
            )}
          </Stack>
        </form>
      </Card>

      {canViewAdminLogs && (
        <Card withBorder radius="lg" p="lg">
          <Text fw={700} mb="sm">
            Change history
          </Text>
          <PromoLogsPanel promoId={resolvedId || null} />
        </Card>
      )}
    </Stack>
  );
};
