"use client";

import { useCallback, useEffect, useState } from "react";
import Image from "next/image";
import { AlertCircle, CheckCircle2, ChevronDown, ChevronUp, Loader2, PowerOff, Save } from "lucide-react";
import { resolveLogoSrc } from "@/lib/bank-logos";
import { CustomSelect } from "@/components/ui/custom-select";

/*
  O cartão do Asaas na tela de Integrações.

  Mora num arquivo próprio, e não dentro de `page.tsx`, porque aquela página já
  carrega frete, Mercado Pago e a aba de novidades em seiscentas linhas. Um
  provedor a mais lá dentro tornaria qualquer mexida futura uma leitura de
  arqueologia.

  O que esta tela sabe e o Mercado Pago não precisa saber:

    1. A chave é conferida no Asaas antes de gravar, então salvar pode falhar
       por motivo de verdade — e o motivo aparece escrito.
    2. Conectar não tira nada de ninguém. Quem recebe o quê é decidido na
       engrenagem, acima dos dois cartões.
    3. A chave nunca volta do servidor. Campo em branco quer dizer "não mexi".

  E UMA REGRA DE LINGUAGEM: esta tela é do lojista, não do desenvolvedor. Ela
  não fala de ambiente, de sandbox nem de como o sistema foi feito por dentro.
  O ambiente de teste existe, mas só aparece na máquina de quem desenvolve; no
  ar, o lojista vê uma integração e uma chave, que é tudo que lhe diz respeito.
*/

const LOGO = "/banks-repository/Asaas IP S.A/header-logo-azul.svg";

/* Em produção não existe escolha de ambiente: a integração é de produção e
   pronto. O seletor e o campo de teste só aparecem na máquina de quem
   desenvolve, que é o único lugar onde o sandbox do Asaas funciona. */
const EM_DESENVOLVIMENTO = process.env.NODE_ENV !== "production";

type Config = {
  active: boolean;
  environment: "sandbox" | "production";
  checkout_enabled: boolean;
  auto_create_order_on_approved_payment: boolean;
  bank_account_id: string;
  sandbox_api_key: string;
  production_api_key: string;
  aceita_pix: boolean;
  aceita_boleto: boolean;
  aceita_cartao: boolean;
  dias_para_vencimento: number;
  tem_chave_sandbox: boolean;
  tem_chave_producao: boolean;
  conta_nome: string | null;
  conta_documento: string | null;
  webhook_url: string | null;
};

const VAZIA: Config = {
  active: false,
  environment: "production",
  checkout_enabled: true,
  auto_create_order_on_approved_payment: true,
  bank_account_id: "",
  sandbox_api_key: "",
  production_api_key: "",
  aceita_pix: true,
  aceita_boleto: true,
  aceita_cartao: false,
  dias_para_vencimento: 1,
  tem_chave_sandbox: false,
  tem_chave_producao: false,
  conta_nome: null,
  conta_documento: null,
  webhook_url: null,
};

/* Os três meios, com o que cada um significa para quem compra. O cartão diz
   que sai da loja porque essa é a única diferença que o lojista precisa pesar
   antes de ligar — e escondê-la seria deixá-lo descobrir pelo cliente. */
const MEIOS = [
  {
    chave: "aceita_pix" as const,
    titulo: "Pix",
    apoio: "QR Code e copia e cola na própria loja. Aprovação na hora.",
  },
  {
    chave: "aceita_boleto" as const,
    titulo: "Boleto",
    apoio: "Linha digitável e PDF na própria loja. Compensa em até 3 dias úteis.",
  },
  {
    chave: "aceita_cartao" as const,
    titulo: "Cartão de crédito",
    apoio: "Concluído em uma página segura do Asaas: o cliente sai da loja e volta assim que aprova.",
  },
];

type Conta = { id: string; name: string; bank_name?: string | null; bank_code?: string | null };
type Aviso = { tipo: "success" | "error" | "info"; texto: string };

