import { NextRequest, NextResponse } from "next/server";
import { z } from "zod";
import { db, collections, eq, desc, sql } from "@epicure/db";
import { requireSessionOrApiKey } from "@/lib/api-auth";

const Schema = z.object({
  name: z.string().min(1).max(100),
  description: z.string().max(500).optional(),
  visibility: z.enum(["private", "unlisted", "public", "followers"]).default("private"),
});

export async function GET(req: NextRequest) {
  const { session, response } = await requireSessionOrApiKey(req);
  if (response) return response;

  const { searchParams } = req.nextUrl;

  const limitRaw = searchParams.get("limit");
  const limit = Math.min(
    limitRaw !== null && !Number.isNaN(Number(limitRaw))
      ? Math.max(1, Number(limitRaw))
      : 20,
    50
  );

  const offsetRaw = searchParams.get("offset");
  const offset =
    offsetRaw !== null && !Number.isNaN(Number(offsetRaw))
      ? Math.max(0, Number(offsetRaw))
      : 0;

  const where = eq(collections.userId, session!.user.id);

  const [rows, countResult] = await Promise.all([
    db.query.collections.findMany({
      where,
      orderBy: desc(collections.updatedAt),
      with: { recipes: { limit: 4, with: { recipe: { with: { photos: true } } } } },
      limit,
      offset,
    }),
    db.select({ total: sql<number>`count(*)::int` }).from(collections).where(where),
  ]);

  const total = countResult[0]?.total ?? 0;

  return NextResponse.json({ data: rows, total, limit, offset });
}

export async function POST(req: NextRequest) {
  const { session, response } = await requireSessionOrApiKey(req);
  if (response) return response;

  const body = await req.json() as unknown;
  const parsed = Schema.safeParse(body);
  if (!parsed.success) return NextResponse.json({ error: "Validation error" }, { status: 400 });

  const id = crypto.randomUUID();
  await db.insert(collections).values({
    id,
    userId: session!.user.id,
    name: parsed.data.name,
    description: parsed.data.description,
    visibility: parsed.data.visibility,
  });

  return NextResponse.json({ id }, { status: 201 });
}
