"use client";

import * as React from "react";
import { Card } from "@/components/ui/card";
import { Badge, type BadgeProps } from "@/components/ui/badge";
import { cn } from "@/lib/utils";

/**
 * AlertCard — collapsible alert banner with severity + optional count chip.
 *
 * Replaces the ad-hoc collapsible alert cards in bill-cash-conflicts.tsx
 * and filing-reminders-banner.tsx with a single primitive.
 *
 * Usage:
 *   <AlertCard
 *     severity="critical"
 *     title="Stop what you're doing"
 *     count={10}
 *     defaultOpen
 *   >
 *     ...body content (only renders when open)...
 *   </AlertCard>
 *
 * Subcomponents:
 *   - AlertCardSummary: a row of metric chip totals under the header.
 *   - AlertCardRow: a single styled list row inside the body.
 */

export type AlertSeverity =
  | "critical"
  | "warning"
  | "advisory"
  | "info"
  | "success";

const SEVERITY_CARD_CLASS: Record<AlertSeverity, string> = {
  critical: "border-destructive/30 bg-destructive/5",
  warning: "border-amber-500/30 bg-amber-500/5",
  advisory: "border-violet-500/30 bg-violet-500/5",
  info: "border-blue-500/30 bg-blue-500/5",
  success: "border-emerald-500/30 bg-emerald-500/5",
};

const SEVERITY_LABEL: Record<AlertSeverity, string> = {
  critical: "Critical",
  warning: "Warning",
  advisory: "Advisory",
  info: "Info",
  success: "Success",
};

// Map to existing Badge variants where available; fall back to inline classes
// for tones not present in the Badge variant map (amber/violet/emerald).
type ChipStyle =
  | { variant: BadgeProps["variant"]; className?: string }
  | { variant?: undefined; className: string };

const SEVERITY_CHIP: Record<AlertSeverity, ChipStyle> = {
  critical: { variant: "destructive" },
  warning: {
    className:
      "border-transparent bg-amber-100 text-amber-900 dark:bg-amber-900/30 dark:text-amber-100",
  },
  advisory: {
    className:
      "border-transparent bg-violet-100 text-violet-900 dark:bg-violet-900/30 dark:text-violet-100",
  },
  info: { variant: "info" },
  success: {
    className:
      "border-transparent bg-emerald-100 text-emerald-900 dark:bg-emerald-900/30 dark:text-emerald-100",
  },
};

function ChevronIcon({ open }: { open: boolean }) {
  return (
    <svg
      aria-hidden="true"
      viewBox="0 0 20 20"
      className={cn(
        "h-4 w-4 shrink-0 text-muted-foreground transition-transform",
        open ? "rotate-180" : "rotate-0",
      )}
      fill="none"
      stroke="currentColor"
      strokeWidth="2"
    >
      <path d="M5 7l5 5 5-5" strokeLinecap="round" strokeLinejoin="round" />
    </svg>
  );
}

function CloseIcon() {
  return (
    <svg
      aria-hidden="true"
      viewBox="0 0 20 20"
      className="h-3.5 w-3.5"
      fill="none"
      stroke="currentColor"
      strokeWidth="2"
    >
      <path d="M5 5l10 10M15 5l-10 10" strokeLinecap="round" strokeLinejoin="round" />
    </svg>
  );
}

export function AlertCard({
  severity,
  title,
  count,
  defaultOpen = false,
  open: openProp,
  onOpenChange,
  dismissable = false,
  onDismiss,
  className,
  bodyClassName,
  headerClassName,
  hideChip = false,
  icon,
  trailing,
  children,
}: {
  severity: AlertSeverity;
  title: React.ReactNode;
  count?: number;
  defaultOpen?: boolean;
  open?: boolean;
  onOpenChange?: (open: boolean) => void;
  dismissable?: boolean;
  onDismiss?: () => void;
  className?: string;
  bodyClassName?: string;
  headerClassName?: string;
  hideChip?: boolean;
  icon?: React.ReactNode;
  trailing?: React.ReactNode;
  children?: React.ReactNode;
}) {
  const [internalOpen, setInternalOpen] = React.useState(defaultOpen);
  const isControlled = openProp !== undefined;
  const open = isControlled ? (openProp as boolean) : internalOpen;

  const setOpen = React.useCallback(
    (next: boolean) => {
      if (!isControlled) setInternalOpen(next);
      onOpenChange?.(next);
    },
    [isControlled, onOpenChange],
  );

  const chip = SEVERITY_CHIP[severity];
  const chipLabel = SEVERITY_LABEL[severity];
  const chipText = count !== undefined ? `${count} ${chipLabel}` : chipLabel;

  return (
    <Card className={cn(SEVERITY_CARD_CLASS[severity], className)}>
      <div className={cn("flex items-center gap-3 p-4", headerClassName)}>
        <button
          type="button"
          onClick={() => setOpen(!open)}
          aria-expanded={open}
          className="flex flex-1 items-center gap-2 text-left min-w-0"
        >
          {icon !== undefined && (
            <span className="shrink-0" aria-hidden>
              {icon}
            </span>
          )}
          {!hideChip && (
            <Badge
              variant={chip.variant}
              className={cn("text-[10px] shrink-0", chip.className)}
            >
              {chipText}
            </Badge>
          )}
          <span className="text-sm font-semibold truncate">{title}</span>
          <span className="ml-auto flex items-center gap-2">
            {trailing}
            <ChevronIcon open={open} />
          </span>
        </button>
        {dismissable && (
          <button
            type="button"
            onClick={() => onDismiss?.()}
            aria-label="Dismiss"
            className="shrink-0 rounded p-1 text-muted-foreground hover:bg-muted hover:text-foreground"
          >
            <CloseIcon />
          </button>
        )}
      </div>
      {open && children !== undefined && (
        <div
          className={cn(
            "px-4 pb-4 pt-0 border-t border-current/10",
            bodyClassName,
          )}
        >
          {children}
        </div>
      )}
    </Card>
  );
}

/**
 * AlertCardSummary — a horizontal row of metric chips, intended for the
 * optional totals strip that bill-cash-conflicts.tsx puts in its header.
 *
 * Usage:
 *   <AlertCardSummary>
 *     <Badge variant="destructive">3 critical</Badge>
 *     <Badge variant="warning">7 tight</Badge>
 *   </AlertCardSummary>
 */
export function AlertCardSummary({
  className,
  children,
}: {
  className?: string;
  children: React.ReactNode;
}) {
  return (
    <div className={cn("flex flex-wrap items-center gap-2", className)}>
      {children}
    </div>
  );
}

/**
 * AlertCardRow — a single list row with consistent styling for use inside
 * the body of an AlertCard.
 */
export function AlertCardRow({
  className,
  children,
}: {
  className?: string;
  children: React.ReactNode;
}) {
  return (
    <div
      className={cn(
        "flex items-center justify-between gap-3 rounded-md border border-current/10 bg-background/40 px-3 py-2 text-sm",
        className,
      )}
    >
      {children}
    </div>
  );
}
