import "@testing-library/jest-dom";
import { Accordion } from "./index";
import { fireEvent, render, screen } from "@testing-library/react";
// Mock dependencies
jest.mock("@shared/components/button", () => ({
Button: ({ children, onClick, ...props }: any) => (
),
}));
jest.mock("@shared/components/collapse", () => ({
Collapse: ({ open, children }: any) => (
{open ? children : null}
),
}));
jest.mock("@shared/components/material-icon", () => ({
MaterialIcon: ({ name, className }: any) => (
{name}
),
}));
jest.mock("@shared/utils", () => ({
cx: (...args: any[]) => args.filter(Boolean).join(" "),
}));
describe("Accordion", () => {
const defaultProps = {
title: "Accordion Title",
children: Accordion content
,
};
it("renders without crashing", () => {
render();
expect(screen.getByText("Accordion Title")).toBeInTheDocument();
});
it("has displayName set to Accordion", () => {
expect(Accordion.displayName).toBe("Accordion");
});
describe("initial state", () => {
it("starts closed by default", () => {
render();
const collapse = screen.getByTestId("collapse");
expect(collapse).toHaveAttribute("data-open", "false");
});
it("starts open when defaultOpen is true", () => {
render();
const collapse = screen.getByTestId("collapse");
expect(collapse).toHaveAttribute("data-open", "true");
});
it("starts closed when defaultOpen is false", () => {
render();
const collapse = screen.getByTestId("collapse");
expect(collapse).toHaveAttribute("data-open", "false");
});
});
describe("openOnlyOnDesktop", () => {
it("opens on desktop (width >= 1024)", () => {
Object.defineProperty(window, "innerWidth", {
writable: true,
value: 1024,
});
render();
const collapse = screen.getByTestId("collapse");
expect(collapse).toHaveAttribute("data-open", "true");
});
it("stays closed on mobile (width < 1024)", () => {
Object.defineProperty(window, "innerWidth", {
writable: true,
value: 768,
});
render();
const collapse = screen.getByTestId("collapse");
expect(collapse).toHaveAttribute("data-open", "false");
});
it("ignores defaultOpen when openOnlyOnDesktop is true", () => {
Object.defineProperty(window, "innerWidth", {
writable: true,
value: 500,
});
render(
);
const collapse = screen.getByTestId("collapse");
expect(collapse).toHaveAttribute("data-open", "false");
});
});
describe("toggle behavior", () => {
it("opens when button is clicked while closed", () => {
render();
const button = screen.getByRole("button");
fireEvent.click(button);
const collapse = screen.getByTestId("collapse");
expect(collapse).toHaveAttribute("data-open", "true");
});
it("closes when button is clicked while open", () => {
render();
const button = screen.getByRole("button");
fireEvent.click(button);
const collapse = screen.getByTestId("collapse");
expect(collapse).toHaveAttribute("data-open", "false");
});
it("toggles multiple times", () => {
render();
const button = screen.getByRole("button");
const collapse = screen.getByTestId("collapse");
fireEvent.click(button);
expect(collapse).toHaveAttribute("data-open", "true");
fireEvent.click(button);
expect(collapse).toHaveAttribute("data-open", "false");
fireEvent.click(button);
expect(collapse).toHaveAttribute("data-open", "true");
});
});
describe("icon state", () => {
it("shows keyboard_arrow_down when closed", () => {
render();
const icon = screen.getByTestId("material-icon");
expect(icon).toHaveAttribute("data-name", "keyboard_arrow_down");
});
it("shows keyboard_arrow_up when open", () => {
render();
const icon = screen.getByTestId("material-icon");
expect(icon).toHaveAttribute("data-name", "keyboard_arrow_up");
});
it("toggles icon when clicked", () => {
render();
const button = screen.getByRole("button");
const icon = screen.getByTestId("material-icon");
expect(icon).toHaveAttribute("data-name", "keyboard_arrow_down");
fireEvent.click(button);
expect(icon).toHaveAttribute("data-name", "keyboard_arrow_up");
});
});
describe("children rendering", () => {
it("renders children when open", () => {
render();
expect(screen.getByText("Accordion content")).toBeInTheDocument();
});
it("does not render children when closed", () => {
render();
expect(screen.queryByText("Accordion content")).not.toBeInTheDocument();
});
it("renders complex children", () => {
render(
Child 1
Child 2
);
const button = screen.getByRole("button");
fireEvent.click(button);
expect(screen.getByTestId("child-1")).toBeInTheDocument();
expect(screen.getByTestId("child-2")).toBeInTheDocument();
});
});
describe("className props", () => {
it("applies containerClassName to outer div", () => {
const { container } = render(
);
expect(container.firstChild).toHaveClass("custom-container");
});
it("applies titleClassName to title span", () => {
render();
const titleSpan = screen.getByText("Accordion Title");
expect(titleSpan).toHaveClass("custom-title");
});
it("applies buttonClassName to button", () => {
render();
const button = screen.getByRole("button");
expect(button.className).toContain("custom-button");
});
it("applies iconClassName to material icon", () => {
render();
const icon = screen.getByTestId("material-icon");
expect(icon).toHaveClass("custom-icon");
});
it("applies className to content div when open", () => {
render(
);
const contentDiv = screen.getByText("Accordion content").parentElement;
expect(contentDiv).toHaveClass("custom-content");
});
});
describe("borderRadiusNone", () => {
it("applies rounded-none when borderRadiusNone is true", () => {
const { container } = render(
);
expect(container.firstChild).toHaveClass("rounded-none");
});
it("applies rounded-surface-xs when borderRadiusNone is false", () => {
const { container } = render(
);
expect(container.firstChild).toHaveClass("rounded-surface-xs");
});
it("applies rounded-surface-xs by default", () => {
const { container } = render();
expect(container.firstChild).toHaveClass("rounded-surface-xs");
});
it("applies rounded-none to button when borderRadiusNone is true", () => {
render();
const button = screen.getByRole("button");
expect(button.className).toContain("rounded-none");
});
it("applies rounded-t-surface-xs to button when borderRadiusNone is false", () => {
render();
const button = screen.getByRole("button");
expect(button.className).toContain("rounded-t-surface-xs");
});
});
describe("button attributes", () => {
it("renders button with type button", () => {
render();
const button = screen.getByRole("button");
expect(button).toHaveAttribute("type", "button");
});
});
});