"use client";

import { Suspense, useEffect, useMemo, useState } from "react";
import { useSearchParams } from "next/navigation";
import { Pencil, X } from "lucide-react";
import { customerApi } from "@/lib/api/customer";
import { ApiException } from "@/lib/api/client";
import { identityErrors } from "@/lib/validation";
import { useToken } from "@/lib/auth/useToken";
import { useAuth } from "@/lib/auth/AuthContext";
import { authApi } from "@/lib/api/auth";
import type { ApiProfile } from "@/lib/api/types";
import Loader from "@/components/ui/Loader";
import KycStatusBanner from "@/components/dashboard/KycStatusBanner";
import { toast } from "sonner";
import { formatDateShort } from "@/lib/utils";

type Errors = Record<string, string[]>;

function Field({
  label,
  name,
  value,
  onChange,
  required,
  type = "text",
  placeholder,
  disabled,
  errors,
  hint,
}: {
  label: string;
  name: string;
  value: string;
  onChange: (v: string) => void;
  required?: boolean;
  type?: string;
  placeholder?: string;
  disabled?: boolean;
  errors?: Errors;
  hint?: string;
}) {
  const err = errors?.[name]?.[0];
  return (
    <div>
      <label className="mb-1 block text-xs font-medium text-gray-700">
        {label}
        {required && <span className="text-red-500"> *</span>}
      </label>
      <input
        type={type}
        value={value}
        placeholder={placeholder ?? `Enter ${label.toLowerCase()}`}
        disabled={disabled}
        onChange={(e) => onChange(e.target.value)}
        className="w-full rounded-lg border border-gray-200 px-3 py-2 text-sm focus:border-[#CC1414] focus:outline-none focus:ring-1 focus:ring-[#CC1414] disabled:bg-gray-50 disabled:text-gray-500"
      />
      {hint && !err && <p className="mt-1 text-xs text-gray-500">{hint}</p>}
      {err && <p className="mt-1 text-xs text-red-600">{err}</p>}
    </div>
  );
}

function Section({ title, children }: { title: string; children: React.ReactNode }) {
  return (
    <div className="rounded-xl bg-white p-5 shadow-sm ring-1 ring-gray-100">
      <h3 className="mb-4 text-sm font-semibold text-gray-900">{title}</h3>
      <div className="grid grid-cols-1 gap-4 md:grid-cols-2">{children}</div>
    </div>
  );
}

function DetailRow({ label, value }: { label: string; value?: string | null }) {
  return (
    <div>
      <div className="text-xs font-medium text-gray-500">{label}</div>
      <div className="mt-1 text-sm text-gray-900">{value?.trim() || "—"}</div>
    </div>
  );
}

function ViewSection({ title, children }: { title: string; children: React.ReactNode }) {
  return (
    <div className="rounded-xl bg-white p-5 shadow-sm ring-1 ring-gray-100">
      <h3 className="mb-4 text-sm font-semibold text-gray-900">{title}</h3>
      <div className="grid grid-cols-1 gap-4 md:grid-cols-2">{children}</div>
    </div>
  );
}

function UpgradeRoleBanner() {
  return (
    <div className="flex flex-col gap-3 rounded-xl bg-linear-to-r from-[#fff5f5] to-white p-5 shadow-sm ring-1 ring-rose-100 sm:flex-row sm:items-center sm:justify-between">
      <div>
        <h3 className="text-sm font-semibold text-gray-900">Grow with Biznie</h3>
        <p className="text-xs text-gray-600">
          Upgrade your account to start selling commodities or move freight on the network.
        </p>
      </div>
      <div className="flex flex-wrap gap-2">
        <a
          href="/profile/become-seller"
          className="rounded-lg bg-[#CC1414] px-4 py-2 text-xs font-medium text-white hover:bg-[#b21010]"
        >
          Become a Seller
        </a>
        <a
          href="/profile/become-transporter"
          className="rounded-lg border border-[#CC1414] px-4 py-2 text-xs font-medium text-[#CC1414] hover:bg-rose-50"
        >
          Become a Transporter
        </a>
      </div>
    </div>
  );
}

