import pool from '@/lib/database';
import type { RowDataPacket } from 'mysql2';

import { sendMail } from '@/lib/mailsend';

import { NextResponse, NextRequest } from 'next/server';

// コード生成
async function createCode(maxAttempts = 10) {
    for (let i = 0; i < maxAttempts; i++) {
        const code = Math.floor(100000 + Math.random() * 900000).toString();
        const [existingCodes] = await pool.execute<RowDataPacket[]>(
            "SELECT * FROM mailverifiedcode WHERE code = ?",[code]
        );
        if (existingCodes.length === 0) {
            return code;
        }
    }
    throw new Error("Failed to generate unique code after maximum attempts");
}

export async function POST(request: NextRequest) {
    // body取得
    const body = await request.json();
    const { email, user } = body;

    const code = await createCode();

    // コードが存在する場合
    const [existingCodes] = await pool.execute<RowDataPacket[]>(
        "SELECT * FROM mailverifiedcode WHERE user = ?",[user]
    );
    
    let row: RowDataPacket[] = [];

    if(existingCodes.length !== 0){
        [row] = await pool.execute<RowDataPacket[]>(
            "UPDATE `mailverifiedcode` SET `code` = ?, `time` = current_timestamp(3) WHERE `mailverifiedcode`.`user` = ?",
            [code, user]
        )
    }else{
        // コードが存在しない場合
        [row] = await pool.execute<RowDataPacket[]>(
            "INSERT INTO `mailverifiedcode` (`code`, `user`, `email`, `time`, `num`) VALUES (?, ?, ?, current_timestamp(3), NULL);",
            [code, user, email]
        )
    }

    // メール送信
    if ((row as RowDataPacket).affectedRows === 1) {
        await sendMail({
            to: email,
            subject: "【Peas】メール認証",
            text: `${user}さんこんにちは。\n
            Peasではメール認証が必要となっています。\n
            メール認証をすることでPeasの機能を利用することができます。\n
            ${request.nextUrl.origin}/mailverify?code=${code} にアクセスしてください。`
        })

        return NextResponse.json({
            status: "success",
            code: code,
        })
    }else{
        // コード保存失敗
        return NextResponse.json({
            status: "error",
            error: "Failed to Save Code"
        }, { status: 400 });
    }
}