import { NextRequest, NextResponse } from "next/server";
import { auth } from "@/lib/auth";
import { headers } from "next/headers";
import { prisma } from "@/lib/prisma";
import { getPromptContent, calculateCost } from "@/lib/simulator-utils";
import { consumeCreditForSimulation, getUserBalance } from "@/lib/services/credit";
import { UniAPIService } from "@/lib/uniapi";
import { FalService } from "@/lib/fal";
import { uploadBase64Image } from "@/lib/storage";
import type { Prisma } from "@prisma/client";

// 图像生成模型适配器接口
interface ModelAdapter {
  id: string;
  name: string;
  prepareRequest: (userInput: string, promptContent: string, params: Record<string, unknown>) => Record<string, unknown>;
  parseResponse: (response: Record<string, unknown>) => { content: string; outputType?: string; imageData?: string };
}

// 图像生成模型适配器
const IMAGE_MODEL_ADAPTERS: Record<string, ModelAdapter> = {
  'gpt-image-1': {
    id: 'gpt-image-1',
    name: 'GPT Image 1',
    prepareRequest: (userInput: string, promptContent: string, params: Record<string, unknown>) => ({
      model: 'gpt-image-1',
      prompt: `${promptContent}\n\nUser input: ${userInput}`,
      size: '1024x1024',
      quality: 'standard',
      ...params
    }),
    parseResponse: (response: Record<string, unknown>) => ({
      content: (response as { data?: { url: string }[]; url?: string }).data?.[0]?.url || (response as { url?: string }).url || 'Image generated successfully',
      outputType: 'image'
    })
  },
  'google/gemini-2.5-flash-image-preview': {
    id: 'google/gemini-2.5-flash-image-preview',
    name: 'Gemini 2.5 Flash Image Preview',
    prepareRequest: (userInput: string, promptContent: string, params: Record<string, unknown>) => ({
      model: 'google/gemini-2.5-flash-image-preview',
      messages: [{
        role: 'user',
        content: `${promptContent}\n\nUser input: ${userInput}`
      }],
      temperature: params.temperature || 0.7,
      ...(params.maxTokens ? { max_tokens: params.maxTokens } : {}),
      ...(params.topP ? { top_p: params.topP } : {}),
      ...(params.frequencyPenalty ? { frequency_penalty: params.frequencyPenalty } : {}),
      ...(params.presencePenalty ? { presence_penalty: params.presencePenalty } : {})
    }),
    parseResponse: (response: Record<string, unknown>) => {
      // 尝试从不同的响应格式中提取内容
      const choices = (response as { choices?: Array<{ message?: { content?: string; images?: Array<{ image_url?: { url?: string } }> } }> }).choices
      const choice = choices?.[0]
      const content = choice?.message?.content || ''
      
      // 提取 base64 图片数据
      const images = choice?.message?.images
      let imageData = ''
      
      if (images && images.length > 0) {
        const imageUrl = images[0]?.image_url?.url
        if (imageUrl && imageUrl.startsWith('data:image/')) {
          imageData = imageUrl
        }
      }
      
      // 如果有图片数据，返回图片数据，否则返回文本内容
      return {
        content: imageData || content || 'No image data found in response',
        outputType: 'image',
        imageData: imageData
      }
    }
  }
};

// Define the type for the simulator run with included relations
type SimulatorRunWithRelations = Prisma.SimulatorRunGetPayload<{
  include: {
    prompt: true;
    promptVersion: true;
    model: true;
    user: {
      include: {
        subscriptionPlan: true;
      };
    };
  };
}>;

