import {
  buildDecisionAdministrativeText,
  computeSallePricing,
  CONDITIONS_FINANCIERES_SALLE_TEXT,
  type SallePricingSummary,
  type SalleReservationFrequency,
  type SalleUsageType,
  type SalleWorkflowData,
  type SalleWorkflowDirectorStatus,
  type SalleWorkflowQuoteStatus,
} from "@shared/sallePricing";

function formatDateFr(date: string | Date | null | undefined) {
  if (!date) return "-";
  try {
    return new Date(date).toLocaleDateString("fr-FR", {
      day: "2-digit",
      month: "2-digit",
      year: "numeric",
    });
  } catch {
    return String(date);
  }
}

function getScheduleSummary(formData: any) {
  const dailySlots = Array.isArray(formData?.horairesParJour)
    ? formData.horairesParJour.filter((slot: any) => slot?.date)
    : [];

  if (Boolean(formData?.useDetailedSchedule) && dailySlots.length > 0) {
    return dailySlots
      .map((slot: any) => `${formatDateFr(slot.date)} : ${slot.heureDebut || "?"} - ${slot.heureFin || "?"}`)
      .join(" | ");
  }

  if (formData?.heureDebut || formData?.heureFin) {
    return `${formData.heureDebut || "?"} - ${formData.heureFin || "?"}`;
  }

  return "-";
}

export function parseRequestFormData(rawFormData?: string | null) {
  if (!rawFormData) return {};
  try {
    return JSON.parse(rawFormData);
  } catch {
    return {};
  }
}

export function getSalleWorkflowData(rawFormData?: string | null): SalleWorkflowData {
  const formData = parseRequestFormData(rawFormData);
  return formData?.salleWorkflow && typeof formData.salleWorkflow === "object" ? formData.salleWorkflow : {};
}

export function computeSalleWorkflowPricing(rawFormData?: string | null): SallePricingSummary | null {
  const formData = parseRequestFormData(rawFormData);
  const usageType = formData?.typeUsage as SalleUsageType | undefined;
  const frequency = formData?.frequence as SalleReservationFrequency | undefined;
  const sallesIds = Array.isArray(formData?.sallesIds) ? formData.sallesIds : [];
  if (!usageType || !frequency || sallesIds.length === 0) {
    return null;
  }

  return computeSallePricing({
    sallesIds,
    usageType,
    frequency,
    dateReservation: formData.dateReservation,
    dateFinReservation: formData.dateFinReservation,
  });
}

export function mergeSalleWorkflowData(rawFormData: string | null | undefined, workflowPatch: Partial<SalleWorkflowData>) {
  const formData = parseRequestFormData(rawFormData);
  const currentWorkflow = getSalleWorkflowData(rawFormData);
  formData.salleWorkflow = {
    ...currentWorkflow,
    ...workflowPatch,
  };
  return JSON.stringify(formData);
}

export function buildDefaultSalleWorkflowTexts(rawFormData?: string | null) {
  const formData = parseRequestFormData(rawFormData);
  const salles = Array.isArray(formData?.sallesSelectionnees) && formData.sallesSelectionnees.length > 0
    ? formData.sallesSelectionnees.join(", ")
    : "-";
  const dates = formData?.dateReservation
    ? `${formatDateFr(formData.dateReservation)}${formData?.dateFinReservation && formData.dateFinReservation !== formData.dateReservation ? ` au ${formatDateFr(formData.dateFinReservation)}` : ""}`
    : "-";
  const horaires = getScheduleSummary(formData);
  const association = formData?.nomAssociation || "-";

  return {
    conditionsFinancieresText: CONDITIONS_FINANCIERES_SALLE_TEXT,
    decisionAdministrativeText: buildDecisionAdministrativeText({
      espace: salles,
      dates,
      horaires,
      association,
    }),
  };
}

export function updateSalleWorkflowQuoteStatus(rawFormData: string | null | undefined, status: SalleWorkflowQuoteStatus) {
  return mergeSalleWorkflowData(rawFormData, {
    quoteStatus: status,
    quoteRespondedAt: status === "accepte" || status === "refuse" ? new Date().toISOString() : undefined,
  });
}

export function updateSalleWorkflowDirectorStatus(rawFormData: string | null | undefined, status: SalleWorkflowDirectorStatus) {
  return mergeSalleWorkflowData(rawFormData, {
    directorStatus: status,
    directorTransmissionAt: status === "en_attente_signature" ? new Date().toISOString() : undefined,
    directorSignedAt: status === "signee" ? new Date().toISOString() : undefined,
    directorReturnComment: status === "en_attente_signature" ? "" : undefined,
    directorReturnedAt: status === "en_attente_signature" ? "" : undefined,
  });
}
