"use client";
import { useState, useEffect, useRef, useCallback } from "react";
import {
  FlaskConical, Play, StopCircle, Send, RefreshCw,
  CheckCircle, XCircle, Clock, Zap, MessageSquare,
  ChevronRight, Phone, AlertCircle, Loader2, RotateCcw,
} from "lucide-react";
import PhoneInput from "@/components/PhoneInput";

// ─── Types ──────────────────────────────────────────────────────
interface Tree {
  id: string;
  name: string;
  description: string | null;
  triggerType: string;
  triggerLabel: string;
  triggerColor: string;
  nodeCount: number;
}
interface Msg {
  id: string;
  direction: "incoming" | "outgoing";
  text: string;
  sentAt: string;
  status: string;
}
interface Execution {
  node: string | null;
  type: string | null;
  status: string;
  executedAt: string | null;
}
interface JourneyStatus {
  id: string;
  status: string;
  treeName: string;
  currentNode: { name: string; type: string } | null;
  lastActiveAt: string;
  executions: Execution[];
}

// ─── Colour maps ────────────────────────────────────────────────
const TRIGGER_BG: Record<string, string> = {
  emerald: "bg-emerald-100 text-emerald-700 border-emerald-200",
  blue:    "bg-blue-100 text-blue-700 border-blue-200",
  amber:   "bg-amber-100 text-amber-700 border-amber-200",
  purple:  "bg-purple-100 text-purple-700 border-purple-200",
  gray:    "bg-gray-100 text-gray-600 border-gray-200",
};
const TRIGGER_DOT: Record<string, string> = {
  emerald: "bg-emerald-500", blue: "bg-blue-500",
  amber: "bg-amber-500",    purple: "bg-purple-500", gray: "bg-gray-400",
};
const NODE_ICON: Record<string, string> = {
  start: "▶", message: "💬", buttons: "🔘", ai_response: "🤖",
  condition: "🔀", wait: "⏳", end: "🏁", sentiment: "😊",
  save_var: "💾", retry: "🔄",
};

function timeSince(iso: string) {
  const s = Math.floor((Date.now() - new Date(iso).getTime()) / 1000);
  if (s < 60) return `${s}s ago`;
  if (s < 3600) return `${Math.floor(s / 60)}m ago`;
  return `${Math.floor(s / 3600)}h ago`;
}
function formatTime(iso: string) {
  return new Date(iso).toLocaleTimeString([], { hour: "2-digit", minute: "2-digit", second: "2-digit" });
}

