import { NextRequest, NextResponse } from "next/server";
import { logger } from "../utils/logger";

export interface ApiLoggerOptions {
  logRequests?: boolean;
  logResponses?: boolean;
  logErrors?: boolean;
  excludePaths?: string[];
}

export class ApiLogger {
  static async logRequest(
    request: NextRequest,
    response: NextResponse,
    duration: number,
    options: ApiLoggerOptions = {}
  ): Promise<void> {
    const {
      logRequests = true,
      logResponses = true,
      logErrors = true,
      excludePaths = [],
    } = options;

    const url = new URL(request.url);
    const path = url.pathname;

    // 跳过排除的路径
    if (excludePaths.some((excludePath) => path.startsWith(excludePath))) {
      return;
    }

    const method = request.method;
    const statusCode = response.status;
    const userAgent = request.headers.get("user-agent") || "Unknown";
    const ip =
      request.headers.get("x-forwarded-for") ||
      request.headers.get("x-real-ip") ||
      "Unknown";

    // 记录请求
    if (logRequests) {
      logger.logApiRequest(method, path, statusCode, duration);
    }

    // 记录错误
    if (logErrors && statusCode >= 400) {
      logger.error("API Error", {
        method,
        path,
        statusCode,
        duration,
        userAgent,
        ip,
      });
    }

    // 记录响应统计
    if (logResponses) {
      logger.info("API Response", {
        method,
        path,
        statusCode,
        duration,
        userAgent,
        ip,
      });
    }
  }

  static createMiddleware(options: ApiLoggerOptions = {}) {
    return async (
      request: NextRequest,
      handler: () => Promise<NextResponse>
    ) => {
      const startTime = Date.now();

      try {
        const response = await handler();
        const duration = Date.now() - startTime;

        await this.logRequest(request, response, duration, options);

        return response;
      } catch (error) {
        const duration = Date.now() - startTime;
        const errorResponse = NextResponse.json(
          { error: "Internal Server Error" },
          { status: 500 }
        );

        await this.logRequest(request, errorResponse, duration, options);

        throw error;
      }
    };
  }
}