export default function CartaoDoAsaas({
  aberto,
  aoAbrir,
  podeSalvar,
  aoMudarOProvedor,
}: {
  aberto: boolean;
  aoAbrir: () => void;
  podeSalvar: boolean;
  aoMudarOProvedor: () => void;
}) {
  const [carregando, setCarregando] = useState(true);
  const [salvando, setSalvando] = useState(false);
  const [config, setConfig] = useState<Config>(VAZIA);
  const [contas, setContas] = useState<Conta[]>([]);
  const [aviso, setAviso] = useState<Aviso | null>(null);

  const carregar = useCallback(async () => {
    try {
      setCarregando(true);
      const resposta = await fetch("/api/integrations/asaas", { cache: "no-store" });
      const corpo = (await resposta.json().catch(() => null)) as
        | { error?: string; config?: Partial<Config>; bank_accounts?: Conta[] }
        | null;

      if (!resposta.ok || corpo?.error) throw new Error(corpo?.error || "Erro ao carregar o Asaas.");

      setConfig({
        ...VAZIA,
        ...corpo?.config,
        /* No ar não há o que escolher: a integração é de produção. Isto também
           conserta sozinho quem tiver sobrado apontando para teste. */
        environment: EM_DESENVOLVIMENTO ? (corpo?.config?.environment ?? "production") : "production",
        sandbox_api_key: "",
        production_api_key: "",
      });
      setContas(corpo?.bank_accounts || []);
    } catch (erro) {
      console.error(erro);
      setAviso({ tipo: "error", texto: "Erro ao carregar a configuração do Asaas." });
    } finally {
      setCarregando(false);
    }
  }, []);

  useEffect(() => {
    void carregar();
  }, [carregar]);

  const usaChaveDeTeste = EM_DESENVOLVIMENTO && config.environment === "sandbox";
  const temChaveDoAmbiente = usaChaveDeTeste ? config.tem_chave_sandbox : config.tem_chave_producao;
  const chaveDigitada = usaChaveDeTeste ? config.sandbox_api_key : config.production_api_key;
  const nenhumMeioLigado = !config.aceita_pix && !config.aceita_boleto && !config.aceita_cartao;

  async function gravar(ligado: boolean) {
    setSalvando(true);
    setAviso(null);

    try {
      const resposta = await fetch("/api/integrations/asaas", {
        method: "PUT",
        headers: { "content-type": "application/json" },
        body: JSON.stringify({ ...config, active: ligado }),
      });
      const corpo = (await resposta.json().catch(() => null)) as
        | {
            error?: string;
            conta?: { nome?: string | null };
            webhook?: { registrado?: boolean; erro?: string | null };
          }
        | null;

      if (!resposta.ok || corpo?.error) throw new Error(corpo?.error || "Erro ao salvar.");

      if (!ligado) {
        setAviso({ tipo: "info", texto: "Asaas desconectado. O que ia para ele volta para o Mercado Pago." });
      } else {
        const partes = [`Conectado à conta ${corpo?.conta?.nome || "do Asaas"}.`];
        partes.push("Escolha em “Onde cada provedor recebe” o que vem para cá.");
        if (corpo?.webhook?.erro) partes.push(`A confirmação automática não pôde ser ativada: ${corpo.webhook.erro}`);
        setAviso({ tipo: corpo?.webhook?.erro ? "info" : "success", texto: partes.join(" ") });
      }

      await carregar();
      aoMudarOProvedor();
    } catch (erro) {
      console.error(erro);
      setAviso({ tipo: "error", texto: erro instanceof Error ? erro.message : "Erro ao salvar." });
    } finally {
      setSalvando(false);
    }
  }

  const opcoesDeConta = [
    { value: "", label: "Sem conta específica" },
    ...contas.map((conta) => ({
      value: conta.id,
      label: conta.name,
      selected_label: conta.name,
      image_url: resolveLogoSrc(null, conta.bank_code || null, conta.bank_name || conta.name),
    })),
  ];

  return (
    <div className="bg-white rounded-2xl border border-zinc-200 shadow-sm overflow-hidden transition-all">
      <div className="p-5 flex items-center justify-between cursor-pointer hover:bg-zinc-50" onClick={aoAbrir}>
        <div className="flex items-center gap-4">
          <div className="w-28 h-12 flex items-center justify-start shrink-0">
            <Image src={resolveLogoSrc(LOGO, null, null)} alt="Asaas" width={112} height={48} className="object-contain w-full h-full" unoptimized />
          </div>
          <div>
            <div className="flex items-center gap-2">
              <h3 className="font-bold text-zinc-900">Asaas</h3>
              {config.active && (
                <span className="px-2 py-0.5 rounded-full bg-emerald-100 text-emerald-700 text-[10px] font-bold uppercase tracking-wider">
                  Ativo
                </span>
              )}
              {usaChaveDeTeste && config.active && (
                <span className="px-2 py-0.5 rounded-full bg-amber-100 text-amber-700 text-[10px] font-bold uppercase tracking-wider">
                  Teste
                </span>
              )}
            </div>
            <p className="text-sm text-zinc-500">Receba por Pix, boleto e cartão direto na sua conta Asaas.</p>
          </div>
        </div>
        <div className="text-zinc-400">{aberto ? <ChevronUp size={20} /> : <ChevronDown size={20} />}</div>
      </div>

      {aberto && (
        <div className="p-5 border-t border-zinc-100 bg-zinc-50/50">
          {carregando ? (
            <div className="flex h-40 items-center justify-center rounded-2xl border border-zinc-200 bg-white text-zinc-500">
              <Loader2 className="mr-2 h-4 w-4 animate-spin" />
              Carregando Asaas...
            </div>
          ) : (
            <div className="space-y-5">
              {config.active && config.conta_nome && (
                <div className="rounded-xl border border-emerald-100 bg-emerald-50 p-3 text-sm text-emerald-800 flex items-start gap-2">
                  <CheckCircle2 size={16} className="mt-0.5 shrink-0" />
                  <span>
                    Conectado à conta <strong>{config.conta_nome}</strong>
                    {config.conta_documento ? ` (${config.conta_documento})` : ""}
                    {usaChaveDeTeste ? ", em ambiente de teste." : "."}
                  </span>
                </div>
              )}

              <div className="grid gap-4 xl:grid-cols-3">
                {/* ------------------------------------------------ checkout */}
                <div className="flex h-full flex-col rounded-2xl border border-zinc-200 bg-white p-4 md:p-5">
                  <div className="min-h-[64px]">
                    <h4 className="text-sm font-semibold text-zinc-900">Checkout</h4>
                    <p className="mt-1 text-xs leading-5 text-zinc-500">Defina como o pagamento se comporta no catálogo.</p>
                  </div>
                  <div className="mt-4 grid flex-1 gap-3 content-start">
                    <label className="flex min-h-[56px] items-center gap-3 rounded-2xl border border-zinc-200 bg-zinc-50 px-4 py-3">
                      <input
                        type="checkbox"
                        checked={config.checkout_enabled}
                        onChange={(e) => setConfig((p) => ({ ...p, checkout_enabled: e.target.checked }))}
                        className="h-4 w-4 rounded border-zinc-300 text-blue-600 focus:ring-blue-500"
                      />
                      <span className="text-sm font-medium text-zinc-700">Ativar checkout no catálogo</span>
                    </label>

                    <label className="flex min-h-[56px] items-center gap-3 rounded-2xl border border-zinc-200 bg-zinc-50 px-4 py-3">
                      <input
                        type="checkbox"
                        checked={config.auto_create_order_on_approved_payment}
                        onChange={(e) =>
                          setConfig((p) => ({ ...p, auto_create_order_on_approved_payment: e.target.checked }))
                        }
                        className="h-4 w-4 rounded border-zinc-300 text-blue-600 focus:ring-blue-500"
                      />
                      <span className="text-sm font-medium text-zinc-700">Dar baixa automática no pedido pago</span>
                    </label>
                  </div>
                </div>

                {/* ------------------------------------------ meios aceitos */}
                <div className="flex h-full flex-col rounded-2xl border border-zinc-200 bg-white p-4 md:p-5">
                  <div className="min-h-[64px]">
                    <h4 className="text-sm font-semibold text-zinc-900">Meios de pagamento</h4>
                    <p className="mt-1 text-xs leading-5 text-zinc-500">
                      Escolha o que o Asaas pode cobrar. Vale só para o que vier para ele.
                    </p>
                  </div>
                  <div className="mt-4 grid flex-1 gap-2 content-start">
                    {MEIOS.map((meio) => (
                      <label
                        key={meio.chave}
                        className="flex items-start gap-3 rounded-2xl border border-zinc-200 bg-zinc-50 px-4 py-3"
                      >
                        <input
                          type="checkbox"
                          checked={config[meio.chave]}
                          onChange={(e) => setConfig((p) => ({ ...p, [meio.chave]: e.target.checked }))}
                          className="mt-0.5 h-4 w-4 shrink-0 rounded border-zinc-300 text-blue-600 focus:ring-blue-500"
                        />
                        <span>
                          <span className="block text-sm font-medium text-zinc-700">{meio.titulo}</span>
                          <span className="mt-0.5 block text-xs leading-5 text-zinc-500">{meio.apoio}</span>
                        </span>
                      </label>
                    ))}
                  </div>
                </div>

                {/* ------------------------------ recebimento e credenciais */}
                <div className="flex h-full flex-col gap-4">
                  <div className="flex flex-col rounded-2xl border border-zinc-200 bg-white p-4 md:p-5">
                    <h4 className="text-sm font-semibold text-zinc-900">Recebimento</h4>
                    <p className="mt-1 text-xs leading-5 text-zinc-500">Onde o dinheiro entra e em quantos dias vence.</p>
                    <div className="mt-4 grid gap-4">
                      <label className="space-y-1.5">
                        <span className="text-sm font-medium text-zinc-700">Conta bancária para baixa automática</span>
                        <CustomSelect
                          options={opcoesDeConta}
                          value={config.bank_account_id}
                          onChange={(valor) => setConfig((p) => ({ ...p, bank_account_id: valor }))}
                          placeholder="Sem conta específica"
                          forceOpenDown
                          searchable
                          className="w-full"
                        />
                      </label>

                      <label className="space-y-1.5">
                        <span className="text-sm font-medium text-zinc-700">Dias até o vencimento</span>
                        <input
                          type="number"
                          min={0}
                          max={90}
                          value={config.dias_para_vencimento}
                          onChange={(e) =>
                            setConfig((p) => ({ ...p, dias_para_vencimento: Math.max(0, Math.min(90, Number(e.target.value) || 0)) }))
                          }
                          className="w-full rounded-xl border border-zinc-200 bg-white px-3 py-2.5 text-sm focus:border-blue-500 focus:outline-none focus:ring-2 focus:ring-blue-500/20"
                        />
                        <span className="block text-xs leading-5 text-zinc-500">
                          Prazo do Pix e do boleto. Zero vence no mesmo dia. O cartão é cobrado na hora.
                        </span>
                      </label>
                    </div>
                  </div>

                  <div className="flex flex-col rounded-2xl border border-zinc-200 bg-white p-4 md:p-5">
                    <h4 className="text-sm font-semibold text-zinc-900">Chave de API</h4>
                    <p className="mt-1 text-xs leading-5 text-zinc-500">
                      No painel do Asaas, em Integrações, gere uma chave e cole aqui.
                    </p>
                    <div className="mt-4 grid gap-4">
                      {EM_DESENVOLVIMENTO && (
                        <label className="space-y-1.5">
                          <span className="text-sm font-medium text-zinc-700">Ambiente</span>
                          <CustomSelect
                            options={[
                              { value: "production", label: "Produção" },
                              { value: "sandbox", label: "Teste (sandbox)" },
                            ]}
                            value={config.environment}
                            onChange={(valor) => setConfig((p) => ({ ...p, environment: valor as Config["environment"] }))}
                            forceOpenDown
                            className="w-full"
                          />
                        </label>
                      )}

                      <label className="space-y-1.5">
                        <span className="text-sm font-medium text-zinc-700">
                          {usaChaveDeTeste ? "Chave de teste" : "Chave de produção"}
                        </span>
                        <input
                          type="password"
                          autoComplete="off"
                          value={chaveDigitada}
                          onChange={(e) =>
                            setConfig((p) =>
                              usaChaveDeTeste
                                ? { ...p, sandbox_api_key: e.target.value }
                                : { ...p, production_api_key: e.target.value }
                            )
                          }
                          className="w-full rounded-xl border border-zinc-200 bg-white px-3 py-2.5 text-sm focus:border-blue-500 focus:outline-none focus:ring-2 focus:ring-blue-500/20"
                          placeholder={temChaveDoAmbiente ? "Já configurada. Preencha só para trocar." : "$aact_..."}
                        />
                      </label>
                    </div>
                  </div>
                </div>
              </div>

              {/* Conectado e sem meio nenhum é uma integração que não cobra
                  nada, e nada na tela diria isso sozinho. */}
              {config.active && nenhumMeioLigado && (
                <div className="rounded-xl border border-amber-100 bg-amber-50 p-3 text-sm text-amber-800 flex items-start gap-2">
                  <AlertCircle size={16} className="mt-0.5 shrink-0" />
                  <span>
                    Nenhum meio de pagamento marcado. Enquanto estiver assim, o Asaas não cobra nada e tudo continua no
                    Mercado Pago.
                  </span>
                </div>
              )}

              {aviso && (
                <div
                  className={`rounded-xl border p-3 text-sm flex items-start gap-2 ${
                    aviso.tipo === "success"
                      ? "border-emerald-100 bg-emerald-50 text-emerald-700"
                      : aviso.tipo === "info"
                        ? "border-blue-100 bg-blue-50 text-blue-800"
                        : "border-red-100 bg-red-50 text-red-700"
                  }`}
                >
                  {aviso.tipo === "error" ? (
                    <AlertCircle size={16} className="mt-0.5 shrink-0" />
                  ) : (
                    <CheckCircle2 size={16} className="mt-0.5 shrink-0" />
                  )}
                  <span>{aviso.texto}</span>
                </div>
              )}

              {podeSalvar && (
                <div className="flex flex-wrap items-center justify-between gap-3">
                  <p className="text-xs leading-5 text-zinc-500">
                    {config.active
                      ? "Conectado. O que ele recebe você decide em “Onde cada provedor recebe”."
                      : "Conectar não desliga o Mercado Pago: os dois convivem."}
                  </p>
                  <div className="flex items-center gap-2">
                    {config.active && (
                      <button
                        onClick={() => gravar(false)}
                        disabled={salvando}
                        className="inline-flex items-center justify-center gap-2 rounded-xl border border-zinc-200 bg-white px-4 py-2.5 text-sm font-medium text-zinc-700 transition-all hover:bg-zinc-50 disabled:opacity-50"
                      >
                        <PowerOff size={16} />
                        Desconectar
                      </button>
                    )}
                    <button
                      onClick={() => gravar(true)}
                      disabled={salvando || (!temChaveDoAmbiente && !chaveDigitada)}
                      className="inline-flex items-center justify-center gap-2 rounded-xl bg-[var(--ks-color-primary)] px-5 py-2.5 text-sm font-medium text-white transition-all hover:bg-[var(--ks-color-primary-strong)] disabled:opacity-50"
                    >
                      {salvando ? <Loader2 size={16} className="animate-spin" /> : <Save size={16} />}
                      {config.active ? "Salvar Asaas" : "Conectar Asaas"}
                    </button>
                  </div>
                </div>
              )}
            </div>
          )}
        </div>
      )}
    </div>
  );
}
