"use client";

import { useCallback, useEffect, useRef, useState } from "react";
import Link from "next/link";
import { ArrowLeft, RotateCw } from "lucide-react";

import type { AmbienteFiscal, PainelFiscal } from "@/lib/fiscal-owner";

import AbaCompras from "./aba-compras";
import AbaEmpresas from "./aba-empresas";
import AbaPacotes from "./aba-pacotes";
import AbaRegras from "./aba-regras";
import AbaVisaoGeral from "./aba-visao-geral";
import { pedir, Recado } from "./ui";

export type Aba = "geral" | "pacotes" | "empresas" | "compras" | "regras";

export type Avisar = (tom: "ok" | "erro", texto: string) => void;

const NOMES_DOS_AMBIENTES: Record<AmbienteFiscal, string> = {
  producao: "Produção",
  sandbox: "Sandbox (testes)",
};

export default function PainelDasNotas({
  inicial,
  ambienteInicial,
  erroInicial,
}: {
  inicial: PainelFiscal | null;
  ambienteInicial: AmbienteFiscal;
  erroInicial: string | null;
}) {
  const [ambiente, setAmbiente] = useState<AmbienteFiscal>(inicial?.ambiente ?? ambienteInicial);
  const [painel, setPainel] = useState<PainelFiscal | null>(inicial);
  const [carregando, setCarregando] = useState(false);
  const [erro, setErro] = useState<string | null>(erroInicial);
  const [atualizadoEm, setAtualizadoEm] = useState<number | null>(null);
  const [aba, setAba] = useState<Aba>("geral");
  const [aviso, setAviso] = useState<{ tom: "ok" | "erro"; texto: string; id: number } | null>(null);
  const ultimoPedido = useRef(0);

  const recarregar = useCallback(async (qual: AmbienteFiscal) => {
    const numero = ++ultimoPedido.current;
    setCarregando(true);
    try {
      const dados = await pedir<PainelFiscal>(`/api/fiscal?ambiente=${qual}`);
      if (numero !== ultimoPedido.current) return;
      setPainel(dados);
      setErro(null);
      setAtualizadoEm(Date.now());
    } catch (falha) {
      if (numero !== ultimoPedido.current) return;
      setErro(falha instanceof Error ? falha.message : "Não foi possível carregar agora.");
    } finally {
      if (numero === ultimoPedido.current) setCarregando(false);
    }
  }, []);

  const avisar = useCallback<Avisar>((tom, texto) => setAviso({ tom, texto, id: Date.now() }), []);

  useEffect(() => {
    if (!aviso) return;
    const relogio = window.setTimeout(() => setAviso(null), aviso.tom === "erro" ? 6000 : 3500);
    return () => window.clearTimeout(relogio);
  }, [aviso]);

  function trocarAmbiente(novo: AmbienteFiscal) {
    if (novo === ambiente) return;
    setAmbiente(novo);
    setPainel(null);
    void recarregar(novo);
  }

  const atualizar = useCallback(() => recarregar(ambiente), [recarregar, ambiente]);

  const abas: Array<{ chave: Aba; rotulo: string; contagem?: number }> = [
    { chave: "geral", rotulo: "Visão geral" },
    { chave: "pacotes", rotulo: "Pacotes", contagem: painel?.pacotes.length },
    { chave: "empresas", rotulo: "Empresas", contagem: painel?.emissores.length },
    { chave: "compras", rotulo: "Compras", contagem: painel?.compras.filter((c) => c.status === "pendente").length || undefined },
    { chave: "regras", rotulo: "Regras" },
  ];

  return (
    <div className="min-h-screen bg-slate-50/50 p-4 font-sans sm:p-8 lg:p-10">
      <div className="mx-auto max-w-[1180px]">
        <div className="flex flex-wrap items-end justify-between gap-4">
          <div className="min-w-0">
            <Link href="/" className="inline-flex items-center gap-2 text-sm font-medium text-slate-500 hover:text-slate-900">
              <ArrowLeft size={16} />
              Voltar ao painel
            </Link>
            <h1 className="mt-3 text-2xl font-semibold tracking-tight text-slate-900">Notas fiscais</h1>
            <p className="mt-1 max-w-2xl text-sm text-slate-500">
              O plano da Spedy, os pacotes que as empresas compram, quem está emitindo e a saúde da emissão.
            </p>
          </div>

          <div className="flex flex-wrap items-center gap-2">
            <div className="inline-flex rounded-xl border border-slate-200 bg-white p-1 shadow-sm" role="radiogroup" aria-label="Ambiente">
              {(["producao", "sandbox"] as const).map((opcao) => (
                <button
                  key={opcao}
                  type="button"
                  role="radio"
                  aria-checked={ambiente === opcao}
                  onClick={() => trocarAmbiente(opcao)}
                  className={`h-9 rounded-lg px-3.5 text-sm font-medium transition ${
                    ambiente === opcao ? "bg-slate-900 text-white shadow-sm" : "text-slate-600 hover:bg-slate-50 hover:text-slate-900"
                  }`}
                >
                  {NOMES_DOS_AMBIENTES[opcao]}
                </button>
              ))}
            </div>
            <button
              type="button"
              onClick={() => void atualizar()}
              disabled={carregando}
              title={atualizadoEm ? `Atualizado às ${new Date(atualizadoEm).toLocaleTimeString("pt-BR", { hour: "2-digit", minute: "2-digit" })}` : undefined}
              className="inline-flex h-11 items-center gap-2 rounded-xl border border-slate-200 bg-white px-4 text-sm font-medium text-slate-700 shadow-sm transition hover:bg-slate-50 disabled:opacity-60"
            >
              <RotateCw size={15} className={carregando ? "animate-spin" : ""} />
              <span className="hidden sm:inline">{carregando ? "Atualizando…" : "Atualizar"}</span>
            </button>
          </div>
        </div>

        {painel && painel.ambiente !== painel.ambientePadrao ? (
          <div className="mt-4">
            <Recado tom="atencao">
              Você está olhando o ambiente <strong>{NOMES_DOS_AMBIENTES[painel.ambiente]}</strong>. Este servidor emite em{" "}
              <strong>{NOMES_DOS_AMBIENTES[painel.ambientePadrao]}</strong>; a fila e os avisos daqui cuidam só dele.
            </Recado>
          </div>
        ) : null}

        <div className="mt-6 flex gap-1 overflow-x-auto border-b border-slate-200" role="tablist" aria-label="Seções">
          {abas.map((item) => (
            <button
              key={item.chave}
              type="button"
              role="tab"
              aria-selected={aba === item.chave}
              onClick={() => setAba(item.chave)}
              className={`-mb-px inline-flex h-11 shrink-0 items-center gap-2 border-b-2 px-3 text-sm font-medium transition ${
                aba === item.chave ? "border-slate-900 text-slate-900" : "border-transparent text-slate-500 hover:text-slate-800"
              }`}
            >
              {item.rotulo}
              {typeof item.contagem === "number" ? (
                <span
                  className={`rounded-full px-1.5 py-0.5 text-[11px] font-semibold tabular-nums ${
                    aba === item.chave ? "bg-slate-900 text-white" : "bg-slate-100 text-slate-600"
                  }`}
                >
                  {item.contagem}
                </span>
              ) : null}
            </button>
          ))}
        </div>

        <div className="mt-6">
          {erro ? (
            <div className="mb-4">
              <Recado tom="erro">
                {erro}{" "}
                <button type="button" onClick={() => void atualizar()} className="font-semibold underline underline-offset-2">
                  Tentar de novo
                </button>
              </Recado>
            </div>
          ) : null}

          {!painel ? (
            erro ? null : <Esqueleto />
          ) : (
            <div className={carregando ? "opacity-60 transition-opacity" : "transition-opacity"} aria-busy={carregando}>
              {aba === "geral" ? <AbaVisaoGeral painel={painel} irPara={setAba} /> : null}
              {aba === "pacotes" ? <AbaPacotes painel={painel} aoMudar={atualizar} avisar={avisar} /> : null}
              {aba === "empresas" ? <AbaEmpresas painel={painel} aoMudar={atualizar} avisar={avisar} /> : null}
              {aba === "compras" ? <AbaCompras painel={painel} /> : null}
              {aba === "regras" ? <AbaRegras painel={painel} aoMudar={atualizar} avisar={avisar} /> : null}
            </div>
          )}
        </div>
      </div>

      {aviso ? (
        <div className="pointer-events-none fixed inset-x-0 bottom-6 z-[60] flex justify-center px-4" role="status" aria-live="polite">
          <div
            key={aviso.id}
            className={`pointer-events-auto rounded-xl px-4 py-3 text-sm font-medium shadow-lg ${
              aviso.tom === "erro" ? "bg-rose-600 text-white" : "bg-slate-900 text-white"
            }`}
          >
            {aviso.texto}
          </div>
        </div>
      ) : null}
    </div>
  );
}

function Esqueleto() {
  return (
    <div className="grid gap-4" aria-hidden>
      <div className="h-44 animate-pulse rounded-2xl border border-slate-200 bg-white" />
      <div className="grid gap-4 md:grid-cols-3">
        <div className="h-28 animate-pulse rounded-2xl border border-slate-200 bg-white" />
        <div className="h-28 animate-pulse rounded-2xl border border-slate-200 bg-white" />
        <div className="h-28 animate-pulse rounded-2xl border border-slate-200 bg-white" />
      </div>
      <div className="h-64 animate-pulse rounded-2xl border border-slate-200 bg-white" />
    </div>
  );
}
