import React, { useState, useMemo, useEffect } from "react";
import Sidebar from "../sidebar/sidebar";
import Header from "../header/header";
import { useFrameworks, useSources, useFinancialYears } from "../../hooks/useApiData";
import { usePermission } from "../../hooks/usePermission";
import {
  SettingLayout, SettingsCard, SettingsSectionHeader,
  SettingsSectionTitle, SettingsCountChip, SettingsModalBody, SettingsModalFooter,
} from "../Settings/SettingShell";
import { Modal, ModalHeader } from "../../globalComponents/ui/Modal";
import { PrimaryButton, SecondaryButton, DangerButton } from "../../globalComponents/ui/Button";
import { useDocuments, useDocumentsBatches } from "./hooks/useEvidenceLibraryData";
import { useReportingQuestionsMap } from "./hooks/useReportingQuestionsMap";
import { deleteDocument } from "../../_services/documentsService";
import { groupDocuments } from "./utils/groupDocuments";
import { getMatchingQuestionIds, matchesTagFilter } from "./utils/kpiTagMatching";
import { getLatestFY } from "../DataManagment/Quantative/component/answerHistoryPage/components/utils";
import EvidenceFilterBar from "./components/EvidenceFilterBar";
import EvidencesListView from "./components/EvidencesListView";
import UploadedDocumentsListView from "./components/UploadedDocumentsListView";
import QualitativeEvidenceListView from "./components/QualitativeEvidenceListView";
import EvidenceDetailPage from "./components/EvidenceDetailPage";
import BatchUploadModal from "./components/BatchUploadModal";
import ViewEditEvidenceModal from "./components/ViewEditEvidenceModal";
import DocumentPreviewModal from "../DataManagment/components/DocumentPreviewModal";

const TOP_TABS = [
  { key: "quantitative", label: "Quantitative", icon: "fas fa-chart-bar" },
  { key: "qualitative", label: "Qualitative", icon: "fas fa-align-left" },
];
const SUB_TABS = [
  { key: "evidences", label: "Evidences", icon: "fas fa-link" },
  { key: "documents", label: "Uploaded Documents", icon: "fas fa-folder-open" },
];

