import React, { useCallback, useEffect, useMemo, useState } from "react";
import ErrorBanner from "../../../components/common/ErrorBanner.jsx";
import { PTW_SECTION_SKIP_ADMIN_UI_ENABLED } from "../../../config/ptwFeatures.js";
import {
  deleteFormSectionMap,
  getFormWithSections,
  listForms,
  listSections,
  mapFormSection,
  reorderFormSections,
  updateFormSectionMap
} from "../../../services/formsApi.js";
import SectionReorderList from "./SectionReorderList.jsx";

function sortMappedSections(list) {
  return [...(list || [])].sort((a, b) => {
    const oa =
      a.section_in_form_order != null && a.section_in_form_order !== ""
        ? Number(a.section_in_form_order)
        : 999999;
    const ob =
      b.section_in_form_order != null && b.section_in_form_order !== ""
        ? Number(b.section_in_form_order)
        : 999999;
    if (oa !== ob) return oa - ob;
    return Number(a.section_id) - Number(b.section_id);
  });
}

function sectionOrderKey(list) {
  return (list || []).map((s) => Number(s.section_id)).join(",");
}

export default function FormSectionMapPanel() {
  const [forms, setForms] = useState([]);
  const [sections, setSections] = useState([]);
  const [formId, setFormId] = useState("");
  const [addSectionId, setAddSectionId] = useState("");
  const [addOrder, setAddOrder] = useState("");
  const [mapped, setMapped] = useState([]);
  const [orderedSections, setOrderedSections] = useState([]);
  const [formTitle, setFormTitle] = useState("");
  const [error, setError] = useState("");
  const [loading, setLoading] = useState(false);
  const [saving, setSaving] = useState(false);
  const [skipableDraft, setSkipableDraft] = useState({});

  const loadCatalog = useCallback(async () => {
    try {
      const [f, s] = await Promise.all([listForms(), listSections()]);
      setForms(Array.isArray(f) ? f : []);
      setSections(Array.isArray(s) ? s : []);
    } catch (err) {
      setError(err?.response?.data?.message || err.message);
    }
  }, []);

  const loadMapped = useCallback(async (id) => {
    if (!id) {
      setMapped([]);
      setOrderedSections([]);
      setFormTitle("");
      setSkipableDraft({});
      return;
    }
    setLoading(true);
    try {
      setError("");
      const data = await getFormWithSections(id);
      setFormTitle(data?.title || `Form #${id}`);
      const list = sortMappedSections(Array.isArray(data?.sections) ? data.sections : []);
      setMapped(list);
      setOrderedSections(list);
      const skipDraft = {};
      for (const row of list) {
        skipDraft[row.section_id] =
          row.skipable === 1 || row.skipable === true || row.skipable === "1";
      }
      setSkipableDraft(skipDraft);
    } catch (err) {
      setError(err?.response?.data?.message || err.message);
      setMapped([]);
      setOrderedSections([]);
      setSkipableDraft({});
    } finally {
      setLoading(false);
    }
  }, []);

  useEffect(() => {
    loadCatalog();
  }, [loadCatalog]);

  useEffect(() => {
    if (formId) {
      loadMapped(formId);
    }
  }, [formId, loadMapped]);

  const mappedIds = useMemo(
    () => new Set(mapped.map((s) => Number(s.section_id))),
    [mapped]
  );

  const availableSections = useMemo(
    () => sections.filter((s) => !mappedIds.has(Number(s.section_id))),
    [sections, mappedIds]
  );

  const orderDirty = useMemo(
    () => sectionOrderKey(orderedSections) !== sectionOrderKey(mapped),
    [orderedSections, mapped]
  );

  const handleAdd = async () => {
    const fid = Number(formId);
    const sid = Number(addSectionId);
    if (!Number.isFinite(fid) || fid <= 0) {
      setError("Select a form first.");
      return;
    }
    if (!Number.isFinite(sid) || sid <= 0) {
      setError("Select a section to add.");
      return;
    }
    const payload = { form_id: fid, section_id: sid };
    if (addOrder !== "") {
      payload.section_in_form_order = Number(addOrder);
    }
    setSaving(true);
    try {
      setError("");
      await mapFormSection(payload);
      setAddSectionId("");
      setAddOrder("");
      await loadMapped(String(fid));
    } catch (err) {
      setError(err?.response?.data?.message || err.message);
    } finally {
      setSaving(false);
    }
  };

  const handleRemove = async (sectionId) => {
    const fid = Number(formId);
    const sid = Number(sectionId);
    if (!Number.isFinite(fid) || !Number.isFinite(sid)) return;
    setSaving(true);
    try {
      setError("");
      await deleteFormSectionMap(fid, sid);
      await loadMapped(String(fid));
    } catch (err) {
      setError(err?.response?.data?.message || err.message);
    } finally {
      setSaving(false);
    }
  };

  const handleSaveSkipable = async (sectionId) => {
    const fid = Number(formId);
    const sid = Number(sectionId);
    if (!Number.isFinite(fid) || !Number.isFinite(sid)) return;
    setSaving(true);
    try {
      setError("");
      await updateFormSectionMap(fid, sid, {
        skipable: skipableDraft[sectionId] ? 1 : 0
      });
      await loadMapped(String(fid));
    } catch (err) {
      setError(err?.response?.data?.message || err.message);
    } finally {
      setSaving(false);
    }
  };

  const handleSaveOrder = async () => {
    const fid = Number(formId);
    if (!Number.isFinite(fid) || fid <= 0) return;
    if (!orderedSections.length) return;

    setSaving(true);
    try {
      setError("");
      const payload = orderedSections.map((section, index) => ({
        section_id: section.section_id,
        section_in_form_order: index + 1
      }));
      await reorderFormSections(fid, payload);
      await loadMapped(String(fid));
    } catch (err) {
      setError(err?.response?.data?.message || err.message);
    } finally {
      setSaving(false);
    }
  };

  return (
    <div className="ptw-mgmt-card">
      <div className="ptw-mgmt-card__header">
        <div>
          <h2 className="ptw-mgmt-card__title">Form–section mapping</h2>
          <p className="ptw-mgmt-card__desc">
            Links are stored in <code>ptw_form_section_map</code> (form_id, section_id,
            section_in_form_order{PTW_SECTION_SKIP_ADMIN_UI_ENABLED ? ", skipable" : ""}). Drag sections or
            use the arrows to reorder, then save the order.
          </p>
        </div>
      </div>

      <ErrorBanner message={error} />

      <div className="ptw-mgmt-form-grid ptw-map-toolbar">
        <label className="ptw-mgmt-field">
          <span className="ptw-mgmt-field__label">Form</span>
          <select
            className="ptw-mgmt-input ptw-mgmt-select"
            value={formId}
            onChange={(e) => setFormId(e.target.value)}
          >
            <option value="">Select form</option>
            {forms.map((f) => (
              <option key={f.form_id} value={String(f.form_id)}>
                #{f.form_id} — {f.title || "Untitled"}
              </option>
            ))}
          </select>
        </label>
        <label className="ptw-mgmt-field">
          <span className="ptw-mgmt-field__label">Add section</span>
          <select
            className="ptw-mgmt-input ptw-mgmt-select"
            value={addSectionId}
            onChange={(e) => setAddSectionId(e.target.value)}
            disabled={!formId}
          >
            <option value="">Select section</option>
            {availableSections.map((s) => (
              <option key={s.section_id} value={String(s.section_id)}>
                #{s.section_id} — {s.title || "Untitled"}
              </option>
            ))}
          </select>
        </label>
        <label className="ptw-mgmt-field">
          <span className="ptw-mgmt-field__label">Order in form (optional)</span>
          <input
            className="ptw-mgmt-input"
            type="number"
            min="0"
            value={addOrder}
            onChange={(e) => setAddOrder(e.target.value)}
            placeholder="Auto if empty"
            disabled={!formId}
          />
        </label>
        <div className="ptw-mgmt-field ptw-map-toolbar__action">
          <button
            type="button"
            className="swi-btn swi-btn--primary"
            onClick={handleAdd}
            disabled={saving || !formId || !addSectionId}
          >
            {saving ? "Saving…" : "Add to form"}
          </button>
        </div>
      </div>

      {formId ? (
        <>
          <div className="ptw-mgmt-list-meta">
            <span>
              {loading
                ? "Loading mapped sections…"
                : `${mapped.length} section${mapped.length === 1 ? "" : "s"} in "${formTitle}"`}
            </span>
            <div className="ptw-section-reorder-list__toolbar">
              <button
                type="button"
                className="swi-btn swi-btn--primary"
                onClick={handleSaveOrder}
                disabled={loading || saving || !orderDirty}
              >
                {saving ? "Saving…" : "Save order"}
              </button>
              <button
                type="button"
                className="swi-btn swi-btn--ghost"
                onClick={() => loadMapped(formId)}
                disabled={loading || saving}
              >
                Refresh
              </button>
            </div>
          </div>
          <SectionReorderList
            sections={orderedSections}
            onSectionsChange={setOrderedSections}
            disabled={loading}
            saving={saving}
            skipableDraft={skipableDraft}
            onSkipableChange={(sectionId, checked) =>
              setSkipableDraft((prev) => ({ ...prev, [sectionId]: checked }))
            }
            onSaveSkipable={handleSaveSkipable}
            onRemove={handleRemove}
          />
        </>
      ) : (
        <p className="ptw-muted ptw-mgmt-list-loading">
          Select a form to view and manage its sections.
        </p>
      )}
    </div>
  );
}