function PasswordChangeSection() {
  const { token } = useToken();
  const [form, setForm] = useState({
    current_password: "",
    password: "",
    password_confirmation: "",
  });
  const [errors, setErrors] = useState<Record<string, string[]>>({});
  const [saving, setSaving] = useState(false);

  const set = (key: keyof typeof form) => (value: string) => setForm({ ...form, [key]: value });

  const submit = async (e: React.FormEvent) => {
    e.preventDefault();
    if (!token) return;

    setSaving(true);
    setErrors({});
    try {
      const response = await authApi.changePassword(token, form);
      toast.success(response.message || "Password updated successfully.");
      setForm({ current_password: "", password: "", password_confirmation: "" });
    } catch (err) {
      if (err instanceof ApiException) {
        if (err.errors) setErrors(err.errors);
        toast.error(err.message);
      } else {
        toast.error("Password update failed.");
      }
    } finally {
      setSaving(false);
    }
  };

  return (
    <form onSubmit={submit} className="space-y-4 rounded-xl bg-white p-5 shadow-sm ring-1 ring-gray-100">
      <div>
        <h3 className="text-sm font-semibold text-gray-900">Change Password</h3>
        <p className="mt-1 text-xs text-gray-500">Use at least 8 characters with letters and numbers.</p>
      </div>
      <div className="grid grid-cols-1 gap-4 md:grid-cols-2">
        <Field
          label="Current password"
          name="current_password"
          type="password"
          value={form.current_password}
          onChange={set("current_password")}
          required
          errors={errors}
        />
        <div className="hidden md:block" />
        <Field
          label="New password"
          name="password"
          type="password"
          value={form.password}
          onChange={set("password")}
          required
          errors={errors}
        />
        <Field
          label="Confirm new password"
          name="password_confirmation"
          type="password"
          value={form.password_confirmation}
          onChange={set("password_confirmation")}
          required
          errors={errors}
        />
      </div>
      <div className="flex justify-end">
        <button
          type="submit"
          disabled={saving}
          className="rounded-lg bg-[#CC1414] px-5 py-2 text-sm font-medium text-white hover:bg-[#b21010] disabled:opacity-60"
        >
          {saving ? "Updating…" : "Update password"}
        </button>
      </div>
    </form>
  );
}

type CommonProps = {
  profile: ApiProfile;
  onSaved: (p: ApiProfile) => void;
};

