import { CloseBotClient, err } from "../client.js";
import type { ToolDefinition, ToolResult, AgencyDashboardSummaryResponse } from "../types.js";

export const tools: ToolDefinition[] = [
  {
    name: "analytics_dashboard_app",
    description: "Rich analytics dashboard showing agency summary stats, booking trends, and response/revenue metrics with time range support. Returns HTML visualization.",
    inputSchema: {
      type: "object",
      properties: {
        sourceId: { type: "string", description: "Optional source ID to filter metrics" },
        start: { type: "string", description: "Start date for booking graph (ISO 8601). Defaults to 30 days ago." },
        end: { type: "string", description: "End date for booking graph (ISO 8601). Defaults to now." },
        resolution: { type: "string", description: "Graph resolution: hourly, daily, monthly. Default: daily" },
      },
    },
  },
];

function escapeHtml(s: string): string {
  return s.replace(/&/g, "&amp;").replace(/</g, "&lt;").replace(/>/g, "&gt;");
}

function pctChange(current: number, last: number): string {
  if (last === 0) return current > 0 ? "+∞" : "—";
  const pct = ((current - last) / last) * 100;
  const sign = pct >= 0 ? "+" : "";
  const color = pct >= 0 ? "#4ecdc4" : "#ff6b6b";
  return `<span style="color:${color};font-size:12px;">${sign}${pct.toFixed(1)}%</span>`;
}

function renderDashboard(
  summary: AgencyDashboardSummaryResponse,
  bookingData: unknown,
  metricData: unknown
): string {
  const cards = [
    {
      label: "Responses This Month",
      value: summary.currentMonthMessageCount ?? 0,
      change: pctChange(summary.currentMonthMessageCount ?? 0, summary.lastMonthMessageCount ?? 0),
      icon: "💬",
    },
    {
      label: "Bookings This Month",
      value: summary.currentMonthSuccessfulBookings ?? 0,
      change: pctChange(summary.currentMonthSuccessfulBookings ?? 0, summary.lastMonthSuccessfulBookings ?? 0),
      icon: "📅",
    },
    {
      label: "Active Sources",
      value: summary.currentMonthActiveSources ?? 0,
      change: pctChange(summary.currentMonthActiveSources ?? 0, summary.lastMonthActiveSources ?? 0),
      icon: "📡",
    },
    {
      label: "Contacts This Month",
      value: summary.currentMonthContacts ?? 0,
      change: pctChange(summary.currentMonthContacts ?? 0, summary.lastMonthContacts ?? 0),
      icon: "👤",
    },
    {
      label: "Current Users",
      value: summary.currentUsers ?? 0,
      change: "",
      icon: "👥",
    },
    {
      label: "Total Storage",
      value: `${((summary.totalStorage ?? 0) / (1024 * 1024)).toFixed(1)} MB`,
      change: "",
      icon: "💾",
    },
  ];

  const cardHtml = cards
    .map(
      (c) => `
    <div style="background:#1a1a2e;border-radius:12px;padding:16px;text-align:center;">
      <div style="font-size:28px;margin-bottom:4px;">${c.icon}</div>
      <div style="font-size:24px;font-weight:700;color:#fff;">${typeof c.value === "number" ? c.value.toLocaleString() : c.value}</div>
      <div style="font-size:12px;color:#888;margin-top:4px;">${escapeHtml(c.label)}</div>
      ${c.change ? `<div style="margin-top:4px;">${c.change}</div>` : ""}
    </div>`
    )
    .join("");

  // Render booking data as a simple text-based bar chart if it's an array
  let bookingChartHtml = "";
  if (Array.isArray(bookingData) && bookingData.length > 0) {
    const maxVal = Math.max(...bookingData.map((d: Record<string, unknown>) => (d.count as number) || 0), 1);
    const bars = bookingData
      .slice(-14) // last 14 data points
      .map((d: Record<string, unknown>) => {
        const val = (d.count as number) || 0;
        const pct = (val / maxVal) * 100;
        const label = d.label || d.date || d.key || "";
        return `
          <div style="display:flex;align-items:center;gap:8px;margin:2px 0;">
            <div style="width:80px;font-size:11px;color:#888;text-align:right;">${escapeHtml(String(label))}</div>
            <div style="flex:1;background:#111;border-radius:4px;height:20px;">
              <div style="width:${pct}%;background:linear-gradient(90deg,#4ecdc4,#44a8a0);height:100%;border-radius:4px;min-width:2px;"></div>
            </div>
            <div style="width:40px;font-size:11px;color:#aaa;">${val}</div>
          </div>`;
      })
      .join("");
    bookingChartHtml = `
      <div style="margin-top:20px;">
        <h3 style="color:#ccc;margin:0 0 12px;">📊 Booking Trend</h3>
        ${bars}
      </div>`;
  }

  // Metric data summary
  let metricHtml = "";
  if (metricData && typeof metricData === "object") {
    metricHtml = `
      <div style="margin-top:20px;">
        <h3 style="color:#ccc;margin:0 0 8px;">📈 Response Metric Data</h3>
        <pre style="background:#111;padding:12px;border-radius:8px;font-size:11px;color:#aaa;overflow-x:auto;max-height:200px;">${escapeHtml(JSON.stringify(metricData, null, 2).slice(0, 2000))}</pre>
      </div>`;
  }

  return `
    <div style="font-family:-apple-system,BlinkMacSystemFont,sans-serif;background:#0d0d1a;color:#e0e0e0;padding:20px;border-radius:16px;">
      <h2 style="margin:0 0 16px;color:#fff;">📊 Analytics Dashboard</h2>
      <div style="display:grid;grid-template-columns:repeat(3,1fr);gap:12px;">
        ${cardHtml}
      </div>
      ${bookingChartHtml}
      ${metricHtml}
    </div>`;
}

export async function handler(
  client: CloseBotClient,
  name: string,
  args: Record<string, unknown>
): Promise<ToolResult> {
  try {
    const now = new Date();
    const thirtyDaysAgo = new Date(now.getTime() - 30 * 24 * 60 * 60 * 1000);
    const start = (args.start as string) || thirtyDaysAgo.toISOString();
    const end = (args.end as string) || now.toISOString();
    const resolution = (args.resolution as string) || "daily";

    const [summary, bookingData, metricData] = await Promise.all([
      client.get<AgencyDashboardSummaryResponse>("/botMetric/agencySummary", {
        sourceId: args.sourceId,
      }),
      client.get("/botMetric/bookingGraph", {
        start,
        end,
        resolution,
        sourceId: args.sourceId,
      }),
      client.get("/botMetric/agencyMetric", {
        metric: "responses",
        start,
        end,
        resolution,
        sourceId: args.sourceId,
      }),
    ]);

    const html = renderDashboard(summary, bookingData, metricData);
    return {
      content: [
        {
          type: "text",
          text: `Analytics: ${summary.currentMonthMessageCount} responses, ${summary.currentMonthSuccessfulBookings} bookings this month`,
        },
      ],
      structuredContent: { type: "html", html },
    };
  } catch (error) {
    return err(error);
  }
}
