import { fireEvent, render, screen } from "@testing-library/react";
import { getFeaturedProjects } from "@/lib/portfolio-data";
import {
buildShowcaseItems,
ShowcaseProvider,
useShowcaseItems,
useShowcaseOpen,
} from "./ShowcaseProvider";
/** A janela ampliada é testada em ProjectLightbox.test.tsx; aqui ela é um dublê que só mostra o índice e navega. */
jest.mock("./ProjectLightbox", () => ({
ProjectLightbox: ({
index,
onClose,
onNavigate,
}: {
index: number;
onClose: () => void;
onNavigate: (index: number) => void;
}) => (
aberto:{index}
),
}));
const projects = getFeaturedProjects(null);
const clientIds = ["sev-modaintima", "lavacao-047", "sc-plus", "as-servicos"];
const clients = projects.filter((project) => clientIds.includes(project.id));
function Opener({ id }: { id: string }) {
const open = useShowcaseOpen();
return (
);
}
describe("buildShowcaseItems", () => {
it("lists only projects that have a recorded showcase, in showcase order", () => {
const items = buildShowcaseItems(projects);
expect(items.map((item) => item.config.id)).toEqual([
"sev-modaintima",
"lavacao-047",
"nutriscan",
"sc-plus",
"as-servicos",
]);
expect(
buildShowcaseItems(projects.filter((p) => p.id === "twins-lab")),
).toEqual([]);
});
it("serves the reel with only the client projects the home passes in, in showcase order", () => {
expect(buildShowcaseItems(clients).map((item) => item.config.id)).toEqual([
"sev-modaintima",
"lavacao-047",
"sc-plus",
"as-servicos",
]);
});
it("ignores projects missing from the list and builds nothing from an empty one", () => {
const only = projects.filter((project) =>
["as-servicos", "sev-modaintima"].includes(project.id),
);
expect(buildShowcaseItems(only).map((item) => item.config.id)).toEqual([
"sev-modaintima",
"as-servicos",
]);
expect(buildShowcaseItems([])).toEqual([]);
});
});
describe("ShowcaseProvider", () => {
it("shares the same list of items with whoever is inside it", () => {
function Count() {
return
itens:{useShowcaseItems().length}
;
}
render(
,
);
expect(screen.getByText("itens:4")).toBeInTheDocument();
});
it("opens the enlarged window on the project's position in the list, and closes it", () => {
render(
,
);
expect(screen.queryByRole("dialog")).toBeNull();
fireEvent.click(screen.getByRole("button", { name: "abrir sc-plus" }));
// posição 3 de 4 na lista que a home passou (o NutriScan não está nela)
expect(screen.getByRole("dialog", { name: "ampliado" })).toHaveTextContent(
"aberto:2",
);
fireEvent.click(screen.getByRole("button", { name: "fechar" }));
expect(screen.queryByRole("dialog")).toBeNull();
});
it("does nothing when asked to open a project that is not in the showcase", () => {
render(
,
);
fireEvent.click(
screen.getByRole("button", { name: "abrir reddit-explorer" }),
);
expect(screen.queryByRole("dialog")).toBeNull();
});
it("changes project when the window navigates to a valid index, and closes on an invalid one", () => {
render(
,
);
fireEvent.click(screen.getByRole("button", { name: "abrir lavacao-047" }));
expect(screen.getByRole("dialog")).toHaveTextContent("aberto:1");
fireEvent.click(screen.getByRole("button", { name: "ir para o primeiro" }));
expect(screen.getByRole("dialog")).toHaveTextContent("aberto:0");
fireEvent.click(
screen.getByRole("button", { name: "ir para um que não existe" }),
);
expect(screen.queryByRole("dialog")).toBeNull();
});
});
describe("hooks used outside the provider", () => {
it("give an empty list, and opening does nothing", () => {
function Outsider() {
const items = useShowcaseItems();
const open = useShowcaseOpen();
return (
);
}
render();
const button = screen.getByRole("button", { name: "itens:0" });
expect(() => fireEvent.click(button)).not.toThrow();
expect(screen.queryByRole("dialog")).toBeNull();
});
});