function CustomerForm({ profile, onSaved }: CommonProps) {
  const { token } = useToken();
  const { refresh } = useAuth();
  const d = profile.user_detail;
  const [form, setForm] = useState({
    name: profile.name ?? "",
    email: profile.email ?? "",
    phone: profile.phone ?? "",
    company_name: d?.company_name ?? "",
    gst_number: d?.gst_number ?? "",
    pan_number: d?.pan_number ?? "",
    company_address: d?.company_address ?? "",
    address_line_one: d?.address_line_one ?? "",
    address_line_two: d?.address_line_two ?? "",
    city: d?.city ?? "",
    state: d?.state ?? "",
    postal_code: d?.postal_code ?? "",
    country: d?.country ?? "India",
  });
  const [errors, setErrors] = useState<Errors>({});
  const [saving, setSaving] = useState(false);
  const [msg, setMsg] = useState<string | null>(null);
  const set = (k: keyof typeof form) => (v: string) => setForm({ ...form, [k]: v });

  const submit = async (e: React.FormEvent) => {
    e.preventDefault();
    if (!token) return;
    // Same identifier rules as the API (B32), caught before the round trip.
    const pre = identityErrors(form);
    if (Object.keys(pre).length > 0) {
      setErrors(pre);
      return;
    }
    setSaving(true);
    setErrors({});
    setMsg(null);
    try {
      const r = await customerApi.updateProfile(token, form);
      setMsg(r.message || "Profile updated");
      toast.success(r.message || "Profile updated successfully.");
      onSaved(r.data);
      await refresh();
    } catch (err) {
      if (err instanceof ApiException && err.errors) setErrors(err.errors);
      else setMsg("Update failed");
      toast.error(err instanceof ApiException ? err.message : "Update failed");
    } finally {
      setSaving(false);
    }
  };

  return (
    <form onSubmit={submit} className="space-y-4">
      <UpgradeRoleBanner />
      <Section title="Personal">
        <Field label="Name" name="name" value={form.name} onChange={set("name")} required errors={errors} />
        <Field label="Email" name="email" type="email" value={form.email} onChange={set("email")} required errors={errors} />
        <Field label="Phone" name="phone" value={form.phone} onChange={set("phone")} required errors={errors} hint="10-digit mobile number" />
      </Section>
      <Section title="Company">
        <Field label="Company name" name="company_name" value={form.company_name} onChange={set("company_name")} errors={errors} />
        <Field label="GST number" name="gst_number" value={form.gst_number} onChange={set("gst_number")} errors={errors} />
        <Field label="PAN number" name="pan_number" value={form.pan_number} onChange={set("pan_number")} errors={errors} />
      </Section>
      <Section title="Address">
        <Field label="Address line 1" name="address_line_one" value={form.address_line_one} onChange={set("address_line_one")} errors={errors} />
        <Field label="Address line 2" name="address_line_two" value={form.address_line_two} onChange={set("address_line_two")} errors={errors} />
        <Field label="City" name="city" value={form.city} onChange={set("city")} errors={errors} />
        <Field label="State" name="state" value={form.state} onChange={set("state")} errors={errors} />
        <Field label="Postal code" name="postal_code" value={form.postal_code} onChange={set("postal_code")} errors={errors} />
        <Field label="Country" name="country" value={form.country} onChange={set("country")} errors={errors} />
      </Section>
      <FormFooter saving={saving} msg={msg} />
    </form>
  );
}

function SellerForm({ profile, onSaved }: CommonProps) {
  const { token } = useToken();
  const { refresh } = useAuth();
  const d = profile.user_detail;
  const k = profile.seller_kyc;
  const resolvedCompanyName = d?.company_name ?? "";
  const [form, setForm] = useState({
    name: profile.name ?? "",
    email: profile.email ?? "",
    phone: profile.phone ?? "",
    company_name: resolvedCompanyName,
    gst_number: d?.gst_number ?? k?.gst_number ?? "",
    pan_number: d?.pan_number ?? k?.identity_number ?? "",
    address: k?.address ?? d?.company_address ?? "",
    city: k?.city ?? d?.city ?? "",
    state: k?.state ?? d?.state ?? "",
    postal_code: k?.postal_code ?? d?.postal_code ?? "",
    country: k?.country ?? d?.country ?? "India",
    account_number: k?.account_number ?? "",
    account_holder_name: k?.account_holder_name ?? "",
    bank_name: k?.bank_name ?? "",
    ifsc_code: k?.ifsc_code ?? "",
  });
  const [errors, setErrors] = useState<Errors>({});
  const [saving, setSaving] = useState(false);
  const [msg, setMsg] = useState<string | null>(null);
  const set = (key: keyof typeof form) => (v: string) => setForm({ ...form, [key]: v });

  const submit = async (e: React.FormEvent) => {
    e.preventDefault();
    if (!token) return;
    // Same identifier rules as the API (B32), caught before the round trip.
    const pre = identityErrors(form);
    if (Object.keys(pre).length > 0) {
      setErrors(pre);
      return;
    }
    setSaving(true);
    setErrors({});
    setMsg(null);
    try {
      const r = await customerApi.updateProfile(token, form);
      setMsg(r.message || "Profile updated");
      toast.success(r.message || "Profile updated successfully.");
      onSaved(r.data);
      await refresh();
    } catch (err) {
      if (err instanceof ApiException && err.errors) setErrors(err.errors);
      else setMsg("Update failed");
      toast.error(err instanceof ApiException ? err.message : "Update failed");
    } finally {
      setSaving(false);
    }
  };

  return (
    <form onSubmit={submit} className="space-y-4">
      <KycStatusBanner profile={profile} />
      <Section title="Personal">
        <Field label="Name" name="name" value={form.name} onChange={set("name")} required errors={errors} />
        <Field label="Email" name="email" type="email" value={form.email} onChange={set("email")} required errors={errors} />
        <Field label="Phone" name="phone" value={form.phone} onChange={set("phone")} errors={errors} disabled hint="Contact support to change phone" />
      </Section>
      <Section title="Business">
        <Field label="Company name" name="company_name" value={form.company_name} onChange={set("company_name")} required errors={errors} />
        <Field label="GST number" name="gst_number" value={form.gst_number} onChange={set("gst_number")} required errors={errors} />
        <Field label="PAN number" name="pan_number" value={form.pan_number} onChange={set("pan_number")} errors={errors} />
      </Section>
      <Section title="Registered Address">
        <Field label="Address" name="address" value={form.address} onChange={set("address")} errors={errors} />
        <Field label="City" name="city" value={form.city} onChange={set("city")} errors={errors} />
        <Field label="State" name="state" value={form.state} onChange={set("state")} errors={errors} />
        <Field label="Postal code" name="postal_code" value={form.postal_code} onChange={set("postal_code")} errors={errors} />
        <Field label="Country" name="country" value={form.country} onChange={set("country")} errors={errors} />
      </Section>
      <Section title="Bank Account">
        <Field label="Account holder name" name="account_holder_name" value={form.account_holder_name} onChange={set("account_holder_name")} errors={errors} />
        <Field label="Account number" name="account_number" value={form.account_number} onChange={set("account_number")} errors={errors} />
        <Field label="Bank name" name="bank_name" value={form.bank_name} onChange={set("bank_name")} errors={errors} />
        <Field label="IFSC code" name="ifsc_code" value={form.ifsc_code} onChange={set("ifsc_code")} errors={errors} />
      </Section>
      <FormFooter saving={saving} msg={msg} />
    </form>
  );
}

