import { NextRequest, NextResponse } from "next/server";
import { PrismaClient } from '@prisma/client';
import { getServerSession } from "next-auth";
import { authOptions } from "../../auth/authOptions";
import { DocumentSchema } from "@/lib/validations/schemas";
import { successResponse, errorResponse, unauthorizedResponse, validationErrorResponse } from "@/lib/api-response";
import { z } from "zod";

const prisma = new PrismaClient();

function addCorsHeaders(response: NextResponse, request?: NextRequest) {
    const origin = request?.headers.get('origin') || '*';
    response.headers.set('Access-Control-Allow-Origin', origin);
    response.headers.set('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE, OPTIONS');
    response.headers.set('Access-Control-Allow-Headers', 'Content-Type, Authorization');
    response.headers.set('Access-Control-Allow-Credentials', 'true');
    response.headers.set('Vary', 'Origin');
    return response;
}

export async function OPTIONS(request: NextRequest) {
    return addCorsHeaders(new NextResponse(null, { status: 204 }), request);
}

const successResponseCors = (data: any, req: NextRequest, status = 200) => addCorsHeaders(successResponse(data, status), req);
const errorResponseCors = (msg: string, req: NextRequest, details?: any, status = 500) => addCorsHeaders(errorResponse(msg, details, status), req);

export async function GET(request: NextRequest, { params }: { params: Promise<{ id: string }> }) {
    try {
        const session = await getServerSession(authOptions);
        if (!session) return addCorsHeaders(unauthorizedResponse(), request);

        const resolvedParams = await params;
        const document = await prisma.document.findUnique({
            where: { id: parseInt(resolvedParams.id) },
            include: {
                client: true,
                folder: true,
                communication: true,
                invoice: true
            }
        });

        if (!document) return errorResponseCors('Document not found', request, undefined, 404);

        return successResponseCors(document, request);
    } catch (error: any) {
        return errorResponseCors("Error fetching document", request, error.message);
    }
}

export async function PUT(request: NextRequest, { params }: { params: Promise<{ id: string }> }) {
    try {
        const session = await getServerSession(authOptions);
        if (!session || (session.user.role !== "MANAGER" && session.user.role !== "ADMIN")) {
            return addCorsHeaders(unauthorizedResponse(), request);
        }

        const body = await request.json();
        
        const PartialDocSchema = DocumentSchema.partial();
        try {
            PartialDocSchema.parse(body);
        } catch (validationError: any) {
            if (validationError instanceof z.ZodError) {
                return addCorsHeaders(validationErrorResponse(validationError), request);
            }
        }

        const resolvedParams = await params;
        const document = await prisma.document.update({
            where: { id: parseInt(resolvedParams.id) },
            data: {
                name: body.name,
                fileType: body.fileType,
                path: body.path,
                isPermanent: body.isPermanent,
                documentType: body.documentType,
                ...(body.clientId && { client: { connect: { id: parseInt(body.clientId) } } }),
                ...(body.folderId && { folder: { connect: { id: parseInt(body.folderId) } } }),
                ...(body.communicationId && { communication: { connect: { id: parseInt(body.communicationId) } } }),
                ...(body.invoiceId && { invoice: { connect: { id: parseInt(body.invoiceId) } } })
            }
        });
        return successResponseCors(document, request);
    } catch (error: any) {
        return errorResponseCors("Error updating document", request, error.message, 400);
    }
}

export async function DELETE(request: NextRequest, { params }: { params: Promise<{ id: string }> }) {
    try {
        const session = await getServerSession(authOptions);
        if (!session || (session.user.role !== "MANAGER" && session.user.role !== "ADMIN")) {
            return addCorsHeaders(unauthorizedResponse(), request);
        }

        const resolvedParams = await params;
        await prisma.document.delete({
            where: { id: parseInt(resolvedParams.id) }
        });
        return addCorsHeaders(new NextResponse(null, { status: 204 }), request);
    } catch (error: any) {
        return errorResponseCors("Error deleting document", request, error.message, 400);
    }
}