/**
 * Sector Config Dashboard API
 *
 * Lets organization owners pick their industry from the dashboard. On
 * save, the route:
 *   1. Updates `industry` + `sector` on the organization
 *   2. Hard-deletes any existing whatsapp_workflows for the org
 *   3. Re-seeds sector default workflows for the new sector
 *   4. Invalidates the WhatsAppRouter cache so the next inbound message
 *      picks up the new industry
 *
 * GET   /api/dashboard/sector-config?organizationId=...
 *   Returns the org's current industry/sector + the number of active
 *   workflows so the UI can show "X workflows are now active".
 *
 * PATCH /api/dashboard/sector-config
 *   Body: { organizationId, industry }
 *   Industry must be one of the 24 known keys (validated against
 *   INDUSTRY_TO_SECTOR). Returns the new sector + workflow count.
 */

import { NextRequest, NextResponse } from "next/server";
import { z } from "zod";
import { auth } from "@/lib/auth";
import { getAuthenticatedUser } from "@/lib/utils/auth-helpers.util";
import { validateCSRFToken } from "@/lib/csrf";
import { rateLimiters, applyRateLimit } from "@/lib/rate-limiter";
import { logger } from "@/lib/logger";
import prisma from "@/lib/db";
import { convexQuery, convexMutation } from "@/lib/convex-client";
import {
  INDUSTRY_TO_SECTOR,
  getSectorForIndustry,
} from "@/lib/config/industry-sector-map";

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

const validIndustries = Object.keys(INDUSTRY_TO_SECTOR);

const patchSchema = z.object({
  organizationId: z.string().min(1),
  industry: z.string().refine((v) => validIndustries.includes(v), {
    message: `industry must be one of: ${validIndustries.join(", ")}`,
  }),
});

interface WorkflowRow {
  _id: string;
  name: string;
}

async function countActiveWorkflows(organizationId: string): Promise<number> {
  try {
    const rows = await convexQuery<WorkflowRow[]>(
      "whatsapp/workflows:listWorkflows",
      { organizationId, activeOnly: true },
    );
    return Array.isArray(rows) ? rows.length : 0;
  } catch (error) {
    scopedLogger.warn("Failed to count workflows", { organizationId, error });
    return 0;
  }
}

// ── GET ─────────────────────────────────────────────────────────────────
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 },
      );
    }

    const org = (await prisma.organizations.findFirst({
      where: { id: organizationId },
      select: {
        id: true,
        ownerId: true,
        industry: true,
        sector: true,
      },
    })) as Record<string, unknown> | null;

    if (!org || org.ownerId !== user.userId) {
      return NextResponse.json(
        { success: false, error: "Forbidden" },
        { status: 403 },
      );
    }

    const activeWorkflowCount = await countActiveWorkflows(organizationId);

    return NextResponse.json({
      success: true,
      industry: org.industry ?? null,
      sector: org.sector ?? null,
      activeWorkflowCount,
    });
  } catch (error) {
    scopedLogger.error("GET sector-config failed", error);
    return NextResponse.json(
      { success: false, error: "Internal server error" },
      { status: 500 },
    );
  }
}

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

    if (!validateCSRFToken(request)) {
      return NextResponse.json(
        { success: false, error: "Invalid CSRF token" },
        { status: 403 },
      );
    }

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

    const body = await request.json();
    const parsed = patchSchema.safeParse(body);
    if (!parsed.success) {
      return NextResponse.json(
        { success: false, error: parsed.error.errors[0].message },
        { status: 400 },
      );
    }

    const { organizationId, industry } = parsed.data;
    const sector = getSectorForIndustry(industry);

    // Verify org ownership
    const org = (await prisma.organizations.findFirst({
      where: { id: organizationId },
      select: { id: true, ownerId: true },
    })) as { id: string; ownerId: string } | null;

    if (!org || org.ownerId !== user.userId) {
      return NextResponse.json(
        { success: false, error: "Forbidden" },
        { status: 403 },
      );
    }

    // 1. Update industry + sector
    await convexMutation(
      "organizations/mutations:updateOrganizationNoAuth",
      { organizationId, industry, sector },
    );

    // 2. Wipe existing workflows so we don't accumulate stale ones
    //    when the owner changes their mind
    let deleted = 0;
    try {
      const wipeResult = await convexMutation<{ deleted: number }>(
        "whatsapp/workflows:hardDeleteAllForOrg",
        { organizationId },
      );
      deleted = wipeResult?.deleted ?? 0;
    } catch (error) {
      scopedLogger.warn("Workflow wipe failed (non-fatal)", {
        organizationId,
        error,
      });
    }

    // 3. Re-seed sector defaults
    let seeded = 0;
    let seedErrors = 0;
    try {
      const { seedDefaultWorkflows } = await import(
        "@/lib/services/workflow-seeder.service"
      );
      const seedResult = await seedDefaultWorkflows(organizationId, industry);
      seeded = seedResult.seeded;
      seedErrors = seedResult.errors;
    } catch (error) {
      scopedLogger.error("Workflow seeding failed", { organizationId, error });
    }

    // 4. Invalidate router cache so the next inbound WhatsApp message
    //    picks up the new industry/sector immediately
    try {
      const { whatsAppRouter } = await import(
        "@/lib/services/whatsapp-router.service"
      );
      await whatsAppRouter.invalidateOrgCache(organizationId);
    } catch (error) {
      scopedLogger.warn("Cache invalidation failed (non-fatal)", { error });
    }

    scopedLogger.info("Sector config saved", {
      organizationId,
      industry,
      sector,
      deleted,
      seeded,
      seedErrors,
    });

    return NextResponse.json({
      success: true,
      industry,
      sector,
      deletedWorkflows: deleted,
      seededWorkflows: seeded,
      seedErrors,
      activeWorkflowCount: seeded,
    });
  } catch (error) {
    scopedLogger.error("PATCH sector-config failed", error);
    return NextResponse.json(
      { success: false, error: "Internal server error" },
      { status: 500 },
    );
  }
}
