"use client";

import { useId, useState, type ReactNode } from "react";
import { useRouter } from "next/navigation";
import { ChevronDown } from "lucide-react";
import { saveEventSettingsAction } from "@/lib/actions/organizations";
import { useRun } from "@/components/features/accounts/use-run";
import { EdField, Pill, YesNo, edInput } from "@/components/features/page-editor/ed-ui";
import { MediaPicker } from "@/components/features/page-editor/media-picker";
import { cn } from "@/lib/utils";
import { SettingsFrame } from "./ed-table";

export interface EventSettingsForm {
  siteId: string; timezone: string; name: string; startsAt: string; endsAt: string; coverMediaId: string | null;
  categoryTypes: string[]; dpaGroupId: string; showForgotPassword: boolean; allowProfileLock: boolean; tagIds: string[]; businessSectors: string[];
  supportContactUserId: string; ssoEnabled: boolean; ssoSecretSet: boolean;
}
interface Options { libraries: { key: string; label: string }[]; dpaGroups: { id: string; name: string }[]; tags: { id: string; name: string }[]; contacts: { id: string; label: string }[]; sectors: string[] }
interface Props { orgId: string; orgName: string; base: string; sites: { id: string; name: string }[]; form: EventSettingsForm | null; options?: Options }

function Section({ id, title, open, onToggle, children }: { id: string; title: string; open: boolean; onToggle: () => void; children: ReactNode }) {
  return (
    <section className="rounded-2xl bg-white">
      <h3>
        <button type="button" id={`${id}-h`} aria-expanded={open} aria-controls={`${id}-p`} onClick={onToggle} className="flex w-full items-center justify-between px-5 py-4 text-left text-sm font-bold text-[var(--ed-ink)]">
          {title}<ChevronDown className={cn("size-4 transition", open && "rotate-180")} aria-hidden />
        </button>
      </h3>
      <div id={`${id}-p`} role="region" aria-labelledby={`${id}-h`} hidden={!open} className="space-y-5 px-5 pb-5">{children}</div>
    </section>
  );
}

function randomSecret() {
  const b = new Uint8Array(32);
  crypto.getRandomValues(b);
  return Array.from(b, (x) => x.toString(16).padStart(2, "0")).join("");
}

function Checks({ legend, hint, items, value, onChange, cols }: { legend: string; hint?: string; items: { id: string; label: string }[]; value: string[]; onChange: (v: string[]) => void; cols?: boolean }) {
  return (
    <fieldset className="space-y-2">
      <legend className="text-xs font-bold text-[var(--ed-ink)]">{legend}</legend>
      {hint ? <p className="text-xs text-[var(--ed-soft)]">{hint}</p> : null}
      <div className={cn("grid gap-1", cols && "sm:grid-cols-2")}>
        {items.map((i) => (
          <label key={i.id} className="flex items-center gap-2 text-sm text-[var(--ed-ink)]">
            <input type="checkbox" checked={value.includes(i.id)} onChange={(e) => onChange(e.target.checked ? [...value, i.id] : value.filter((x) => x !== i.id))} />{i.label}
          </label>
        ))}
        {items.length === 0 ? <p className="text-sm text-[var(--ed-soft)]">None available.</p> : null}
      </div>
    </fieldset>
  );
}

