import { getCurrentUser } from "@/lib/auth";
import { getExercises, createExercise } from "@/lib/db/exercises";
import { prisma } from "@/lib/prisma";
import { NextRequest, NextResponse } from "next/server";
import { z } from "zod";

const CreateExerciseSchema = z.object({
  name: z.string().min(1, "Exercise name is required"),
  type: z.string().min(1),
  muscleGroups: z.array(z.string()).default([]),
  description: z.string().optional(),
  inputFields: z.array(z.string().min(1)).optional(),
  defaultWeightUnit: z.string().nullable().optional(),
});

/**
 * GET /api/exercises
 */
export async function GET(request: NextRequest) {
  try {
    const user = await getCurrentUser();
    if (!user) {
      return NextResponse.json({ error: "Unauthorized" }, { status: 401 });
    }

    const { searchParams } = new URL(request.url);
    const query = searchParams.get("q");

    let exercises;

    if (query) {
      exercises = await prisma.exercise.findMany({
        where: {
          userId: user.id,
          name: { contains: query },
        },
        orderBy: { name: "asc" },
      });
    } else {
      exercises = await getExercises(user.id);
    }

    return NextResponse.json(exercises);
  } catch (error) {
    console.error("GET /api/exercises error:", error);
    return NextResponse.json(
      { error: "Internal server error" },
      { status: 500 }
    );
  }
}

/**
 * POST /api/exercises
 */
export async function POST(request: NextRequest) {
  try {
    const user = await getCurrentUser();
    if (!user) {
      return NextResponse.json({ error: "Unauthorized" }, { status: 401 });
    }

    const body = await request.json();
    const validated = CreateExerciseSchema.parse(body);

    const existing = await prisma.exercise.findUnique({
      where: {
        userId_name: {
          userId: user.id,
          name: validated.name,
        },
      },
    });

    if (existing) {
      return NextResponse.json(
        { error: "Exercise already exists" },
        { status: 400 }
      );
    }

    // Determine default inputFields based on type
    let inputFields = validated.inputFields;
    if (!inputFields) {
      if (validated.type === "cardio") {
        inputFields = ["sets", "duration", "calories"];
      } else {
        inputFields = ["sets", "reps", "weight"];
      }
    }

    // Kettlebell defaults to kg
    let defaultWeightUnit = validated.defaultWeightUnit;
    if (defaultWeightUnit === undefined && validated.type === "kettlebell") {
      defaultWeightUnit = "kg";
    }

    const exercise = await createExercise({
      userId: user.id,
      name: validated.name,
      type: validated.type,
      description: validated.description,
      muscleGroups: JSON.stringify(validated.muscleGroups),
      inputFields: JSON.stringify(inputFields),
      defaultWeightUnit: defaultWeightUnit || null,
      isCustom: true,
    });

    return NextResponse.json(exercise, { status: 201 });
  } catch (error) {
    if (error instanceof z.ZodError) {
      return NextResponse.json(
        { error: "Validation error", details: error.errors },
        { status: 400 }
      );
    }

    console.error("POST /api/exercises error:", error);
    return NextResponse.json(
      { error: "Internal server error" },
      { status: 500 }
    );
  }
}
