"use client";

/**
 * Dual-line chart: Actual GSC clicks vs a 7-day trailing moving
 * average ("Normalized"). Lets users eyeball days where Actual
 * diverges from trend — those are the points the correlation
 * cards below are trying to explain (external events, weather,
 * regulatory shifts, etc.).
 *
 * Data flow:
 *   1. Fetch /api/industry-intel/daily-gsc on brandId change
 *   2. Render recharts LineChart with two <Line>s on the same
 *      axes — solid emerald for Actual, dashed slate for the
 *      moving average
 *   3. When the fetch returns zero points, render a "Connect
 *      GSC" empty-state instead of the chart frame
 */

import { useEffect, useState } from "react";
import { ArrowUp, ArrowDown, Minus } from "lucide-react";
import {
  ResponsiveContainer, LineChart, Line, XAxis, YAxis, Tooltip,
  CartesianGrid, Legend,
} from "recharts";

interface Correlation { event?: string; metric?: string; correlation?: string; explanation?: string; normalizedPerformance?: string; recovery?: string }

interface DailyPoint {
  date: string;
  clicks: number;
  impressions: number;
  position: number | null;
  ctr: number | null;
}

interface ChartRow {
  date: string;
  /** Display-friendly date for the X-axis ("Mar 18"). */
  label: string;
  clicks: number;
  /** 7-day trailing moving average of clicks. null for the first 6
   *  points — no average possible without a full window. */
  normalized: number | null;
}

interface Props { correlations: Correlation[]; brandId: string }

/** Compute a 7-day trailing moving average. Null for the first 6
 *  points so recharts leaves that portion of the line unrendered
 *  instead of painting a jagged ramp-up. */
function withMovingAverage(points: DailyPoint[]): ChartRow[] {
  const WINDOW = 7;
  return points.map((p, i) => {
    const start = Math.max(0, i - WINDOW + 1);
    const window = points.slice(start, i + 1);
    const normalized = window.length >= WINDOW
      ? Math.round(window.reduce((s, w) => s + w.clicks, 0) / window.length)
      : null;
    return {
      date: p.date,
      label: formatShortDate(p.date),
      clicks: p.clicks,
      normalized,
    };
  });
}

/** Turn an ISO date ("2026-03-18") into a short display label
 *  ("Mar 18"). UTC-fixed so tests + rendered output stay
 *  deterministic across environments + timezones. */
function formatShortDate(iso: string): string {
  try {
    const d = new Date(iso + "T00:00:00Z");
    return d.toLocaleDateString("en-US", { month: "short", day: "numeric", timeZone: "UTC" });
  } catch {
    return iso;
  }
}