// ════════════════════════════════════════════════════════════════
export default function TestRemindersPage() {
  const [trees,       setTrees]       = useState<Tree[]>([]);
  const [loading,     setLoading]     = useState(true);
  const [selected,    setSelected]    = useState<Tree | null>(null);
  const [phone,       setPhone]       = useState("");
  const [running,     setRunning]     = useState(false);
  const [journeyId,   setJourneyId]   = useState<string | null>(null);
  const [journey,     setJourney]     = useState<JourneyStatus | null>(null);
  const [messages,    setMessages]    = useState<Msg[]>([]);
  const [replyText,   setReplyText]   = useState("");
  const [replySending,setReplySending]= useState(false);
  const [error,       setError]       = useState<string | null>(null);
  const [startError,  setStartError]  = useState<string | null>(null);
  const chatRef  = useRef<HTMLDivElement>(null);
  const pollRef  = useRef<ReturnType<typeof setInterval> | null>(null);

  // ── Load trees on mount ───────────────────────────────────────
  useEffect(() => {
    fetch("/api/test-reminders?action=trees")
      .then(r => r.json())
      .then(d => { setTrees(d.trees ?? []); setLoading(false); })
      .catch(() => setLoading(false));
  }, []);

  // ── Auto-scroll chat ──────────────────────────────────────────
  useEffect(() => {
    if (chatRef.current) {
      chatRef.current.scrollTop = chatRef.current.scrollHeight;
    }
  }, [messages]);

  // ── Poll for messages while journey is active ─────────────────
  const poll = useCallback(async (jId: string) => {
    try {
      const res  = await fetch(`/api/test-reminders?action=status&journeyId=${jId}`);
      const data = await res.json();
      if (data.journey) setJourney(data.journey);
      if (data.messages) setMessages(data.messages);
      // Stop polling when done
      if (data.journey?.status !== "active" && pollRef.current) {
        clearInterval(pollRef.current);
        pollRef.current = null;
      }
    } catch { /* ignore */ }
  }, []);

  useEffect(() => {
    if (!journeyId) return;
    poll(journeyId); // immediate first poll
    pollRef.current = setInterval(() => poll(journeyId), 1500);
    return () => { if (pollRef.current) clearInterval(pollRef.current); };
  }, [journeyId, poll]);

  // ── Start test ────────────────────────────────────────────────
  const startTest = async () => {
    if (!selected || !phone.trim()) return;
    setRunning(true);
    setStartError(null);
    setMessages([]);
    setJourney(null);
    setJourneyId(null);
    try {
      const res  = await fetch("/api/test-reminders", {
        method:  "POST",
        headers: { "Content-Type": "application/json" },
        body:    JSON.stringify({ action: "run", treeId: selected.id, phone: phone.trim() }),
      });
      const data = await res.json();
      if (data.error) { setStartError(data.error); setRunning(false); return; }
      setJourneyId(data.journeyId);
    } catch (e: any) {
      setStartError(e.message ?? "Failed to start test");
      setRunning(false);
    }
  };

  // ── Stop test ─────────────────────────────────────────────────
  const stopTest = async () => {
    if (!journeyId) return;
    await fetch("/api/test-reminders", {
      method:  "POST",
      headers: { "Content-Type": "application/json" },
      body:    JSON.stringify({ action: "stop", journeyId }),
    });
    if (pollRef.current) { clearInterval(pollRef.current); pollRef.current = null; }
    setRunning(false);
    setJourneyId(null);
  };

  // ── Reset ─────────────────────────────────────────────────────
  const reset = () => {
    if (pollRef.current) { clearInterval(pollRef.current); pollRef.current = null; }
    setRunning(false);
    setJourneyId(null);
    setJourney(null);
    setMessages([]);
    setReplyText("");
    setStartError(null);
    setError(null);
  };

  // ── Send reply ────────────────────────────────────────────────
  const sendReply = async () => {
    if (!replyText.trim() || !journeyId || replySending) return;
    const text = replyText.trim();
    setReplyText("");
    setReplySending(true);
    try {
      await fetch("/api/test-reminders", {
        method:  "POST",
        headers: { "Content-Type": "application/json" },
        body:    JSON.stringify({ action: "reply", journeyId, message: text }),
      });
      // Messages will update via next poll
    } catch { /* ignore */ }
    finally { setReplySending(false); }
  };

  const isActive   = journey?.status === "active";
  const isComplete = journey?.status === "completed" || journey?.status === "paused";
  const outgoing   = messages.filter(m => m.direction === "outgoing");

  // ════════════════════════════════════════════════════════════════
  return (
    <div className="h-full flex flex-col gap-0 max-w-7xl mx-auto">

      {/* ── Header ── */}
      <div className="flex items-center gap-3 mb-6 animate-fade-in">
        <div className="w-10 h-10 rounded-xl bg-violet-500/10 flex items-center justify-center">
          <FlaskConical size={18} className="text-violet-500" />
        </div>
        <div>
          <h1 className="text-xl font-bold text-dark">Reminder Testing</h1>
          <p className="text-xs text-muted">Fire any reminder tree to your real WhatsApp instantly — all waits skipped</p>
        </div>
        {(journeyId || messages.length > 0) && (
          <button onClick={reset}
            className="ml-auto flex items-center gap-1.5 text-xs text-muted hover:text-dark px-3 py-1.5 rounded-lg border border-gray-200 hover:border-gray-300 transition-all">
            <RotateCcw size={12} /> New Test
          </button>
        )}
      </div>

      <div className="flex gap-5 flex-1 min-h-0">

        {/* ══ LEFT PANEL — Tree selection ══════════════════════════ */}
        <div className="w-[340px] shrink-0 flex flex-col gap-4">

          {/* Phone input */}
          <div className="card p-4">
            <label className="text-xs font-semibold text-muted uppercase tracking-wide mb-2 block">
              Send test messages to
            </label>
            <PhoneInput
              value={phone}
              onChange={setPhone}
              variant="dashboard"
              height="h-[40px]"
              placeholder="5X XXX XXXX"
              disabled={!!journeyId}
            />
            <p className="text-[10px] text-muted mt-1.5">Messages sent to this WhatsApp number in real-time</p>
          </div>

          {/* Tree list */}
          <div className="card p-4 flex-1 overflow-auto">
            <p className="text-xs font-semibold text-muted uppercase tracking-wide mb-3">
              Active Reminder Trees
            </p>

            {loading ? (
              <div className="flex flex-col gap-2">
                {[1,2,3].map(i => (
                  <div key={i} className="h-16 rounded-xl bg-gray-100 animate-pulse" />
                ))}
              </div>
            ) : trees.length === 0 ? (
              <div className="text-center py-8">
                <p className="text-sm text-muted">No active trees found.</p>
                <p className="text-xs text-muted mt-1">Activate a tree in Reminder Trees first.</p>
              </div>
            ) : (
              <div className="flex flex-col gap-2">
                {trees.map(tree => {
                  const isSelected = selected?.id === tree.id;
                  const dotColor   = TRIGGER_DOT[tree.triggerColor] ?? TRIGGER_DOT.gray;
                  const badgeClass = TRIGGER_BG[tree.triggerColor]  ?? TRIGGER_BG.gray;
                  return (
                    <button key={tree.id}
                      onClick={() => { if (!journeyId) setSelected(isSelected ? null : tree); }}
                      disabled={!!journeyId}
                      className={`w-full text-left p-3 rounded-xl border transition-all group ${
                        isSelected
                          ? "border-primary-400 bg-primary-50 shadow-sm"
                          : "border-gray-200 hover:border-gray-300 hover:bg-gray-50 disabled:opacity-50 disabled:cursor-not-allowed"
                      }`}
                    >
                      <div className="flex items-start gap-2.5">
                        <div className={`w-2 h-2 rounded-full mt-1.5 shrink-0 ${dotColor}`} />
                        <div className="flex-1 min-w-0">
                          <p className="text-[13px] font-semibold text-dark truncate">{tree.name}</p>
                          {tree.description && (
                            <p className="text-[11px] text-muted truncate mt-0.5">{tree.description}</p>
                          )}
                          <div className="flex items-center gap-2 mt-1.5">
                            <span className={`text-[10px] font-semibold px-2 py-0.5 rounded-full border ${badgeClass}`}>
                              {tree.triggerLabel}
                            </span>
                            <span className="text-[10px] text-muted">{tree.nodeCount} nodes</span>
                          </div>
                        </div>
                        {isSelected && <ChevronRight size={14} className="text-primary-500 mt-1 shrink-0" />}
                      </div>
                    </button>
                  );
                })}
              </div>
            )}
          </div>

          {/* Run button */}
          {!journeyId ? (
            <button
              onClick={startTest}
              disabled={!selected || !phone.trim() || running}
              className="w-full py-3 rounded-xl font-semibold text-sm flex items-center justify-center gap-2 transition-all disabled:opacity-40 disabled:cursor-not-allowed bg-gradient-to-r from-violet-600 to-indigo-600 text-white hover:from-violet-700 hover:to-indigo-700 shadow-lg shadow-violet-500/20 active:scale-[0.98]"
            >
              {running ? <Loader2 size={16} className="animate-spin" /> : <Zap size={16} />}
              {running ? "Starting…" : "Run Test"}
            </button>
          ) : (
            <button
              onClick={stopTest}
              className="w-full py-3 rounded-xl font-semibold text-sm flex items-center justify-center gap-2 bg-red-50 text-red-600 border border-red-200 hover:bg-red-100 transition-all"
            >
              <StopCircle size={16} /> Stop Test
            </button>
          )}

          {startError && (
            <div className="flex items-start gap-2 bg-red-50 border border-red-200 rounded-xl p-3">
              <AlertCircle size={14} className="text-red-500 mt-0.5 shrink-0" />
              <p className="text-xs text-red-600">{startError}</p>
            </div>
          )}
        </div>

        {/* ══ RIGHT PANEL — Live test console ══════════════════════ */}
        <div className="flex-1 flex flex-col gap-4 min-h-0">

          {!journeyId && messages.length === 0 ? (
            /* Empty state */
            <div className="flex-1 card flex flex-col items-center justify-center gap-4 text-center py-16">
              <div className="w-16 h-16 rounded-2xl bg-violet-50 flex items-center justify-center">
                <FlaskConical size={28} className="text-violet-400" />
              </div>
              <div>
                <p className="font-semibold text-dark">Ready to test</p>
                <p className="text-sm text-muted mt-1 max-w-xs">
                  Select a tree on the left, enter your WhatsApp number, and hit <strong>Run Test</strong>.
                  All wait delays are skipped — the full sequence fires in seconds.
                </p>
              </div>
              <div className="flex items-center gap-6 text-xs text-muted mt-2">
                <span className="flex items-center gap-1.5"><Zap size={12} className="text-amber-500" /> Waits skipped</span>
                <span className="flex items-center gap-1.5"><MessageSquare size={12} className="text-blue-500" /> Real messages</span>
                <span className="flex items-center gap-1.5"><RefreshCw size={12} className="text-emerald-500" /> Live updates</span>
              </div>
            </div>
          ) : (
            <>
              {/* Status bar */}
              <div className="card p-3 flex items-center gap-3">
                <div className={`w-2.5 h-2.5 rounded-full shrink-0 ${
                  isComplete ? "bg-gray-400" :
                  journey?.status === "active" ? "bg-emerald-400 animate-pulse" : "bg-amber-400"
                }`} />
                <div className="flex-1 min-w-0">
                  <p className="text-sm font-semibold text-dark truncate">
                    {journey?.treeName ?? selected?.name ?? "Starting…"}
                  </p>
                  <p className="text-xs text-muted">
                    {isComplete
                      ? `Journey ${journey?.status} • ${outgoing.length} message${outgoing.length !== 1 ? "s" : ""} sent`
                      : journey?.currentNode
                      ? `${NODE_ICON[journey.currentNode.type] ?? "•"} Waiting at: ${journey.currentNode.name}`
                      : "Initialising…"
                    }
                  </p>
                </div>
                <div className="flex items-center gap-2 shrink-0">
                  {isActive && (
                    <span className="text-[10px] font-bold text-emerald-600 bg-emerald-50 border border-emerald-200 px-2 py-0.5 rounded-full animate-pulse">
                      LIVE
                    </span>
                  )}
                  {isComplete && (
                    <span className="text-[10px] font-bold text-gray-500 bg-gray-100 border border-gray-200 px-2 py-0.5 rounded-full">
                      {journey?.status?.toUpperCase()}
                    </span>
                  )}
                </div>
              </div>

              <div className="flex gap-4 flex-1 min-h-0">

                {/* ── Chat feed ── */}
                <div className="flex-1 flex flex-col min-h-0 card overflow-hidden">
                  <div className="px-4 py-3 border-b border-gray-100 flex items-center gap-2">
                    <MessageSquare size={14} className="text-muted" />
                    <span className="text-xs font-semibold text-muted uppercase tracking-wide">
                      Message Log ({outgoing.length} sent)
                    </span>
                  </div>

                  {/* Messages */}
                  <div ref={chatRef} className="flex-1 overflow-y-auto p-4 space-y-3"
                    style={{ background: "#f0f2f5" }}>
                    {messages.length === 0 && (
                      <div className="flex items-center justify-center h-full">
                        <div className="text-center">
                          <Loader2 size={20} className="animate-spin text-violet-400 mx-auto mb-2" />
                          <p className="text-xs text-muted">Sending first message…</p>
                        </div>
                      </div>
                    )}
                    {messages.map(msg => (
                      <div key={msg.id}
                        className={`flex ${msg.direction === "incoming" ? "justify-end" : "justify-start"}`}>
                        <div className={`max-w-[80%] px-3.5 py-2.5 rounded-2xl text-[13px] leading-relaxed shadow-sm whitespace-pre-wrap ${
                          msg.direction === "incoming"
                            ? "bg-[#DCF8C6] text-gray-800 rounded-tr-sm"
                            : "bg-white text-gray-800 rounded-tl-sm"
                        }`}>
                          {msg.text}
                          <div className={`flex items-center gap-1 mt-1 ${
                            msg.direction === "incoming" ? "justify-end" : "justify-start"
                          }`}>
                            <span className="text-[10px] text-gray-400">{formatTime(msg.sentAt)}</span>
                            {msg.direction === "incoming" && (
                              <span className="text-[10px] text-blue-400">✓✓</span>
                            )}
                          </div>
                        </div>
                      </div>
                    ))}
                  </div>

                  {/* Reply input */}
                  {isActive && journey?.currentNode?.type === "buttons" && (
                    <div className="px-3 py-2.5 border-t border-gray-100 bg-gray-50">
                      <p className="text-[10px] text-muted mb-1.5 font-medium">
                        💡 Tip: Reply with a number (1, 2, 3) or the option text
                      </p>
                      <div className="flex gap-2">
                        <input
                          className="flex-1 px-3 py-2 rounded-xl border border-gray-200 bg-white text-sm focus:outline-none focus:border-primary-400 transition-all"
                          placeholder="Type a reply… e.g. 1 or Yes"
                          value={replyText}
                          onChange={e => setReplyText(e.target.value)}
                          onKeyDown={e => { if (e.key === "Enter") sendReply(); }}
                          disabled={replySending}
                        />
                        <button onClick={sendReply} disabled={!replyText.trim() || replySending}
                          className="px-3 py-2 rounded-xl bg-[#25D366] text-white hover:bg-[#128C7E] transition-all disabled:opacity-40 active:scale-95">
                          {replySending ? <Loader2 size={16} className="animate-spin" /> : <Send size={16} />}
                        </button>
                      </div>
                    </div>
                  )}
                </div>

                {/* ── Execution timeline ── */}
                <div className="w-[200px] shrink-0 card flex flex-col overflow-hidden">
                  <div className="px-3 py-3 border-b border-gray-100">
                    <p className="text-[10px] font-semibold text-muted uppercase tracking-wide">
                      Node Execution
                    </p>
                  </div>
                  <div className="flex-1 overflow-y-auto p-3 space-y-1.5">
                    {(journey?.executions ?? []).map((ex, i) => (
                      <div key={i} className="flex items-start gap-2">
                        <div className={`w-1.5 h-1.5 rounded-full mt-1.5 shrink-0 ${
                          ex.status === "executed" ? "bg-emerald-400" :
                          ex.status === "failed"   ? "bg-red-400" : "bg-gray-300"
                        }`} />
                        <div className="min-w-0">
                          <p className="text-[11px] font-medium text-dark leading-tight truncate">
                            {NODE_ICON[ex.type ?? ""] ?? "•"} {ex.node ?? "Unknown"}
                          </p>
                          <p className="text-[9px] text-muted">
                            {ex.status === "failed" ? "⚠ failed" :
                             ex.executedAt ? formatTime(ex.executedAt) : "…"}
                          </p>
                        </div>
                      </div>
                    ))}
                    {(journey?.executions ?? []).length === 0 && (
                      <p className="text-[10px] text-muted text-center py-4">No executions yet</p>
                    )}
                  </div>

                  {/* Summary */}
                  {messages.length > 0 && (
                    <div className="p-3 border-t border-gray-100 space-y-1.5">
                      <div className="flex items-center justify-between">
                        <span className="text-[10px] text-muted">Sent</span>
                        <span className="text-[11px] font-bold text-emerald-600">{outgoing.length}</span>
                      </div>
                      <div className="flex items-center justify-between">
                        <span className="text-[10px] text-muted">Nodes run</span>
                        <span className="text-[11px] font-bold text-dark">
                          {journey?.executions?.filter(e => e.status === "executed").length ?? 0}
                        </span>
                      </div>
                      {(journey?.executions?.filter(e => e.status === "failed").length ?? 0) > 0 && (
                        <div className="flex items-center justify-between">
                          <span className="text-[10px] text-red-500">Failed</span>
                          <span className="text-[11px] font-bold text-red-600">
                            {journey?.executions?.filter(e => e.status === "failed").length}
                          </span>
                        </div>
                      )}
                    </div>
                  )}
                </div>
              </div>
            </>
          )}
        </div>
      </div>
    </div>
  );
}
