import { NextRequest, NextResponse } from "next/server";
import { prisma } from "@/lib/prisma";
import { requireAuth } from "@/lib/auth";

// GET /api/souq/orders — my orders (as buyer or seller)
export async function GET(request: NextRequest) {
  try {
    const auth = await requireAuth(request);
    if (!auth) {
      return NextResponse.json({ error: "Unauthorized" }, { status: 401 });
    }

    const { searchParams } = new URL(request.url);
    const role = searchParams.get("role"); // "buyer" | "seller" | null (both)
    const page = parseInt(searchParams.get("page") || "1", 10);
    const limit = parseInt(searchParams.get("limit") || "20", 10);
    const skip = (page - 1) * limit;

    const where: Record<string, unknown> = {};

    if (role === "buyer") {
      where.buyerId = auth.userId;
    } else if (role === "seller") {
      where.sellerId = auth.userId;
    } else {
      where.OR = [
        { buyerId: auth.userId },
        { sellerId: auth.userId },
      ];
    }

    const [orders, total] = await Promise.all([
      prisma.purchase.findMany({
        where,
        include: {
          listing: {
            select: { id: true, title: true, category: true, priceFlh: true },
          },
          buyer: {
            select: { id: true, name: true, email: true, avatar: true },
          },
          seller: {
            select: { id: true, name: true, email: true, avatar: true },
          },
        },
        orderBy: { createdAt: "desc" },
        skip,
        take: limit,
      }),
      prisma.purchase.count({ where }),
    ]);

    // Parse messages JSON for each order
    const parsed = orders.map((order) => {
      // eslint-disable-next-line @typescript-eslint/no-explicit-any
      const o = order as any;
      return {
        ...o,
        messages: o.messages ? JSON.parse(o.messages) : null,
        deliveryFiles: o.deliveryFiles ? JSON.parse(o.deliveryFiles) : null,
      };
    });

    return NextResponse.json({
      orders: parsed,
      pagination: {
        page,
        limit,
        total,
        totalPages: Math.ceil(total / limit),
      },
    });
  } catch (error) {
    console.error("GET /api/souq/orders error:", error);
    return NextResponse.json(
      { error: "Internal server error" },
      { status: 500 }
    );
  }
}

// POST /api/souq/orders — place a new order
export async function POST(request: NextRequest) {
  try {
    const auth = await requireAuth(request);
    if (!auth) {
      return NextResponse.json({ error: "Unauthorized" }, { status: 401 });
    }

    const user = await prisma.user.findUnique({ where: { id: auth.userId } });
    if (!user) {
      return NextResponse.json({ error: "User not found" }, { status: 404 });
    }

    const { listingId, packageName } = await request.json();

    if (!listingId) {
      return NextResponse.json(
        { error: "Missing required field: listingId" },
        { status: 400 }
      );
    }

    // Validate listing exists
    const listing = await prisma.listing.findUnique({
      where: { id: listingId },
    });

    if (!listing) {
      return NextResponse.json(
        { error: "Listing not found" },
        { status: 404 }
      );
    }

    if (listing.status !== "active") {
      return NextResponse.json(
        { error: "Listing is not available for purchase" },
        { status: 400 }
      );
    }

    // Prevent buying own listing
    if (listing.sellerId === user.id) {
      return NextResponse.json(
        { error: "You cannot purchase your own listing" },
        { status: 400 }
      );
    }

    // Determine amount: if packageName provided, look it up in packages JSON
    let amountFlh = listing.priceFlh;
    if (packageName) {
      if (!listing.packages) {
        return NextResponse.json(
          { error: "This listing has no packages" },
          { status: 400 }
        );
      }

      const packages = JSON.parse(listing.packages) as Array<{
        name: string;
        price?: number;
      }>;
      const selectedPackage = packages.find((p) => p.name === packageName);

      if (!selectedPackage) {
        return NextResponse.json(
          { error: `Package "${packageName}" not found` },
          { status: 400 }
        );
      }

      amountFlh = selectedPackage.price ?? listing.priceFlh;
    }

    // Check buyer balance
    if (user.flhBalance < amountFlh) {
      return NextResponse.json(
        { error: "Insufficient FLH balance" },
        { status: 400 }
      );
    }

    // Calculate fees
    const platformFee = Math.round(amountFlh * 0.015);
    const sellerPayout = amountFlh - platformFee;

    // Create purchase and deduct balance in a transaction
    const [purchase] = await prisma.$transaction([
      prisma.purchase.create({
        data: {
          listingId,
          buyerId: user.id,
          sellerId: listing.sellerId,
          packageName: packageName || null,
          amountFlh,
          platformFee,
          sellerPayout,
          status: "paid",
        },
        include: {
          listing: {
            select: { id: true, title: true, category: true, priceFlh: true },
          },
          buyer: {
            select: { id: true, name: true, email: true, avatar: true },
          },
          seller: {
            select: { id: true, name: true, email: true, avatar: true },
          },
        },
      }),
      prisma.user.update({
        where: { id: user.id },
        data: { flhBalance: { decrement: amountFlh } },
      }),
      // Increment sales count on the listing
      prisma.listing.update({
        where: { id: listingId },
        data: { salesCount: { increment: 1 } },
      }),
    ]);

    return NextResponse.json({ order: purchase }, { status: 201 });
  } catch (error) {
    console.error("POST /api/souq/orders error:", error);
    return NextResponse.json(
      { error: "Internal server error" },
      { status: 500 }
    );
  }
}
