import { describe, expect, it } from "vitest";
import { getHeaderController } from "@/interface-adapters/controllers/get-header.controller";
import { getHeaderUseCase } from "@/application/use-cases/get-header.use-case";
import { MockHeaderRepository } from "@/infrastructure/repositories/header.repository.mock";
import { InputParseError } from "@/entities/errors/common";

describe("getHeaderController", () => {
  it("returns the header with items", async () => {
    const repo = new MockHeaderRepository();
    const useCase = getHeaderUseCase(repo);
    const controller = getHeaderController(useCase);

    const result = await controller({});

    expect(result.items.length).toBeGreaterThan(0);
    expect(result.items[0]?.label).toBe("Home");
  });

  it("throws InputParseError on unknown fields (strict schema)", async () => {
    const repo = new MockHeaderRepository();
    const useCase = getHeaderUseCase(repo);
    const controller = getHeaderController(useCase);

    await expect(controller({ unknownField: 1 })).rejects.toThrow(
      InputParseError,
    );
  });

  it("InputParseError preserves the cause from Zod", async () => {
    const repo = new MockHeaderRepository();
    const useCase = getHeaderUseCase(repo);
    const controller = getHeaderController(useCase);

    try {
      await controller({ unknownField: 1 });
      expect.fail("expected InputParseError");
    } catch (err) {
      expect(err).toBeInstanceOf(InputParseError);
      expect((err as Error).name).toBe("InputParseError");
      expect((err as InputParseError).cause).toBeDefined();
    }
  });
});
