"use client";

import * as React from "react";

import { ArrowLeft, KeyRound, Plus, Save } from "lucide-react";
import Link from "next/link";
import { useRouter } from "next/navigation";
import { toast } from "sonner";

import { ListPageCard } from "@/app/dashboard/_components";
import { ErrorBanner } from "@/components/shared/error-banner";
import { Button } from "@/components/ui/button";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
import { Textarea } from "@/components/ui/textarea";
import { savePermission } from "@/components/admins/rbac/api/permissions-api";
import type { PermissionCatalogEntry } from "@/components/admins/rbac/types";

type CreatePermissionFormValues = {
  name: string;
  label: string;
  description: string;
};

const createPermissionDefaults: CreatePermissionFormValues = {
  name: "",
  label: "",
  description: "",
};

type CreatePermissionPageClientProps = {
  initialPermission?: PermissionCatalogEntry | null;
  initialErrorMessage?: string | null;
  requestedPermissionName?: string;
};

export function CreatePermissionPageClient({
  initialPermission = null,
  initialErrorMessage = null,
  requestedPermissionName,
}: CreatePermissionPageClientProps) {
  const router = useRouter();
  const isEditMode = Boolean(requestedPermissionName);
  const [form, setForm] = React.useState<CreatePermissionFormValues>(
    initialPermission
      ? permissionToFormValues(initialPermission)
      : { ...createPermissionDefaults, name: requestedPermissionName ?? "" },
  );
  const [submitting, setSubmitting] = React.useState(false);
  const [loadErrorMessage] = React.useState(initialErrorMessage);

  const handleSubmit = async (event: React.FormEvent<HTMLFormElement>) => {
    event.preventDefault();

    if (!form.name.trim() || !form.label.trim()) {
      toast.error("Name and label are required.");
      return;
    }

    setSubmitting(true);

    try {
      const data = await savePermission(isEditMode ? "update" : "create", form);

      toast.success(
        data.message ??
          `Permission "${form.name}" ${isEditMode ? "updated" : "created"}.`,
      );
      router.push("/dashboard/admins/access/permissions");
    } catch (error) {
      const message =
        error instanceof Error
          ? error.message
          : isEditMode
            ? "Could not update permission."
            : "Could not create permission.";
      toast.error(message);
    } finally {
      setSubmitting(false);
    }
  };

  return (
    <ListPageCard
      icon={KeyRound}
      title={isEditMode ? "Update permission" : "Create permission"}
      description={
        isEditMode
          ? "Edit permission metadata in the RBAC registry."
          : "Add a permission to the RBAC registry and make it available for roles and assignments."
      }
      breadcrumb={[
        { label: "Admins & Access", href: "/dashboard/admins/users" },
        { label: "Permissions", href: "/dashboard/admins/access/permissions" },
        { label: isEditMode ? "Update" : "Create" },
      ]}
      actions={
        <Button type="button" variant="outline" size="sm" asChild>
          <Link href="/dashboard/admins/access/permissions">
            <ArrowLeft className="size-4" />
            Back to permissions
          </Link>
        </Button>
      }
    >
      <ErrorBanner message={loadErrorMessage} className="mb-4" />
      <form className="space-y-6" onSubmit={handleSubmit}>
        <FormSection
          title="Permission details"
          description="Create or update the permission fields returned by the catalog endpoint."
        >
          <div className="grid gap-4 md:grid-cols-2">
            <FormField label="Permission name" htmlFor="permission-name" required>
              <Input
                id="permission-name"
                value={form.name}
                onChange={(event) => setFormValue(setForm, "name", event.target.value)}
                placeholder="customers_front.index"
                className="font-mono"
                disabled={isEditMode}
              />
            </FormField>
            <FormField label="Label" htmlFor="permission-label" required>
              <Input
                id="permission-label"
                value={form.label}
                onChange={(event) => setFormValue(setForm, "label", event.target.value)}
                placeholder="View Customer Backend"
              />
            </FormField>
          </div>
          <FormField label="Description" htmlFor="permission-description">
            <Textarea
              id="permission-description"
              value={form.description}
              onChange={(event) =>
                setFormValue(setForm, "description", event.target.value)
              }
              placeholder="List And View Customers From Backend"
              className="min-h-28"
            />
          </FormField>
        </FormSection>

        <div className="sticky bottom-0 -mx-4 flex flex-col-reverse gap-2 border-t bg-background/95 px-4 py-4 backdrop-blur sm:flex-row sm:justify-end lg:-mx-6 lg:px-6">
          <Button type="button" variant="outline" asChild disabled={submitting}>
            <Link href="/dashboard/admins/access/permissions">Cancel</Link>
          </Button>
          <Button type="submit" disabled={submitting || Boolean(loadErrorMessage)}>
            {isEditMode ? <Save className="size-4" /> : <Plus className="size-4" />}
            {submitting
              ? isEditMode
                ? "Updating..."
                : "Creating..."
              : isEditMode
                ? "Update permission"
                : "Create permission"}
          </Button>
        </div>
      </form>
    </ListPageCard>
  );
}

function setFormValue<Key extends keyof CreatePermissionFormValues>(
  setForm: React.Dispatch<React.SetStateAction<CreatePermissionFormValues>>,
  key: Key,
  value: CreatePermissionFormValues[Key],
) {
  setForm((current) => ({ ...current, [key]: value }));
}

function permissionToFormValues(permission: PermissionCatalogEntry): CreatePermissionFormValues {
  return {
    name: permission.name,
    label: permission.label,
    description: permission.description,
  };
}

function FormSection({
  title,
  description,
  children,
}: {
  title: string;
  description: string;
  children: React.ReactNode;
}) {
  return (
    <section className="rounded-2xl border bg-card p-5 shadow-xs">
      <div className="mb-5">
        <h3 className="font-medium text-base">{title}</h3>
        <p className="mt-1 text-muted-foreground text-sm">{description}</p>
      </div>
      <div className="space-y-4">{children}</div>
    </section>
  );
}

function FormField({
  label,
  htmlFor,
  required = false,
  children,
}: {
  label: string;
  htmlFor: string;
  required?: boolean;
  children: React.ReactNode;
}) {
  return (
    <div className="space-y-2">
      <Label htmlFor={htmlFor} className="text-xs">
        {label}
        {required ? <span className="text-destructive"> *</span> : null}
      </Label>
      {children}
    </div>
  );
}