const EvidenceLibrary = (props) => {
  const [sidebarExpanded, setSidebarExpanded] = useState(true);
  const [topTab, setTopTab] = useState("quantitative");
  const [activeTab, setActiveTab] = useState("evidences");
  const [detailTarget, setDetailTarget] = useState(null);
  const isQuantitative = topTab === "quantitative";

  const financialYears = useFinancialYears();
  const sources = useSources();
  useFrameworks();

  // Quantitative and qualitative evidence are fetched separately — different
  // columns, different business rules (qualitative never batches/parses).
  const { data: quantDocuments, isLoading: quantLoading, error: quantError, refetch: refetchQuant } = useDocuments(["EVIDENCE"], "quantitative");
  const { data: batches, isLoading: batchesLoading, error: batchesError, refetch: refetchBatches } = useDocumentsBatches();
  const { data: qualDocuments, isLoading: qualLoading, error: qualError, refetch: refetchQual } = useDocuments(["EVIDENCE"], "qualitative");
  const batchesById = useMemo(() => Object.fromEntries(batches.map((b) => [b.id, b])), [batches]);

  const [search, setSearch] = useState("");
  const [financialYearId, setFinancialYearId] = useState("");
  const [sourceId, setSourceId] = useState("");
  const [subLocationId, setSubLocationId] = useState("");
  const [periodFrom, setPeriodFrom] = useState("");
  const [periodTo, setPeriodTo] = useState("");
  // 'all' | 'verified' | 'unverified'
  const [verifiedFilter, setVerifiedFilter] = useState("all");
  const [filterSteps, setFilterSteps] = useState([]);

  // Financial year always defaults to the latest one available.
  useEffect(() => {
    if (!financialYearId && financialYears.length) {
      const latest = getLatestFY(financialYears);
      if (latest) setFinancialYearId(String(latest.id));
    }
  }, [financialYears, financialYearId]);

  // Tag steps reference a different KPI universe per tab — clear on switch.
  useEffect(() => { setFilterSteps([]); }, [topTab]);

  const [showUpload, setShowUpload] = useState(false);
  const [viewDoc, setViewDoc] = useState(null);
  const [previewDoc, setPreviewDoc] = useState(null);
  const [deleteDoc, setDeleteDoc] = useState(null);

  const [canUpload] = usePermission("evidence-library.upload-evidence", "LIST_EVIDENCES");
  const [canDelete] = usePermission("evidence-library.delete-evidence", "LIST_EVIDENCES");
  const [canEdit] = usePermission("evidence-library.upload-evidence", "LIST_EVIDENCES");

  const reportingQuestionsMap = useReportingQuestionsMap(financialYearId, isQuantitative ? "quantitative" : "tabular_question");
  const matchingQuestionIds = useMemo(
    () => getMatchingQuestionIds(reportingQuestionsMap.map, filterSteps),
    [reportingQuestionsMap.map, filterSteps]
  );
  const allTagQuestions = useMemo(() => Object.values(reportingQuestionsMap.map), [reportingQuestionsMap.map]);

  // ── Quantitative: documents filtered by FY/location/sub-location/period/tags ──
  const filteredQuantDocuments = useMemo(() => {
    let list = quantDocuments;
    if (financialYearId) list = list.filter((d) => String(d.financialYearId) === String(financialYearId));
    if (sourceId) list = list.filter((d) => String(d.sourceId) === String(sourceId));
    if (subLocationId) list = list.filter((d) => String(d.subLocationId) === String(subLocationId));
    if (periodFrom || periodTo) {
      list = list.filter((d) => {
        if (!d.answerFromDate || !d.answerToDate) return false;
        if (periodFrom && d.answerToDate < periodFrom) return false;
        if (periodTo && d.answerFromDate > periodTo) return false;
        return true;
      });
    }
    if (search.trim()) {
      const q = search.trim().toLowerCase();
      list = list.filter((d) => (d.fileName || "").toLowerCase().includes(q));
    }
    if (verifiedFilter === "verified") list = list.filter((d) => d.isVerified);
    else if (verifiedFilter === "unverified") list = list.filter((d) => !d.isVerified);
    list = list.filter((d) => matchesTagFilter(d, matchingQuestionIds));
    return list;
  }, [quantDocuments, financialYearId, sourceId, subLocationId, periodFrom, periodTo, search, verifiedFilter, matchingQuestionIds]);

  // Evidences only shows documents actually backing a saved answer, or a
  // batch with at least one KPI already reviewed+saved from it — an
  // unreviewed batch stays Uploaded-Documents-only until then.
  const evidenceGroups = useMemo(
    () => groupDocuments(filteredQuantDocuments, batchesById)
      .filter((g) => g.type === "answer" || (g.type === "batch" && g.reviewedCount > 0)),
    [filteredQuantDocuments, batchesById]
  );

  // Batch aggregates from GET /documents/batches carry no verified/unverified counts
  // — derived here from the flat (unfiltered) document list so they stay stable
  // regardless of other active filters. A batch matches "verified"/"unverified" if
  // ANY of its documents is in that state (batches can be a mix of both).
  const { verifiedBatchIds, unverifiedBatchIds } = useMemo(() => {
    const verified = new Set();
    const unverified = new Set();
    quantDocuments.forEach((d) => {
      if (d.documentsBatchId == null) return;
      (d.isVerified ? verified : unverified).add(d.documentsBatchId);
    });
    return { verifiedBatchIds: verified, unverifiedBatchIds: unverified };
  }, [quantDocuments]);

  const filteredBatches = useMemo(() => {
    let list = batches;
    if (financialYearId) list = list.filter((b) => String(b.financialYearId) === String(financialYearId));
    if (sourceId) list = list.filter((b) => String(b.sourceId) === String(sourceId));
    if (subLocationId) list = list.filter((b) => String(b.subLocationId) === String(subLocationId));
    if (search.trim()) {
      const q = search.trim().toLowerCase();
      list = list.filter((b) => (b.name || `Batch #${b.id}`).toLowerCase().includes(q));
    }
    if (verifiedFilter === "verified") list = list.filter((b) => verifiedBatchIds.has(b.id));
    else if (verifiedFilter === "unverified") list = list.filter((b) => unverifiedBatchIds.has(b.id));
    list = list.filter((b) => matchesTagFilter(b, matchingQuestionIds));
    return list;
  }, [batches, financialYearId, sourceId, subLocationId, search, verifiedFilter, verifiedBatchIds, unverifiedBatchIds, matchingQuestionIds]);

  // ── Qualitative: FY + search + tags only — no location/sub-location/period ──
  const filteredQualDocuments = useMemo(() => {
    let list = qualDocuments;
    if (financialYearId) list = list.filter((d) => String(d.financialYearId) === String(financialYearId));
    if (search.trim()) {
      const q = search.trim().toLowerCase();
      list = list.filter((d) => (d.fileName || "").toLowerCase().includes(q));
    }
    list = list.filter((d) => matchesTagFilter(d, matchingQuestionIds));
    return list;
  }, [qualDocuments, financialYearId, search, matchingQuestionIds]);

  const qualitativeGroups = useMemo(
    () => groupDocuments(filteredQualDocuments, {}),
    [filteredQualDocuments]
  );

  const refetchAll = () => { refetchQuant(); refetchBatches(); refetchQual(); };

  const handleDelete = async () => {
    if (!deleteDoc) return;
    const [doc, onDeleted] = Array.isArray(deleteDoc) ? deleteDoc : [deleteDoc, null];
    await deleteDocument(doc.id);
    setDeleteDoc(null);
    refetchAll();
    onDeleted?.();
  };

  const handleOpenDetail = (target) => setDetailTarget(target);
  const handleBack = () => setDetailTarget(null);

  const totalCount = isQuantitative ? quantDocuments.length : qualDocuments.length;

  return (
    <div className="d-flex flex-row mainclass" style={{ height: "100vh", overflow: "auto" }}>
      <div style={{ flex: sidebarExpanded ? "0 0 21%" : "0 0 60px", position: "sticky", top: 0, zIndex: 999 }}>
        <Sidebar dataFromParent={props.location.pathname} onSidebarToggle={setSidebarExpanded} />
      </div>

      <div style={{ flex: "1", minWidth: 0, transition: "all 0.3s ease" }}>
        <div style={{ position: "sticky", top: 0, zIndex: 999 }}><Header /></div>

        <SettingLayout
          title="Evidence Library"
          subtitle={detailTarget ? undefined : `${totalCount} ${topTab} evidence document${totalCount === 1 ? "" : "s"}`}
          $wide
          rightContent={
            !detailTarget && isQuantitative && canUpload && (
              <PrimaryButton onClick={() => setShowUpload(true)}>
                <i className="fas fa-upload" style={{ marginRight: 6 }} />Upload Evidence
              </PrimaryButton>
            )
          }
        >
          {detailTarget ? (
            <EvidenceDetailPage
              target={detailTarget}
              sources={sources}
              financialYears={financialYears}
              onBack={handleBack}
              onViewDocument={setViewDoc}
              onPreview={setPreviewDoc}
              onDelete={(doc, onDeleted) => setDeleteDoc([doc, onDeleted])}
              canDelete={canDelete}
            />
          ) : (
            <>
              <div style={{ display: "flex", gap: 4, marginBottom: 12 }}>
                {TOP_TABS.map((tab) => (
                  <button
                    key={tab.key}
                    onClick={() => setTopTab(tab.key)}
                    style={{
                      display: "flex", alignItems: "center", gap: 7, padding: "8px 16px",
                      border: `1.5px solid ${topTab === tab.key ? "#3f88a5" : "#e2e8f0"}`,
                      borderRadius: 8,
                      background: topTab === tab.key ? "#eff6ff" : "#fff",
                      cursor: "pointer",
                      fontSize: 13, fontWeight: topTab === tab.key ? 700 : 500,
                      color: topTab === tab.key ? "#3f88a5" : "#64748b",
                    }}
                  >
                    <i className={tab.icon} />{tab.label}
                  </button>
                ))}
              </div>

              {isQuantitative && (
                <div style={{ display: "flex", gap: 4, marginBottom: 16, borderBottom: "2px solid #e5e8ed" }}>
                  {SUB_TABS.map((tab) => (
                    <button
                      key={tab.key}
                      onClick={() => setActiveTab(tab.key)}
                      style={{
                        display: "flex", alignItems: "center", gap: 7, padding: "10px 18px",
                        border: "none", borderBottom: `2px solid ${activeTab === tab.key ? "#3f88a5" : "transparent"}`,
                        marginBottom: -2,
                        background: "none", cursor: "pointer",
                        fontSize: 13.5, fontWeight: activeTab === tab.key ? 700 : 500,
                        color: activeTab === tab.key ? "#3f88a5" : "#64748b",
                      }}
                    >
                      <i className={tab.icon} />{tab.label}
                    </button>
                  ))}
                </div>
              )}

              <EvidenceFilterBar
                search={search} onSearchChange={setSearch}
                financialYears={financialYears} financialYearId={financialYearId} onFinancialYearChange={setFinancialYearId}
                isQuantitative={isQuantitative}
                sources={sources} sourceId={sourceId} onSourceChange={setSourceId}
                subLocationId={subLocationId} onSubLocationChange={setSubLocationId}
                periodFrom={periodFrom} periodTo={periodTo} onPeriodFromChange={setPeriodFrom} onPeriodToChange={setPeriodTo}
                verifiedFilter={verifiedFilter} onVerifiedFilterChange={setVerifiedFilter}
                allTagQuestions={allTagQuestions}
                filterSteps={filterSteps}
                onFilterStepsChange={setFilterSteps}
              />

              <SettingsCard style={{ marginBottom: 20 }}>
                <SettingsSectionHeader>
                  <i className={!isQuantitative ? "fas fa-align-left" : activeTab === "evidences" ? "fas fa-link" : "fas fa-folder-open"} style={{ fontSize: 12, color: "#3f88a5" }} />
                  <SettingsSectionTitle>
                    {!isQuantitative ? "Qualitative Evidence" : activeTab === "evidences" ? "Evidences" : "Uploaded Documents"}
                  </SettingsSectionTitle>
                  <SettingsCountChip>
                    {!isQuantitative ? qualitativeGroups.length : activeTab === "evidences" ? evidenceGroups.length : filteredBatches.length}
                  </SettingsCountChip>
                </SettingsSectionHeader>
                <div style={{ padding: 16 }}>
                  {!isQuantitative ? (
                    <QualitativeEvidenceListView
                      groups={qualitativeGroups}
                      financialYears={financialYears}
                      reportingQuestionsMap={reportingQuestionsMap.map}
                      isLoading={qualLoading}
                      error={qualError}
                      onRetry={refetchQual}
                      onRowClick={handleOpenDetail}
                    />
                  ) : activeTab === "evidences" ? (
                    <EvidencesListView
                      groups={evidenceGroups}
                      sources={sources}
                      financialYears={financialYears}
                      reportingQuestionsMap={reportingQuestionsMap.map}
                      isLoading={quantLoading}
                      error={quantError}
                      onRetry={refetchQuant}
                      onRowClick={handleOpenDetail}
                    />
                  ) : (
                    <UploadedDocumentsListView
                      batches={filteredBatches}
                      documents={quantDocuments}
                      sources={sources}
                      financialYears={financialYears}
                      isLoading={batchesLoading}
                      error={batchesError}
                      onRetry={refetchBatches}
                      onRowClick={handleOpenDetail}
                    />
                  )}
                </div>
              </SettingsCard>
            </>
          )}
        </SettingLayout>
      </div>

      <BatchUploadModal
        show={showUpload}
        onClose={() => setShowUpload(false)}
        onUploaded={() => refetchAll()}
        financialYears={financialYears}
        sources={sources}
      />

      <ViewEditEvidenceModal
        show={!!viewDoc}
        onClose={() => setViewDoc(null)}
        document={viewDoc}
        financialYears={financialYears}
        sources={sources}
        onSaved={() => { refetchAll(); setViewDoc(null); }}
        canEdit={canEdit}
      />

      <DocumentPreviewModal
        document={previewDoc}
        onClose={() => setPreviewDoc(null)}
      />

      <Modal show={!!deleteDoc} onClose={() => setDeleteDoc(null)} maxWidth={420}>
        <ModalHeader icon="fas fa-exclamation-triangle" title="Delete Evidence" onClose={() => setDeleteDoc(null)} />
        <SettingsModalBody>
          <p style={{ margin: 0, fontSize: 13, color: "#475569" }}>
            Delete <strong>{(Array.isArray(deleteDoc) ? deleteDoc[0] : deleteDoc)?.fileName}</strong>? It will no longer count as evidence for any linked answer.
          </p>
        </SettingsModalBody>
        <SettingsModalFooter>
          <SecondaryButton onClick={() => setDeleteDoc(null)}>Cancel</SecondaryButton>
          <DangerButton onClick={handleDelete}>Delete</DangerButton>
        </SettingsModalFooter>
      </Modal>
    </div>
  );
};

export default EvidenceLibrary;