function TransporterForm({ profile, onSaved }: CommonProps) {
  const { token } = useToken();
  const { refresh } = useAuth();
  const t = profile.transporter_detail;
  const [form, setForm] = useState({
    name: profile.name ?? "",
    email: profile.email ?? "",
    phone: profile.phone ?? "",
    company_name: t?.company_name ?? "",
    gst_number: t?.gst_number ?? "",
    pan_number: t?.pan_number ?? "",
    address: t?.address ?? "",
    alternate_phone: t?.alternate_phone ?? "",
    aadhar_number: t?.aadhar_number ?? "",
  });
  const [errors, setErrors] = useState<Errors>({});
  const [saving, setSaving] = useState(false);
  const [msg, setMsg] = useState<string | null>(null);
  const set = (key: keyof typeof form) => (v: string) => setForm({ ...form, [key]: v });

  const submit = async (e: React.FormEvent) => {
    e.preventDefault();
    if (!token) return;
    // Same identifier rules as the API (B32), caught before the round trip.
    const pre = identityErrors(form);
    if (Object.keys(pre).length > 0) {
      setErrors(pre);
      return;
    }
    setSaving(true);
    setErrors({});
    setMsg(null);
    try {
      const r = await customerApi.updateProfile(token, form);
      setMsg(r.message || "Profile updated");
      toast.success(r.message || "Profile updated successfully.");
      onSaved(r.data);
      await refresh();
    } catch (err) {
      if (err instanceof ApiException && err.errors) setErrors(err.errors);
      else setMsg("Update failed");
      toast.error(err instanceof ApiException ? err.message : "Update failed");
    } finally {
      setSaving(false);
    }
  };

  return (
    <form onSubmit={submit} className="space-y-4">
      <Section title="Personal">
        <Field label="Name" name="name" value={form.name} onChange={set("name")} required errors={errors} />
        <Field label="Phone" name="phone" value={form.phone} onChange={set("phone")} required errors={errors} hint="10-digit mobile number" />
        <Field label="Email" name="email" type="email" value={form.email} onChange={set("email")} errors={errors} />
        <Field label="Alternate phone" name="alternate_phone" value={form.alternate_phone} onChange={set("alternate_phone")} errors={errors} />
      </Section>
      <Section title="Company">
        <Field label="Company name" name="company_name" value={form.company_name} onChange={set("company_name")} required errors={errors} />
        <Field label="GST number" name="gst_number" value={form.gst_number} onChange={set("gst_number")} errors={errors} />
        <Field label="PAN number" name="pan_number" value={form.pan_number} onChange={set("pan_number")} errors={errors} />
        <Field label="Aadhar number" name="aadhar_number" value={form.aadhar_number} onChange={set("aadhar_number")} errors={errors} />
        <Field label="Address" name="address" value={form.address} onChange={set("address")} errors={errors} />
      </Section>
      <FormFooter saving={saving} msg={msg} />
    </form>
  );
}

