import {
  DEFAULT_DISCLAIMER,
  isPriceSearchResponse,
  parseN8nResponseBody,
} from "@/src/lib/price-search/normalize";
import type { PriceSearchRequest, PriceSearchResponse } from "@/src/types/priceSearch";

function getWebhookConfig() {
  const url =
    process.env.N8N_PRICE_SEARCH_WEBHOOK_URL?.trim() ??
    process.env.N8N_PRICE_WEBHOOK_URL?.trim();
  const secret = process.env.N8N_PRICE_WEBHOOK_SECRET?.trim();
  const timeoutMs = Number(process.env.N8N_PRICE_WEBHOOK_TIMEOUT_MS ?? 45_000);

  if (!url || !secret) {
    throw new Error("Ricerca prezzi n8n non configurata (URL o secret mancanti)");
  }

  return { url, secret, timeoutMs: Number.isFinite(timeoutMs) ? timeoutMs : 45_000 };
}

export async function searchPriceOffersViaN8n(
  input: PriceSearchRequest,
  meta?: { userId?: string; userName?: string },
): Promise<PriceSearchResponse> {
  const { url, secret, timeoutMs } = getWebhookConfig();

  const controller = new AbortController();
  const timer = setTimeout(() => controller.abort(), timeoutMs);

  try {
    const res = await fetch(url, {
      method: "POST",
      headers: {
        "Content-Type": "application/json",
        "X-Webhook-Secret": secret,
      },
      body: JSON.stringify({
        ...input,
        meta: {
          source: "magricambi",
          userId: meta?.userId ?? null,
          userName: meta?.userName ?? null,
          requestedAt: new Date().toISOString(),
        },
      }),
      signal: controller.signal,
      cache: "no-store",
    });

    const text = await res.text();
    const data = parseN8nResponseBody(text, res.status);

    if (!res.ok) {
      const err =
        data && typeof data === "object" && "error" in data
          ? String((data as { error: unknown }).error)
          : `Errore n8n (HTTP ${res.status})`;
      throw new Error(err);
    }

    if (!isPriceSearchResponse(data)) {
      throw new Error(
        "Formato risposta n8n non conforme. Verifica il nodo Respond OK del workflow.",
      );
    }

    return data;
  } catch (error) {
    if (error instanceof Error && error.name === "AbortError") {
      throw new Error("Timeout ricerca prezzi: riprova tra poco");
    }
    throw error;
  } finally {
    clearTimeout(timer);
  }
}

export { DEFAULT_DISCLAIMER };