export function EventSettingsManager({ orgId, orgName, base, sites, form, options }: Props) {
  const router = useRouter();
  const { pending, msg, errors, run } = useRun();
  const idp = useId();
  const [f, setF] = useState<EventSettingsForm | null>(form);
  const [open, setOpen] = useState<Record<string, boolean>>({ general: true });
  const [secret, setSecret] = useState("");
  const [showSecret, setShowSecret] = useState(false);
  const toggle = (k: string) => setOpen((s) => ({ ...s, [k]: !s[k] }));
  const patch = (p: Partial<EventSettingsForm>) => setF((x) => (x ? { ...x, ...p } : x));

  if (!f || !options) {
    return <SettingsFrame orgName={orgName} title="Event Settings"><p className="rounded-2xl bg-white p-5 text-sm text-[var(--ed-soft)]">Add a website to this organization to edit its event settings.</p></SettingsFrame>;
  }
  const submit = () => run(() => saveEventSettingsAction(orgId, {
    siteId: f.siteId, name: f.name, startsAt: f.startsAt, endsAt: f.endsAt, coverMediaId: f.coverMediaId, categoryTypes: f.categoryTypes,
    dpaGroupId: f.dpaGroupId, showForgotPassword: f.showForgotPassword, allowProfileLock: f.allowProfileLock, tagIds: f.tagIds,
    businessSectors: f.businessSectors, supportContactUserId: f.supportContactUserId, ssoEnabled: f.ssoEnabled, ...(secret ? { ssoSecret: secret } : {}),
  }), () => { if (secret) patch({ ssoSecretSet: true }); setSecret(""); setShowSecret(false); });

  return (
    <SettingsFrame orgName={orgName} title="Event Settings" actions={
      <>
        <label htmlFor={`${idp}-site`} className="self-center text-sm font-bold text-[var(--ed-ink)]">Website</label>
        <select id={`${idp}-site`} value={f.siteId} onChange={(e) => router.push(`${base}?tab=event&site=${e.target.value}`)} className={cn(edInput, "w-64 rounded-full bg-white")}>
          {sites.map((s) => <option key={s.id} value={s.id}>{s.name}</option>)}
        </select>
      </>
    }>
      <Section id={`${idp}-general`} title="General" open={!!open.general} onToggle={() => toggle("general")}>
        <EdField id={`${idp}-name`} label="Name: *" hint="Please enter a name for this website" error={errors.name}>
          <input id={`${idp}-name`} value={f.name} maxLength={120} onChange={(e) => patch({ name: e.target.value })} className={cn(edInput, "rounded-xl")} aria-describedby={`${idp}-name-hint`} />
        </EdField>
        <div className="space-y-1">
          <p className="text-xs font-bold text-[var(--ed-ink)]">Cover Picture:</p>
          <MediaPicker key={f.siteId} siteId={f.siteId} label="cover picture" value={f.coverMediaId} onChange={(id) => patch({ coverMediaId: id })} />
        </div>
        <div className="grid gap-4 sm:grid-cols-2">
          <EdField id={`${idp}-start`} label="Start Date: *" hint={`Time zone: ${f.timezone}`} error={errors.startsAt}>
            <input id={`${idp}-start`} type="datetime-local" value={f.startsAt} onChange={(e) => patch({ startsAt: e.target.value })} className={cn(edInput, "rounded-xl")} aria-describedby={`${idp}-start-hint`} />
          </EdField>
          <EdField id={`${idp}-end`} label="End Date: *" hint={`Time zone: ${f.timezone}`} error={errors.endsAt}>
            <input id={`${idp}-end`} type="datetime-local" value={f.endsAt} onChange={(e) => patch({ endsAt: e.target.value })} className={cn(edInput, "rounded-xl")} aria-describedby={`${idp}-end-hint`} />
          </EdField>
        </div>
      </Section>

      <Section id={`${idp}-mods`} title="Modules and Configuration" open={!!open.mods} onToggle={() => toggle("mods")}>
        <Checks legend="Categories:" hint="Select which categories are applicable within this website's libraries:" items={options.libraries.map((l) => ({ id: l.key, label: l.label }))} value={f.categoryTypes} onChange={(v) => patch({ categoryTypes: v })} />
        <EdField id={`${idp}-dpa`} label="DPA Settings:">
          <select id={`${idp}-dpa`} value={f.dpaGroupId} onChange={(e) => patch({ dpaGroupId: e.target.value })} className={cn(edInput, "rounded-xl")}>
            <option value="">- Select -</option>
            {options.dpaGroups.map((g) => <option key={g.id} value={g.id}>{g.name}</option>)}
          </select>
        </EdField>
        <EdField id={`${idp}-fp`} label="Zone login:">
          <select id={`${idp}-fp`} value={f.showForgotPassword ? "yes" : "no"} onChange={(e) => patch({ showForgotPassword: e.target.value === "yes" })} className={cn(edInput, "rounded-xl")}>
            <option value="no">Don&apos;t display forgotten password link</option>
            <option value="yes">Display forgotten password link</option>
          </select>
        </EdField>
        <EdField id={`${idp}-pl`} label="Zone Profile Lock">
          <select id={`${idp}-pl`} value={f.allowProfileLock ? "yes" : "no"} onChange={(e) => patch({ allowProfileLock: e.target.value === "yes" })} className={cn(edInput, "rounded-xl")}>
            <option value="no">Don&apos;t allow exhibitors to lock their profile</option>
            <option value="yes">Allow exhibitors to lock their profile</option>
          </select>
        </EdField>
        <Checks legend="Tags:" hint={options.tags.length ? undefined : "No tags have been created for this website yet."} items={options.tags.map((t) => ({ id: t.id, label: t.name }))} value={f.tagIds} onChange={(v) => patch({ tagIds: v })} cols />
        <Checks legend="Business Sector:" items={options.sectors.map((s) => ({ id: s, label: s }))} value={f.businessSectors} onChange={(v) => patch({ businessSectors: v })} cols />
      </Section>

      <Section id={`${idp}-support`} title="Support" open={!!open.support} onToggle={() => toggle("support")}>
        <EdField id={`${idp}-contact`} label="Main Contact:">
          <select id={`${idp}-contact`} value={f.supportContactUserId} onChange={(e) => patch({ supportContactUserId: e.target.value })} className={cn(edInput, "rounded-xl")}>
            <option value="">- Select -</option>
            {options.contacts.map((c) => <option key={c.id} value={c.id}>{c.label}</option>)}
          </select>
        </EdField>
      </Section>

      <Section id={`${idp}-sso`} title="Single Sign-On" open={!!open.sso} onToggle={() => toggle("sso")}>
        <p className="text-sm text-[var(--ed-ink)]">Single Sign-On (SSO) can be used to allow application providers to generate a secure login URL for an Exhibitor Contact without needing their login details.</p>
        <div className="space-y-1">
          <p className="text-xs font-bold text-[var(--ed-ink)]">Enabled for E-Zone:</p>
          <p className="text-xs text-[var(--ed-soft)]">If not enabled, no old or new SSO URLs will work.</p>
          <YesNo value={f.ssoEnabled} onChange={(v) => patch({ ssoEnabled: v })} label="Enabled for E-Zone" />
        </div>
        <EdField id={`${idp}-secret`} label="Exhibitor Shared Secret" hint={f.ssoSecretSet ? "A secret is set and is not shown again. Enter a new one to replace it." : "Secret key used to generate signed SSO URLs for Exhibitor Contacts."} error={errors.ssoSecret}>
          <div className="flex gap-2">
            <input id={`${idp}-secret`} type={showSecret ? "text" : "password"} autoComplete="off" value={secret} maxLength={128} placeholder={f.ssoSecretSet ? "••••••••••••" : ""} onChange={(e) => setSecret(e.target.value)} className={cn(edInput, "rounded-xl")} aria-describedby={`${idp}-secret-hint`} />
            <Pill variant="grey" onClick={() => { setSecret(randomSecret()); setShowSecret(true); }}>Generate</Pill>
          </div>
        </EdField>
      </Section>

      <div role="region" aria-label="Event settings actions" className="sticky bottom-0 z-30 flex items-center justify-end gap-3 rounded-3xl bg-[var(--ed-dark)] px-4 py-3 text-white shadow-xl">
        <div className="flex-1 text-xs" aria-live="polite">{msg ? <span className={cn("font-bold", msg.ok ? "text-[#9be7c9]" : "text-[#ffb4c8]")}>{msg.text}</span> : null}</div>
        <Pill variant="green" disabled={pending} onClick={submit}>{pending ? "Saving…" : "Save"}</Pill>
      </div>
    </SettingsFrame>
  );
}