function FormFooter({ saving, msg }: { saving: boolean; msg: string | null }) {
  return (
    <div className="flex items-center justify-between rounded-xl bg-white p-4 shadow-sm ring-1 ring-gray-100">
      <span className={`text-sm ${msg?.toLowerCase().includes("fail") ? "text-red-600" : "text-emerald-700"}`}>
        {msg}
      </span>
      <button
        type="submit"
        disabled={saving}
        className="rounded-lg bg-[#CC1414] px-5 py-2 text-sm font-medium text-white hover:bg-[#b21010] disabled:opacity-60"
      >
        {saving ? "Saving…" : "Save changes"}
      </button>
    </div>
  );
}

function CustomerProfileView({ profile }: { profile: ApiProfile }) {
  const detail = profile.user_detail;

  return (
    <div className="space-y-4">
      <UpgradeRoleBanner />
      <ViewSection title="Personal">
        <DetailRow label="Name" value={profile.name} />
        <DetailRow label="Email" value={profile.email} />
        <DetailRow label="Phone" value={profile.phone} />
      </ViewSection>
      <ViewSection title="Company">
        <DetailRow label="Company name" value={detail?.company_name} />
        <DetailRow label="GST number" value={detail?.gst_number} />
        <DetailRow label="PAN number" value={detail?.pan_number} />
      </ViewSection>
      <ViewSection title="Address">
        <DetailRow label="Address line 1" value={detail?.address_line_one} />
        <DetailRow label="Address line 2" value={detail?.address_line_two} />
        <DetailRow label="City" value={detail?.city} />
        <DetailRow label="State" value={detail?.state} />
        <DetailRow label="Postal code" value={detail?.postal_code} />
        <DetailRow label="Country" value={detail?.country} />
      </ViewSection>
    </div>
  );
}

function SellerProfileView({ profile }: { profile: ApiProfile }) {
  const detail = profile.user_detail;
  const kyc = profile.seller_kyc;

  return (
    <div className="space-y-4">
      <KycStatusBanner profile={profile} />
      <ViewSection title="Personal">
        <DetailRow label="Name" value={profile.name} />
        <DetailRow label="Email" value={profile.email} />
        <DetailRow label="Phone" value={profile.phone} />
      </ViewSection>
      <ViewSection title="Business">
        <DetailRow label="Company name" value={detail?.company_name} />
        <DetailRow label="GST number" value={detail?.gst_number ?? kyc?.gst_number} />
        <DetailRow label="PAN number" value={detail?.pan_number ?? kyc?.identity_number} />
      </ViewSection>
      <ViewSection title="Registered Address">
        <DetailRow label="Address" value={kyc?.address ?? detail?.company_address} />
        <DetailRow label="City" value={kyc?.city ?? detail?.city} />
        <DetailRow label="State" value={kyc?.state ?? detail?.state} />
        <DetailRow label="Postal code" value={kyc?.postal_code ?? detail?.postal_code} />
        <DetailRow label="Country" value={kyc?.country ?? detail?.country} />
      </ViewSection>
      <ViewSection title="Bank Account">
        <DetailRow label="Account holder name" value={kyc?.account_holder_name} />
        <DetailRow label="Account number" value={kyc?.account_number} />
        <DetailRow label="Bank name" value={kyc?.bank_name} />
        <DetailRow label="IFSC code" value={kyc?.ifsc_code} />
      </ViewSection>
    </div>
  );
}