export async function POST(
  request: NextRequest,
  { params }: { params: Promise<{ id: string }> }
) {
  const { id } = await params;
  try {
    const session = await auth.api.getSession({ headers: await headers() });
    if (!session?.user) {
      return NextResponse.json({ error: "Unauthorized" }, { status: 401 });
    }
    const user = session.user;

    const run: SimulatorRunWithRelations | null = await prisma.simulatorRun.findFirst({
      where: {
        id,
        userId: user.id,
      },
      include: {
        prompt: true,
        promptVersion: true, // 内部使用，用于获取内容
        model: true,
        user: {
          include: {
            subscriptionPlan: true
          }
        }
      }
    });

    if (!run) {
      return NextResponse.json({ error: "Run not found" }, { status: 404 });
    }

    if (run.status !== "pending") {
      return NextResponse.json({ error: "Run already executed" }, { status: 400 });
    }

    // Check user's credit balance before execution
    const userBalance = await getUserBalance(user.id);
    const costMultiplier = (run.user.subscriptionPlan as { costMultiplier?: number })?.costMultiplier || 1.0;
    const estimatedCost = calculateCost(0, 100, run.model, costMultiplier); // Rough estimate
    
    if (userBalance < estimatedCost) {
      return NextResponse.json(
        { error: "Insufficient credit balance", requiredCredit: estimatedCost, currentBalance: userBalance }, 
        { status: 402 } // Payment Required
      );
    }

    // 更新状态为运行中
    await prisma.simulatorRun.update({
      where: { id },
      data: { status: "running" },
    });

    // 准备AI API请求
    const promptContent = getPromptContent(run);
    const finalPrompt = `${promptContent}\n\nUser Input: ${run.userInput}`;
    
    let apiResponse: Response;
    let debugRequest: Record<string, unknown> | null = null;
    let debugResponse: Record<string, unknown> | null = null;
    const isDevelopment = process.env.NODE_ENV === 'development';
    
    // 根据服务提供商和模型类型选择不同的API
    if (run.model.serviceProvider === 'openrouter') {
      // 检查是否是图像生成模型
      if (run.model.outputType === 'image' && IMAGE_MODEL_ADAPTERS[run.model.modelId]) {
        // 使用图像生成模型适配器
        const adapter = IMAGE_MODEL_ADAPTERS[run.model.modelId];
        const requestBody = adapter.prepareRequest(
          run.userInput, 
          promptContent, 
          {
            temperature: run.temperature,
            maxTokens: run.maxTokens,
            topP: run.topP,
            frequencyPenalty: run.frequencyPenalty,
            presencePenalty: run.presencePenalty,
          }
        );

        // 存储调试信息
        if (isDevelopment) {
          debugRequest = {
            url: "https://openrouter.ai/api/v1/chat/completions",
            method: "POST",
            headers: {
              "Content-Type": "application/json",
              "HTTP-Referer": process.env.NEXT_PUBLIC_APP_URL || "http://localhost:3000",
              "X-Title": "Prmbr - AI Prompt Studio",
            },
            body: requestBody
          };
        }

        // 对于图像生成，使用非流式请求
        apiResponse = await fetch("https://openrouter.ai/api/v1/chat/completions", {
          method: "POST",
          headers: {
            "Authorization": `Bearer ${process.env.OPENROUTER_API_KEY}`,
            "Content-Type": "application/json",
            "HTTP-Referer": process.env.NEXT_PUBLIC_APP_URL || "http://localhost:3000",
            "X-Title": "Prmbr - AI Prompt Studio",
          },
          body: JSON.stringify(requestBody),
        });

        // 对于图像生成，我们需要处理非流式响应
        if (apiResponse.ok) {
          const responseData = await apiResponse.json();
          
          // 存储调试响应信息
          if (isDevelopment) {
            debugResponse = {
              status: apiResponse.status,
              headers: Object.fromEntries(apiResponse.headers.entries()),
              body: responseData
            };
          }
          
          const parsedResult = adapter.parseResponse(responseData);
          
          // 创建模拟的流式响应
          const mockStream = new ReadableStream({
            start(controller) {
              // 模拟流式数据
              controller.enqueue(new TextEncoder().encode(`data: ${JSON.stringify({
                choices: [{
                  delta: { content: parsedResult.content }
                }]
              })}\n\n`));
              
              controller.enqueue(new TextEncoder().encode(`data: ${JSON.stringify({
                usage: { prompt_tokens: 50, completion_tokens: 100 } // 估算的token使用量
              })}\n\n`));

              // 异步处理图像生成数据存储
              (async () => {
                try {
                  // 对于图像生成，存储图片数据并完成运行
                  const startTime = Date.now();
                  const duration = Date.now() - startTime;
                  const actualCost = calculateCost(50, 100, run.model, costMultiplier);

                  // Consume credits for this simulation
                  let creditTransaction;
                  try {
                    creditTransaction = await consumeCreditForSimulation(
                      user.id,
                      actualCost,
                      id,
                      `${run.model.name} image generation`
                    );
                  } catch (creditError) {
                    await prisma.simulatorRun.update({
                      where: { id },
                      data: {
                        status: "failed",
                        error: `Credit consumption failed: ${creditError}`,
                      },
                    });
                    return;
                  }

                  // 更新运行状态并存储图片数据
                  // 如果有图片数据，上传到S3
                  let generatedFilePath = null;
                  if (parsedResult.imageData && parsedResult.imageData.startsWith('data:image/')) {
                    try {
                      const fileName = `run-${id}-${Date.now()}.png`;
                      generatedFilePath = await uploadBase64Image(parsedResult.imageData, fileName);
                      console.log('Image uploaded to S3:', generatedFilePath);
                    } catch (error) {
                      console.error('Error uploading image to S3:', error);
                    }
                  }

                  await prisma.simulatorRun.update({
                    where: { id },
                    data: {
                      status: "completed",
                      output: parsedResult.content,
                      inputTokens: 50,
                      outputTokens: 100,
                      totalCost: actualCost,
                      duration,
                      creditId: creditTransaction.id,
                      completedAt: new Date(),
                      generatedFilePath,
                      ...(isDevelopment && debugRequest ? { debugRequest: debugRequest as Prisma.InputJsonValue } : {}),
                      ...(isDevelopment && debugResponse ? { debugResponse: debugResponse as Prisma.InputJsonValue } : {}),
                    },
                  });
                } catch (error) {
                  console.error("Error storing image data:", error);
                }
              })();
              
              controller.enqueue(new TextEncoder().encode(`data: [DONE]\n\n`));
              controller.close();
            }
          });

          apiResponse = new Response(mockStream, {
            headers: {
              'Content-Type': 'text/event-stream',
            }
          });
        } else {
          const errorData = await apiResponse.text();
          // 存储错误响应信息
          if (isDevelopment) {
            debugResponse = {
              status: apiResponse.status,
              headers: Object.fromEntries(apiResponse.headers.entries()),
              body: { error: errorData }
            };
          }
        }
      } else {
        // 使用标准的文本聊天完成API
        const requestBody = {
          model: run.model.modelId,
          messages: [
            {
              role: "user",
              content: finalPrompt,
            }
          ],
          temperature: run.temperature || 0.7,
          ...(run.maxTokens && { max_tokens: run.maxTokens }),
          ...(run.topP && { top_p: run.topP }),
          ...(run.frequencyPenalty && { frequency_penalty: run.frequencyPenalty }),
          ...(run.presencePenalty && { presence_penalty: run.presencePenalty }),
          stream: true,
        };

        // 存储调试信息
        if (isDevelopment) {
          debugRequest = {
            url: "https://openrouter.ai/api/v1/chat/completions",
            method: "POST",
            headers: {
              "Content-Type": "application/json",
              "HTTP-Referer": process.env.NEXT_PUBLIC_APP_URL || "http://localhost:3000",
              "X-Title": "Prmbr - AI Prompt Studio",
            },
            body: requestBody
          };
        }

        apiResponse = await fetch("https://openrouter.ai/api/v1/chat/completions", {
          method: "POST",
          headers: {
            "Authorization": `Bearer ${process.env.OPENROUTER_API_KEY}`,
            "Content-Type": "application/json",
            "HTTP-Referer": process.env.NEXT_PUBLIC_APP_URL || "http://localhost:3000",
            "X-Title": "Prmbr - AI Prompt Studio",
          },
          body: JSON.stringify(requestBody),
        });
      }
    } else if (run.model.serviceProvider === 'uniapi') {
      const uniAPIService = new UniAPIService();
      
      if (run.model.outputType === 'text' || run.model.outputType === 'multimodal') {
        // 使用聊天完成API
        const requestBody = {
          model: run.model.modelId,
          messages: [
            {
              role: "user",
              content: finalPrompt,
            }
          ],
          temperature: run.temperature || 0.7,
          ...(run.maxTokens && { max_tokens: run.maxTokens }),
          ...(run.topP && { top_p: run.topP }),
          ...(run.frequencyPenalty && { frequency_penalty: run.frequencyPenalty }),
          ...(run.presencePenalty && { presence_penalty: run.presencePenalty }),
        };

        // 注意：UniAPI 可能不支持流式响应，这里需要调整
        const response = await uniAPIService.createChatCompletion(requestBody);
        
        // 创建模拟的流式响应
        const mockStream = new ReadableStream({
          start(controller) {
            const content = response.choices?.[0]?.message?.content || '';
            const usage = response.usage || { prompt_tokens: 0, completion_tokens: 0 };
            
            // 模拟流式数据
            controller.enqueue(new TextEncoder().encode(`data: ${JSON.stringify({
              choices: [{
                delta: { content: content }
              }]
            })}\n\n`));
            
            controller.enqueue(new TextEncoder().encode(`data: ${JSON.stringify({
              usage: usage
            })}\n\n`));
            
            controller.enqueue(new TextEncoder().encode(`data: [DONE]\n\n`));
            controller.close();
          }
        });

        apiResponse = new Response(mockStream, {
          headers: {
            'Content-Type': 'text/event-stream',
          }
        });
      } else {
        // 对于非文本模型，返回错误
        await prisma.simulatorRun.update({
          where: { id },
          data: {
            status: "failed",
            error: `Unsupported model type: ${run.model.outputType}`,
          },
        });
        return NextResponse.json({ error: "Unsupported model type" }, { status: 400 });
      }
    } else if (run.model.serviceProvider === 'fal') {
      const falService = new FalService();
      
      if (run.model.outputType === 'image') {
        // 使用图像生成API
        const response = await falService.generateImage({
          model: run.model.modelId,
          prompt: finalPrompt,
          num_images: 1,
        });
        
        // 创建模拟的流式响应
        const mockStream = new ReadableStream({
          start(controller) {
            const imageUrl = response.images?.[0]?.url || '';
            const result = {
              images: response.images,
              prompt: finalPrompt,
              model: run.model.modelId
            };
            
            // 模拟流式数据
            controller.enqueue(new TextEncoder().encode(`data: ${JSON.stringify({
              choices: [{
                delta: { content: `Generated image: ${imageUrl}\n\nResult: ${JSON.stringify(result, null, 2)}` }
              }]
            })}\n\n`));
            
            controller.enqueue(new TextEncoder().encode(`data: ${JSON.stringify({
              usage: { prompt_tokens: 50, completion_tokens: 100 } // 估算的token使用量
            })}\n\n`));
            
            controller.enqueue(new TextEncoder().encode(`data: [DONE]\n\n`));
            controller.close();
          }
        });

        apiResponse = new Response(mockStream, {
          headers: {
            'Content-Type': 'text/event-stream',
          }
        });
      } else if (run.model.outputType === 'video') {
        // 使用视频生成API
        const response = await falService.generateVideo({
          model: run.model.modelId,
          prompt: finalPrompt,
        });
        
        // 创建模拟的流式响应
        const mockStream = new ReadableStream({
          start(controller) {
            const videoUrl = response.video?.url || '';
            const result = {
              video: response.video,
              prompt: finalPrompt,
              model: run.model.modelId
            };
            
            controller.enqueue(new TextEncoder().encode(`data: ${JSON.stringify({
              choices: [{
                delta: { content: `Generated video: ${videoUrl}\n\nResult: ${JSON.stringify(result, null, 2)}` }
              }]
            })}\n\n`));
            
            controller.enqueue(new TextEncoder().encode(`data: ${JSON.stringify({
              usage: { prompt_tokens: 50, completion_tokens: 150 } // 估算的token使用量
            })}\n\n`));
            
            controller.enqueue(new TextEncoder().encode(`data: [DONE]\n\n`));
            controller.close();
          }
        });

        apiResponse = new Response(mockStream, {
          headers: {
            'Content-Type': 'text/event-stream',
          }
        });
      } else {
        // 对于其他类型，返回错误
        await prisma.simulatorRun.update({
          where: { id },
          data: {
            status: "failed",
            error: `Unsupported Fal.ai model type: ${run.model.outputType}`,
          },
        });
        return NextResponse.json({ error: "Unsupported model type" }, { status: 400 });
      }
    } else {
      await prisma.simulatorRun.update({
        where: { id },
        data: {
          status: "failed",
          error: `Unsupported service provider: ${run.model.serviceProvider}`,
        },
      });
      return NextResponse.json({ error: "Unsupported service provider" }, { status: 400 });
    }

    if (!apiResponse.ok) {
      const errorText = await apiResponse.text();
      await prisma.simulatorRun.update({
        where: { id },
        data: {
          status: "failed",
          error: `API error: ${apiResponse.status} - ${errorText}`,
        },
      });
      return NextResponse.json({ error: "AI API request failed" }, { status: 500 });
    }

    // 创建流式响应
    const stream = new ReadableStream({
      async start(controller) {
        const reader = apiResponse.body?.getReader();
        if (!reader) {
          controller.close();
          return;
        }

        let fullResponse = "";
        let inputTokens = 0;
        let outputTokens = 0;
        const startTime = Date.now();

        try {
          while (true) {
            const { done, value } = await reader.read();
            if (done) break;

            const chunk = new TextDecoder().decode(value);
            const lines = chunk.split('\n');

            for (const line of lines) {
              if (line.startsWith('data: ')) {
                const data = line.slice(6);
                if (data === '[DONE]') {
                  // 计算最终数据并更新数据库
                  const duration = Date.now() - startTime;
                  const actualCost = calculateCost(inputTokens, outputTokens, run.model, costMultiplier);

                  // Consume credits for this simulation
                  let creditTransaction;
                  try {
                    creditTransaction = await consumeCreditForSimulation(
                      user.id,
                      actualCost,
                      id,
                      `${run.model.name} simulation: ${inputTokens} input + ${outputTokens} output tokens`
                    );
                  } catch (creditError) {
                    // If credit consumption fails, mark the run as failed
                    await prisma.simulatorRun.update({
                      where: { id },
                      data: {
                        status: "failed",
                        error: `Credit consumption failed: ${creditError}`,
                      },
                    });
                    controller.enqueue(new TextEncoder().encode(`data: {"error": "Credit consumption failed"}\n\n`));
                    controller.close();
                    return;
                  }

                  // Update the run with completion data and credit reference
                  await prisma.simulatorRun.update({
                    where: { id },
                    data: {
                      status: "completed",
                      output: fullResponse,
                      inputTokens,
                      outputTokens,
                      totalCost: actualCost,
                      duration,
                      creditId: creditTransaction.id,
                      completedAt: new Date(),
                      ...(isDevelopment && debugRequest ? { debugRequest: debugRequest as Prisma.InputJsonValue } : {}),
                      ...(isDevelopment && debugResponse ? { debugResponse: debugResponse as Prisma.InputJsonValue } : {}),
                    },
                  });

                  controller.enqueue(new TextEncoder().encode(`data: [DONE]\n\n`));
                  controller.close();
                  return;
                }

                try {
                  const parsed = JSON.parse(data);
                  if (parsed.choices?.[0]?.delta?.content) {
                    const content = parsed.choices[0].delta.content;
                    fullResponse += content;
                  }
                  
                  // 估算token使用量（简化版本）
                  if (parsed.usage) {
                    inputTokens = parsed.usage.prompt_tokens || 0;
                    outputTokens = parsed.usage.completion_tokens || 0;
                  }
                } catch {
                  // 忽略解析错误，继续处理其他数据
                }

                controller.enqueue(new TextEncoder().encode(`data: ${data}\n\n`));
              }
            }
          }
        } catch (error) {
          console.error("Stream processing error:", error);
          await prisma.simulatorRun.update({
            where: { id },
            data: {
              status: "failed",
              error: `Stream processing error: ${error}`,
            },
          });
          controller.close();
        }
      },
    });

    return new NextResponse(stream, {
      headers: {
        'Content-Type': 'text/event-stream',
        'Cache-Control': 'no-cache',
        'Connection': 'keep-alive',
      },
    });
  } catch (error) {
    console.error("Error executing simulator run:", error);
    
    // 更新运行状态为失败
    await prisma.simulatorRun.update({
      where: { id },
      data: {
        status: "failed",
        error: `Execution error: ${error}`,
      },
    }).catch(() => {}); // 忽略更新失败

    return NextResponse.json(
      { error: "Internal server error" },
      { status: 500 }
    );
  }
}