export default function CorrelationChart({ correlations, brandId }: Props) {
  const [rows, setRows] = useState<ChartRow[] | null>(null);
  const [loading, setLoading] = useState(true);

  useEffect(() => {
    if (!brandId) { setRows([]); setLoading(false); return; }
    let cancelled = false;
    setLoading(true);
    fetch(`/api/industry-intel/daily-gsc?brandId=${brandId}&days=90`)
      .then((r) => r.ok ? r.json() : null)
      .then((data) => {
        if (cancelled) return;
        const pts = Array.isArray(data?.points) ? data.points as DailyPoint[] : [];
        setRows(withMovingAverage(pts));
      })
      .catch(() => { if (!cancelled) setRows([]); })
      .finally(() => { if (!cancelled) setLoading(false); });
    return () => { cancelled = true; };
  }, [brandId]);

  // Hide the card entirely when there are zero correlations AND
  // zero chart data — neither half has anything to show, rendering
  // an empty dark card is visual noise.
  const hasCorrelations = correlations.length > 0;
  const hasChartData = (rows?.length ?? 0) > 0;
  if (!hasCorrelations && !loading && !hasChartData) return null;

  return (
    <div>
      <h2 className="text-xs font-bold uppercase tracking-widest text-slate-400 mb-3">Performance Correlations</h2>
      <div className="rounded-2xl overflow-hidden" style={{ background: "#0B1120" }}>
        {/* Chart frame */}
        <div className="px-6 py-5 border-b border-white/10">
          <p className="text-xs text-slate-400 mb-1">Actual vs Normalized Performance</p>
          <div className="flex items-center gap-4 text-[10px] mb-3">
            <span className="flex items-center gap-1 text-slate-300">
              <span className="w-6 h-0.5 bg-emerald-400 rounded" /> Actual clicks
            </span>
            <span className="flex items-center gap-1 text-slate-300">
              <span className="w-6 h-0.5 border-t-2 border-dashed border-slate-400" /> 7-day moving avg
            </span>
          </div>

          {loading ? (
            <div className="h-32 flex items-center justify-center">
              <p className="text-xs text-slate-500">Loading GSC time series…</p>
            </div>
          ) : !hasChartData ? (
            // Connect-GSC empty state. Keeps the dark frame + legend
            // visible so the section's shape matches the populated
            // case; copy makes the missing-data reason explicit.
            <div className="h-32 flex flex-col items-center justify-center text-center">
              <p className="text-xs text-slate-400">No GSC daily data available</p>
              <p className="text-[11px] text-slate-500 mt-1">
                Connect Google Search Console and let the first daily sync land (usually &lt; 24h) to see performance correlations.
              </p>
            </div>
          ) : (
            <div className="h-48">
              <ResponsiveContainer width="100%" height="100%">
                <LineChart data={rows ?? []} margin={{ top: 8, right: 12, left: 0, bottom: 0 }}>
                  <CartesianGrid strokeDasharray="3 3" stroke="#1e293b" vertical={false} />
                  <XAxis
                    dataKey="label"
                    stroke="#64748b"
                    tick={{ fontSize: 10, fill: "#94a3b8" }}
                    tickLine={false}
                    axisLine={{ stroke: "#1e293b" }}
                    minTickGap={24}
                  />
                  <YAxis
                    stroke="#64748b"
                    tick={{ fontSize: 10, fill: "#94a3b8" }}
                    tickLine={false}
                    axisLine={{ stroke: "#1e293b" }}
                    width={40}
                  />
                  <Tooltip
                    contentStyle={{ background: "#0b1120", border: "1px solid #1e293b", borderRadius: 8, fontSize: 11 }}
                    labelStyle={{ color: "#cbd5e1", fontWeight: 600 }}
                    itemStyle={{ color: "#e2e8f0" }}
                  />
                  <Legend
                    wrapperStyle={{ fontSize: 10, color: "#cbd5e1" }}
                    iconType="plainline"
                  />
                  <Line
                    type="monotone"
                    dataKey="clicks"
                    name="Actual clicks"
                    stroke="#34d399"
                    strokeWidth={2}
                    dot={false}
                    activeDot={{ r: 4 }}
                    isAnimationActive={false}
                  />
                  <Line
                    type="monotone"
                    dataKey="normalized"
                    name="7-day moving avg"
                    stroke="#94a3b8"
                    strokeWidth={1.5}
                    strokeDasharray="4 3"
                    dot={false}
                    activeDot={false}
                    isAnimationActive={false}
                    // connectNulls=false leaves the first 6 points
                    // unrendered — a partial moving average during
                    // the warm-up window would just lie about the
                    // trend direction.
                    connectNulls={false}
                  />
                </LineChart>
              </ResponsiveContainer>
            </div>
          )}
        </div>

        {/* Correlation cards — unchanged. These stay below the chart
            so users can read the AI's explanation of what drove each
            divergence right next to where they see the divergence on
            the line. */}
        {hasCorrelations && (
          <div className="p-5 space-y-3">
            {correlations.map((c, i) => {
              const isNeg = c.correlation === "negative";
              const isPos = c.correlation === "positive";
              return (
                <div key={i} className="bg-white/5 rounded-xl px-4 py-3">
                  <div className="flex items-center gap-2 mb-1.5">
                    {isNeg ? <ArrowDown className="w-4 h-4 text-red-400" /> : isPos ? <ArrowUp className="w-4 h-4 text-emerald-400" /> : <Minus className="w-4 h-4 text-slate-400" />}
                    <span className="text-sm font-semibold text-white">{c.event}</span>
                    {c.metric && <span className="text-[9px] font-bold uppercase tracking-wider text-slate-400 bg-white/10 rounded-full px-2 py-0.5">{c.metric}</span>}
                  </div>
                  {c.explanation && <p className="text-xs text-slate-300 leading-relaxed mb-1">{c.explanation}</p>}
                  <div className="flex items-center gap-4 text-[10px] text-slate-500">
                    {c.normalizedPerformance && <span>Normalized: {c.normalizedPerformance}</span>}
                    {c.recovery && <span>Recovery: {c.recovery}</span>}
                  </div>
                </div>
              );
            })}
          </div>
        )}
      </div>
    </div>
  );
}
