import { describe, expect, it, vi } from "vitest";
import { render, screen } from "@testing-library/react";

const { replace, state } = vi.hoisted(() => ({
  replace: vi.fn(),
  state: { authInfo: null as { token: string; is_blocked?: number } | null, _hydrated: true },
}));

vi.mock("next/navigation", () => ({
  useRouter: () => ({ replace }),
}));
vi.mock("@/lib/auth/store", () => ({
  useAuthStore: (
    selector: (store: typeof state) => unknown,
  ) => selector(state),
}));

import AuthGuard from "@/components/AuthGuard";

describe("AuthGuard", () => {
  it("redirects unauthenticated dashboard visitors without showing children", () => {
    state.authInfo = null;
    state._hydrated = true;
    render(<AuthGuard variant="dashboard"><p>محتوى محمي</p></AuthGuard>);
    expect(replace).toHaveBeenCalledWith("/login");
    expect(screen.queryByText("محتوى محمي")).not.toBeInTheDocument();
  });

  it("redirects authenticated visitors away from auth pages", () => {
    state.authInfo = { token: "token", is_blocked: 0 };
    state._hydrated = true;
    render(<AuthGuard variant="auth"><p>تسجيل الدخول</p></AuthGuard>);
    expect(replace).toHaveBeenCalledWith("/");
    expect(screen.queryByText("تسجيل الدخول")).not.toBeInTheDocument();
  });

  it("keeps blocked users on auth pages instead of redirecting to the dashboard", () => {
    state.authInfo = { token: "token", is_blocked: 1 };
    state._hydrated = true;
    render(<AuthGuard variant="auth"><p>تسجيل الدخول</p></AuthGuard>);
    expect(replace).not.toHaveBeenCalled();
    expect(screen.getByText("تسجيل الدخول")).toBeInTheDocument();
  });

  it("redirects blocked dashboard visitors to login", () => {
    state.authInfo = { token: "token", is_blocked: 1 };
    state._hydrated = true;
    render(<AuthGuard variant="dashboard"><p>محتوى محمي</p></AuthGuard>);
    expect(replace).toHaveBeenCalledWith("/login");
    expect(screen.queryByText("محتوى محمي")).not.toBeInTheDocument();
  });

  it("shows a hydration placeholder before access is decided", () => {
    state.authInfo = null;
    state._hydrated = false;
    render(<AuthGuard variant="dashboard"><p>محتوى محمي</p></AuthGuard>);
    expect(screen.queryByText("محتوى محمي")).not.toBeInTheDocument();
    expect(document.querySelector(".ri-loader-4-line")).toBeInTheDocument();
    expect(replace).not.toHaveBeenCalled();
  });

  it("renders allowed children after hydration", () => {
    state.authInfo = { token: "token", is_blocked: 0 };
    state._hydrated = true;
    render(<AuthGuard variant="dashboard"><p>لوحة المستثمر</p></AuthGuard>);
    expect(screen.getByText("لوحة المستثمر")).toBeInTheDocument();
  });
});
