/**
 * Suggested FAQs Dashboard API
 *
 * GET /api/dashboard/suggested-faqs?organizationId=...
 *
 * Returns:
 * - coverageScore: 0-100, percent of recent questions answered from KB
 * - answeredCount / totalQuestions: raw counts
 * - unansweredThisWeek: count in the last 7 days
 * - unanswered: list of open unanswered questions (sorted by frequency)
 * - suggestions: list of pending FAQ suggestions
 */

import { NextRequest, NextResponse } from "next/server";
import { auth } from "@/lib/auth";
import { getAuthenticatedUser } from "@/lib/utils/auth-helpers.util";
import { convexQuery } from "@/lib/convex-client";
import { rateLimiters, applyRateLimit } from "@/lib/rate-limiter";
import { logger } from "@/lib/logger";
import prisma from "@/lib/db";

const scopedLogger = logger.scope("SuggestedFAQsAPI");

const ONE_WEEK_MS = 7 * 24 * 60 * 60 * 1000;

interface UnansweredDoc {
  _id: string;
  question: string;
  language: string;
  frequency: number;
  lastAskedAt: number;
}

interface SuggestionDoc {
  _id: string;
  question: string;
  suggestedAnswer: string;
  language: string;
  frequency: number;
}

export async function GET(request: NextRequest) {
  try {
    const rateLimitResponse = await applyRateLimit(
      request,
      rateLimiters.authGeneral,
    );
    if (rateLimitResponse) return rateLimitResponse;

    const user = await getAuthenticatedUser(request, auth);
    if (!user) {
      return NextResponse.json(
        { success: false, error: "Unauthorized" },
        { status: 401 },
      );
    }

    const url = new URL(request.url);
    const organizationId = url.searchParams.get("organizationId");
    if (!organizationId) {
      return NextResponse.json(
        { success: false, error: "organizationId is required" },
        { status: 400 },
      );
    }

    // Verify the authenticated user owns this org
    const org = await prisma.organizations.findFirst({
      where: { id: organizationId },
      select: { id: true, ownerId: true },
    });
    if (!org || org.ownerId !== user.userId) {
      return NextResponse.json(
        { success: false, error: "Forbidden" },
        { status: 403 },
      );
    }

    // Fetch open unanswered questions and pending suggestions in parallel
    const [unansweredRaw, suggestionsRaw] = await Promise.all([
      convexQuery<UnansweredDoc[]>(
        "whatsapp/queries:getUnansweredQuestions",
        { organizationId, status: "open", limit: 50 },
      ).catch(() => [] as UnansweredDoc[]),
      convexQuery<SuggestionDoc[]>(
        "whatsapp/queries:getSuggestedFaqs",
        { organizationId, status: "pending", limit: 20 },
      ).catch(() => [] as SuggestionDoc[]),
    ]);

    const unansweredList = Array.isArray(unansweredRaw) ? unansweredRaw : [];
    const suggestionsList = Array.isArray(suggestionsRaw) ? suggestionsRaw : [];

    // Coverage score: total tracked questions vs answered (out of company KB)
    // Use approximate metric — answeredCount = total messages with KB used
    // For now, derive from unanswered count + a baseline
    const totalUnanswered = unansweredList.reduce(
      (sum, q) => sum + (q.frequency || 1),
      0,
    );

    // Best-effort answered count from KB hits — query message metadata
    // (Falls back to a baseline if unavailable)
    let answeredCount = 0;
    try {
      // Pull recent conversations and count messages with kbUsed=true
      const conversations = await convexQuery<Array<{ _id: string }>>(
        "whatsapp/queries:getOrgConversations",
        { organizationId, limit: 50 },
      ).catch(() => [] as Array<{ _id: string }>);

      if (Array.isArray(conversations)) {
        for (const conv of conversations.slice(0, 20)) {
          const msgs = await convexQuery<Array<{ kbUsed?: boolean; role: string }>>(
            "whatsapp/queries:getOrgMessages",
            { conversationId: conv._id, limit: 100 },
          ).catch(() => []);
          if (Array.isArray(msgs)) {
            answeredCount += msgs.filter(
              (m) => m.role === "assistant" && m.kbUsed === true,
            ).length;
          }
        }
      }
    } catch (error) {
      scopedLogger.warn("Failed to compute answered count", { error });
    }

    const totalQuestions = answeredCount + totalUnanswered;
    const coverageScore =
      totalQuestions > 0
        ? Math.round((answeredCount / totalQuestions) * 100)
        : 100;

    // Unanswered this week
    const weekAgo = Date.now() - ONE_WEEK_MS;
    const unansweredThisWeek = unansweredList.reduce((sum, q) => {
      if ((q.lastAskedAt || 0) >= weekAgo) return sum + (q.frequency || 1);
      return sum;
    }, 0);

    // Map to component shape
    const unanswered = unansweredList
      .sort((a, b) => (b.frequency || 0) - (a.frequency || 0))
      .map((q) => ({
        id: q._id,
        question: q.question,
        language: (q.language === "ar" ? "ar" : "en") as "en" | "ar",
        count: q.frequency || 1,
        lastAskedAt: q.lastAskedAt,
      }));

    const suggestions = suggestionsList.map((s) => ({
      id: s._id,
      question: s.question,
      answer: s.suggestedAnswer,
      language: (s.language === "ar" ? "ar" : "en") as "en" | "ar",
      sourceCount: s.frequency || 1,
    }));

    return NextResponse.json({
      coverageScore,
      answeredCount,
      totalQuestions,
      unansweredThisWeek,
      unanswered,
      suggestions,
    });
  } catch (error) {
    scopedLogger.error("Failed to load suggested FAQs", error);
    return NextResponse.json(
      { success: false, error: "Internal server error" },
      { status: 500 },
    );
  }
}
