import { useState } from "react";
import ButtonFixed from "../paying/ButtonFixed";
import { Button } from "@mui/material";
import ArrowLeftB from "@/components/icons/ArrowLeftB";
import { request } from "@/services/response";
import Cookies from "js-cookie";
import { setAccessToken } from "@/lib/tokenStore";
import { useProvince } from "@/context/ProvinceProvider";

function SubmitData({ setStep, data, prevData, setErrors, doctor, isForAnother, selectedSlot, selectedDate, setAppointmentId, setAppointmentExpiresAt, selectedServiceUuids = [] }) {
  const [loading, setLoading] = useState(false);
  const { cityId } = useProvince();
  const newStep = () => setStep((prev) => prev + 1);

  const refreshAccessToken = async () => {
    try {
      const res = await fetch("/api/auth/refresh", { method: "POST" });
      if (!res.ok) return false;
      const response = await res.json();

      if (response?.access_token) {
        setAccessToken(response.access_token);
        return true;
      }
      return false;
    } catch {
      return false;
    }
  };

  // پاسخ خطای backend: { success:false, errors:[{ code, field, message }] }
  // به نگاشت field→message تبدیل می‌شود تا inline در فرم نمایش داده شود.
  const fieldErrorsFromResponse = (error) => {
    const list = error?.response?.data?.errors;
    if (!Array.isArray(list)) return {};
    return list.reduce((acc, e) => {
      if (e?.field && e?.message) acc[e.field] = e.message;
      return acc;
    }, {});
  };

  const isNationalCodeTaken = (error) =>
    error?.response?.data?.errors?.some((e) => e?.code === "ERR_PROFILE_001");

  const validate = () => {
    const errs = {};
    const nationalCode = (data?.national_code?.value || "").trim();
    if (!data?.name?.value?.trim()) errs.name = "نام الزامی است";
    if (!data?.family?.value?.trim()) errs.family = "نام خانوادگی الزامی است";
    if (!nationalCode) errs.national_code = "کد ملی الزامی است";
    else if (!/^\d{10}$/.test(nationalCode))
      errs.national_code = "کد ملی باید ۱۰ رقم باشد";
    if (!data?.gender?.value) errs.gender = "جنسیت الزامی است";
    if (!data?.basic_insurance?.value?.id) errs.basic_insurance = "نوع بیمه الزامی است";
    return errs;
  };

  const handleSubmit = async () => {
    const errs = validate();
    if (Object.keys(errs).length > 0) {
      setErrors(errs);
      return;
    }

    const isChanged = JSON.stringify(prevData) !== JSON.stringify(data);

    setErrors({});
    setLoading(true);

    try {
      if (!isForAnother && isChanged) {
        const { basic_insurance, supplementary_insurance, name, family, national_code, gender, insurance_id, uuid } = data;

        let payload = {};

        // برای PATCH فقط فیلدهای تغییر یافته را ارسال می‌کنیم
        if (uuid) {
          // بررسی تغییرات فیلد به فیلد
          if (JSON.stringify(prevData.name) !== JSON.stringify(name)) {
            payload.name = name?.value;
          }
          if (JSON.stringify(prevData.family) !== JSON.stringify(family)) {
            payload.family = family?.value;
          }
          if (JSON.stringify(prevData.national_code) !== JSON.stringify(national_code)) {
            payload.national_code = national_code?.value;
          }
          if (JSON.stringify(prevData.gender) !== JSON.stringify(gender)) {
            payload.gender = gender?.value?.id || gender?.value;
          }
          if (JSON.stringify(prevData.insurance_id) !== JSON.stringify(insurance_id)) {
            payload.insurance_id = insurance_id?.value;
          }
          if (JSON.stringify(prevData.basic_insurance) !== JSON.stringify(basic_insurance)) {
            payload.basic_insurance = basic_insurance?.value?.id ? [basic_insurance.value.id] : [];
          }
          if (JSON.stringify(prevData.supplementary_insurance) !== JSON.stringify(supplementary_insurance)) {
            payload.supplementary_insurance = supplementary_insurance?.value?.id ? [supplementary_insurance.value.id] : [];
          }
        } else {
          // برای POST همه فیلدها را ارسال می‌کنیم
          payload = {
            name: name?.value,
            family: family?.value,
            national_code: national_code?.value,
            gender: gender?.value?.id || gender?.value,
            insurance_id: insurance_id?.value,
            basic_insurance: basic_insurance?.value?.id ? [basic_insurance.value.id] : [],
            supplementary_insurance: supplementary_insurance?.value?.id ? [supplementary_insurance.value.id] : [],
          };
        }

        if (uuid) {
          await request.patchUserProfile(payload, uuid);
        } else {
          const userUuid = data?.uuid || Cookies.get("uuid");
          try {
            await request.postUserProfile(payload);
          } catch (err) {
            // 409 با کد ERR_PROFILE_001 یعنی کد ملی تکراری، نه «پروفایل موجود» → باید throw شود تا inline نمایش یابد
            // پروفایل از قبل ساخته شده (lazy-create در سمت backend) → به‌جای ساخت، ویرایش
            if (err?.response?.status === 409 && userUuid && !isNationalCodeTaken(err)) {
              await request.patchUserProfile(payload, userUuid);
            } else {
              throw err;
            }
          }
        }

        const refreshed = await refreshAccessToken();

        if (refreshed) {
          await new Promise(resolve => setTimeout(resolve, 1000));
        }
      }

      if (doctor && selectedSlot) {
        const appointmentPayload = {
          doctor_uuid: doctor.uuid,
          slot_start: selectedSlot.start,
          slot_end: selectedSlot.end,
          for_self: !isForAnother,
          note: data?.patient_reason?.value || "",
          // کد ملی و جنسیت در هر دو حالت (خودِ بیمار / شخص دیگر) الزامی است.
          patient_national_code: data?.national_code?.value || "",
          patient_gender: data?.gender?.value?.id || data?.gender?.value || "",
          // شناسه‌ی شهرِ دامنه‌ی جاری؛ backend برای گاردِ پورسانت نماینده استفاده می‌کند.
          city_id: cityId ?? null,
          // حالت نوبت‌دهی سرویسی: backend مدت و slot_end را از این سرویس‌ها بازمحاسبه می‌کند.
          ...(selectedServiceUuids?.length ? { service_item_uuids: selectedServiceUuids } : {}),
          ...(isForAnother
            ? {
                patient_name: [data?.name?.value, data?.family?.value].filter(Boolean).join(" ").trim(),
                patient_mobile: data?.phone?.value,
                patient_reason: data?.patient_reason?.value || "",
              }
            : {}),
        };

        const res = await request.postAppointment(appointmentPayload);
        const appointment = res?.data?.data;
        const appointmentUuid = appointment?.uuid;
        if (appointmentUuid) {
          setAppointmentId(appointmentUuid);
          setAppointmentExpiresAt?.(appointment?.expires_at ?? null);
        }
      }

      setLoading(false);
      newStep();
    } catch (error) {
      setLoading(false);

      const fieldErrors = fieldErrorsFromResponse(error);
      if (Object.keys(fieldErrors).length > 0) {
        setErrors(fieldErrors);
        return;
      }

      if (error?.response?.status === 409) {
        setStep(0);
        return;
      }
    }
  };

  return (
    <ButtonFixed>
      <Button
        disabled={loading}
        className={` !flex !w-full md:!w-fit !mt-0 md:!mt-[32px] !gap-[4px] md:!mr-auto !px-[12px] !py-[8px] md:!py-[9px] !min-w-[150px] `}
        variant="contained"
        onClick={handleSubmit}
      >
        <p
          className={`${loading && "opacity-0"} text-[#EFEFEF] text-[16px] font-medium`}
        >
          ثبت اطلاعات
        </p>
        <ArrowLeftB />
      </Button>
    </ButtonFixed>
  );
}

export default SubmitData;
