import { readFileSync } from "node:fs";
import { describe, expect, it, vi } from "vitest";
import { euautodalas } from "../src/adapters/euautodalas.js";
import { normalizeQuery } from "../src/core/normalize.js";
import { OfferSchema, type FetchContext } from "../src/core/types.js";

const html = readFileSync("fixtures/euautodalas/W71252.html", "utf-8");

describe("euautodalas adapter (fixture: W71252, recorded 2026-07-12 via resident browser)", () => {
  const offers = euautodalas.parse(html, normalizeQuery("W 712/52")!);

  it("finds the product cards", () => {
    expect(offers.length).toBe(15);
  });

  it("waits for a result card before accepting a rendered 403 page", async () => {
    const fetchPageHtml = vi.fn().mockResolvedValue(html);
    const ctx = { browser: { fetchPageHtml } } as unknown as FetchContext;

    await euautodalas.fetchRaw(normalizeQuery("W 712/52")!, ctx);

    expect(fetchPageHtml).toHaveBeenCalledWith(
      "euautodalas",
      "https://www.euautodalas.lv/meklesana-rezervesdalas?keyword=W71252",
      { waitForSelector: ".cat_items .cat_item" },
    );
  });

  it("every offer passes schema validation", () => {
    for (const o of offers) expect(() => OfferSchema.parse(o)).not.toThrow();
  });

  it("parses the known MANN filter correctly (data-price, not the decorative 0,00 €)", () => {
    const mann = offers.find((o) => o.partNumber === "W 712/52");
    expect(mann).toBeDefined();
    expect(mann!.brand).toBe("MANN-FILTER");
    expect(mann!.priceEur).toBe(8.43);
    expect(mann!.title).toContain("Eļļas filtrs");
    expect(mann!.availability).toBe("Pieejams");
    expect(mann!.url).toBe("https://www.euautodalas.lv/dalas/mann-filter/963592");
  });

  it("extracts image and spec-line attributes (flags get label '')", () => {
    const mann = offers.find((o) => o.partNumber === "W 712/52")!;
    expect(mann.imageUrl).toBe("https://media.euautoteile.de/360_photos/963592/preview.jpg");
    expect(mann.attributes).toContainEqual({ label: "Augstums", value: "92mm" });
    expect(mann.attributes).toContainEqual({ label: "", value: "ar atgriezējvārstu" });
  });

  it("includes cross-brand analogues", () => {
    const brands = new Set(offers.map((o) => o.brand));
    expect(brands.size).toBeGreaterThan(1);
  });
});
