import { NextRequest, NextResponse } from "next/server";
import { auth } from "@clerk/nextjs/server";
import { getDatabase } from "@/lib/database";
import { randomBytes } from "crypto";
import log from "@/lib/logger";
import {
  fitnessGoalSchema,
  paginationSchema,
  statusFilterSchema,
} from "@/lib/validation/schemas";
import {
  validateRequestBody,
  validateQueryParams,
  validationErrorResponse,
} from "@/lib/validation/helpers";
import {
  successResponse,
  createdResponse,
  unauthorizedResponse,
  internalErrorResponse,
  addCorsHeaders,
} from "@/lib/api/responses";

// Helper to get user ID from auth (works with both web sessions and mobile tokens)
async function getAuthenticatedUserId(
  req: NextRequest,
): Promise<string | null> {
  // The auth() function from Clerk should handle Bearer tokens automatically
  // when called within an API route that's processed by clerkMiddleware
  const { userId } = await auth();
  return userId;
}

// OPTIONS - Handle preflight requests
export async function OPTIONS() {
  return NextResponse.json({}, { headers: addCorsHeaders() });
}

// GET - List user's fitness goals
export async function GET(req: NextRequest) {
  try {
    const userId = await getAuthenticatedUserId(req);

    if (!userId) {
      log.error("Fitness goals GET - authentication failed", undefined, {
        headers: Object.fromEntries(req.headers.entries()),
      });
      return unauthorizedResponse(undefined, addCorsHeaders());
    }

    log.debug("Fitness goals GET - authenticated user", { userId });

    const { searchParams } = new URL(req.url);
    const targetUserId = searchParams.get("userId") || userId;
    const status = searchParams.get("status"); // active, completed, all

    const db = await getDatabase();

    // Fetch goals with optional status filter
    const goals = await db.getFitnessGoalsByUserId(
      targetUserId,
      status && status !== "all" ? status : undefined,
    );

    log.debug("Fitness goals retrieved", {
      count: goals.length,
      userId: targetUserId,
    });
    return successResponse(goals, { headers: addCorsHeaders() });
  } catch (error) {
    log.error("Failed to get fitness goals", error);
    return internalErrorResponse(undefined, addCorsHeaders());
  }
}

// POST - Create new fitness goal
export async function POST(req: NextRequest) {
  try {
    const userId = await getAuthenticatedUserId(req);

    if (!userId) {
      log.error("Fitness goals POST - authentication failed");
      return unauthorizedResponse(undefined, addCorsHeaders());
    }

    // Validate request body
    const validation = await validateRequestBody(req, fitnessGoalSchema);

    if (!validation.success) {
      log.warn("Fitness goal creation validation failed", {
        errors: validation.errors,
      });
      return validationErrorResponse(validation.errors);
    }

    const {
      goalType,
      title,
      description,
      targetValue,
      currentValue,
      unit,
      targetDate,
      priority,
      status,
      notes,
    } = validation.data;

    const db = await getDatabase();

    // Create the goal
    const goal = await db.createFitnessGoal({
      id: randomBytes(16).toString("hex"),
      userId,
      fitnessProfileId: undefined,
      goalType,
      title,
      description,
      targetValue,
      currentValue: currentValue || 0,
      unit,
      startDate: new Date(),
      targetDate: targetDate ? new Date(targetDate) : undefined,
      status: status || "active",
      progress: 0,
      priority: priority || "medium",
      notes,
    });

    log.info("Fitness goal created", { goalId: goal.id, userId });
    return createdResponse(goal, { headers: addCorsHeaders() });
  } catch (error) {
    log.error("Failed to create fitness goal", error);
    return internalErrorResponse(undefined, addCorsHeaders());
  }
}