function TransporterProfileView({ profile }: { profile: ApiProfile }) {
  const detail = profile.transporter_detail;

  return (
    <div className="space-y-4">
      <ViewSection title="Personal">
        <DetailRow label="Name" value={profile.name} />
        <DetailRow label="Phone" value={profile.phone} />
        <DetailRow label="Email" value={profile.email} />
        <DetailRow label="Alternate phone" value={detail?.alternate_phone} />
      </ViewSection>
      <ViewSection title="Company">
        <DetailRow label="Company name" value={detail?.company_name} />
        <DetailRow label="GST number" value={detail?.gst_number} />
        <DetailRow label="PAN number" value={detail?.pan_number} />
        <DetailRow label="Aadhar number" value={detail?.aadhar_number} />
        <DetailRow label="Address" value={detail?.address} />
      </ViewSection>
    </div>
  );
}

function ProfilePageInner() {
  const { token, ready } = useToken();
  const search = useSearchParams();
  const editParam = search.get("edit") === "true";
  const [profile, setProfile] = useState<ApiProfile | null>(null);
  const [loading, setLoading] = useState(true);
  const [isEditing, setIsEditing] = useState(editParam);

  useEffect(() => {
    setIsEditing(editParam);
  }, [editParam]);

  useEffect(() => {
    if (!ready || !token) return;
    customerApi.profile(token).then((r) => setProfile(r)).finally(() => setLoading(false));
  }, [ready, token]);

  const heading = useMemo(() => {
    if (!profile) return "Profile";
    if (profile.type === "seller") return "Seller Profile";
    if (profile.type === "transporter") return "Transporter Profile";
    return "My Profile";
  }, [profile]);

  if (loading || !profile) {
    return (
      <div className="rounded-xl bg-white p-10 shadow-sm ring-1 ring-gray-100">
        <Loader label="Loading profile…" />
      </div>
    );
  }

  return (
    <div className="space-y-4" data-edit={editParam ? "true" : undefined}>
      <div className="flex items-center justify-between">
        <h1 className="text-xl font-semibold text-gray-900">{heading}</h1>
        <div className="flex items-center gap-3">
          <span className="hidden text-xs text-gray-500 sm:inline">
            Member since {formatDateShort(profile.created_at)}
          </span>
          {isEditing ? (
            <button
              type="button"
              onClick={() => setIsEditing(false)}
              className="inline-flex items-center gap-2 rounded-lg border border-gray-200 bg-white px-4 py-2 text-sm font-medium text-gray-700 hover:bg-gray-50"
            >
              <X className="h-4 w-4" /> Cancel
            </button>
          ) : (
            <button
              type="button"
              onClick={() => setIsEditing(true)}
              className="inline-flex items-center gap-2 rounded-lg bg-[#CC1414] px-4 py-2 text-sm font-medium text-white hover:bg-[#b21010]"
            >
              <Pencil className="h-4 w-4" /> Edit Profile
            </button>
          )}
        </div>
      </div>

      {!isEditing ? profile.type === "seller" ? (
        <SellerProfileView profile={profile} />
      ) : profile.type === "transporter" ? (
        <TransporterProfileView profile={profile} />
      ) : (
        <CustomerProfileView profile={profile} />
      ) : profile.type === "seller" ? (
        <SellerForm profile={profile} onSaved={(next) => { setProfile(next); setIsEditing(false); }} />
      ) : profile.type === "transporter" ? (
        <TransporterForm profile={profile} onSaved={(next) => { setProfile(next); setIsEditing(false); }} />
      ) : (
        <CustomerForm profile={profile} onSaved={(next) => { setProfile(next); setIsEditing(false); }} />
      )}

      {isEditing && <PasswordChangeSection />}
    </div>
  );
}

export default function ProfilePage() {
  return (
    <Suspense fallback={<div className="rounded-xl bg-white p-10 shadow-sm ring-1 ring-gray-100"><Loader label="Loading profile…" /></div>}>
      <ProfilePageInner />
    </Suspense>
  );
}
