// @vitest-environment jsdom
import { cleanup, render, screen } from "@testing-library/react";
import { userEvent } from "@testing-library/user-event";
import { afterEach, beforeAll, describe, expect, it, vi } from "vitest";
import { polyfillDialog } from "../../__tests__/polyfill-dialog.js";
import { Dialog, DialogHeader } from "../ui/dialog.js";

beforeAll(() => {
	polyfillDialog();
});

afterEach(cleanup);

describe("Dialog", () => {
	it("opens when open=true", () => {
		render(
			<Dialog open={true} onClose={() => {}}>
				Content
			</Dialog>,
		);
		expect(screen.getByText("Content")).toBeDefined();
	});

	it("closes when open changes from true to false", () => {
		const { rerender } = render(
			<Dialog open={true} onClose={() => {}}>
				Content
			</Dialog>,
		);
		const dialog = document.querySelector("dialog");
		expect(dialog?.hasAttribute("open")).toBe(true);

		rerender(
			<Dialog open={false} onClose={() => {}}>
				Content
			</Dialog>,
		);
		expect(dialog?.hasAttribute("open")).toBe(false);
	});

	it("unmounts children when closed so internal state does not persist", () => {
		const { rerender } = render(
			<Dialog open={true} onClose={() => {}}>
				<span>Body</span>
			</Dialog>,
		);
		expect(screen.queryByText("Body")).not.toBeNull();

		rerender(
			<Dialog open={false} onClose={() => {}}>
				<span>Body</span>
			</Dialog>,
		);
		expect(screen.queryByText("Body")).toBeNull();
	});

	it("calls onClose on cancel event", () => {
		const onClose = vi.fn();
		render(
			<Dialog open={true} onClose={onClose}>
				Content
			</Dialog>,
		);
		const dialog = document.querySelector("dialog");
		dialog?.dispatchEvent(new Event("cancel"));
		expect(onClose).toHaveBeenCalledOnce();
	});
});

describe("DialogHeader", () => {
	it("renders title and close button", async () => {
		const onClose = vi.fn();
		render(<DialogHeader title="Test Title" onClose={onClose} />);

		expect(screen.getByText("Test Title")).toBeDefined();
		await userEvent.click(screen.getByRole("button"));
		expect(onClose).toHaveBeenCalledOnce();
	});
});
