import { NextRequest, NextResponse } from 'next/server';
import { getAuth } from 'firebase-admin/auth';
import { getFirebaseAdmin } from '@/lib/firebase-admin';
import { FieldValue, Timestamp } from 'firebase-admin/firestore';
import { ADMIN_EMAILS } from '@/lib/constants';

const BATCH_LIMIT = 400;

export async function POST(req: NextRequest) {
    try {
        const authHeader = req.headers.get('Authorization');
        if (!authHeader?.startsWith('Bearer ')) {
            return NextResponse.json({ error: 'Unauthorized' }, { status: 401 });
        }
        const idToken = authHeader.split('Bearer ')[1];
        getFirebaseAdmin();
        let userEmail: string | undefined;
        try {
            const decoded = await getAuth().verifyIdToken(idToken);
            userEmail = decoded.email;
        } catch {
            return NextResponse.json({ error: 'Unauthorized: Invalid token' }, { status: 401 });
        }
        if (!userEmail || !ADMIN_EMAILS.includes(userEmail)) {
            return NextResponse.json({ error: 'Forbidden: Admin only' }, { status: 403 });
        }

        const { productId } = await req.json();
        if (!productId) {
            return NextResponse.json({ error: 'productId required' }, { status: 400 });
        }

        const db = getFirebaseAdmin().firestore();

        // 1. insurance_chunks_staging에서 해당 productId의 staging 청크 조회
        const stagingQuery = await db.collection('insurance_chunks_staging')
            .where('productId', '==', productId)
            .get();

        if (stagingQuery.empty) {
            return NextResponse.json(
                { error: 'No staging chunks found for this productId. Run reindex first.' },
                { status: 404 }
            );
        }

        const stagingDocs = stagingQuery.docs;
        const stagingCount = stagingDocs.length;

        // 2. 기존 insurance_chunks에서 해당 productId 청크 조회
        const existingChunksQuery = await db.collection('insurance_chunks')
            .where('productId', '==', productId)
            .get();

        const existingDocs = existingChunksQuery.docs;
        const previousCount = existingDocs.length;

        // 3. 기존 insurance_chunks → insurance_chunks_archive로 이동 (archiveExpireAt = 7일 후)
        if (previousCount > 0) {
            const archiveExpireAt = Timestamp.fromDate(new Date(Date.now() + 7 * 24 * 60 * 60 * 1000));
            const archivedAt = Timestamp.now();

            for (let i = 0; i < existingDocs.length; i += BATCH_LIMIT) {
                const archiveBatch = db.batch();
                const sliceDocs = existingDocs.slice(i, i + BATCH_LIMIT);

                for (const doc of sliceDocs) {
                    const archiveRef = db.collection('insurance_chunks_archive').doc(doc.id);
                    archiveBatch.set(archiveRef, {
                        ...doc.data(),
                        archivedAt,
                        archiveExpireAt,
                        originalDocId: doc.id,
                    });
                }
                await archiveBatch.commit();
            }
            console.log(`기존 ${previousCount}개 청크를 insurance_chunks_archive로 이동 완료`);
        }

        // 4. staging 청크를 insurance_chunks로 이동
        for (let i = 0; i < stagingDocs.length; i += BATCH_LIMIT) {
            const moveBatch = db.batch();
            const sliceDocs = stagingDocs.slice(i, i + BATCH_LIMIT);

            for (const doc of sliceDocs) {
                const targetRef = db.collection('insurance_chunks').doc(doc.id);
                moveBatch.set(targetRef, doc.data());
            }
            await moveBatch.commit();
        }
        console.log(`${stagingCount}개 staging 청크를 insurance_chunks로 이동 완료`);

        // 5. staging 청크 삭제
        for (let i = 0; i < stagingDocs.length; i += BATCH_LIMIT) {
            const deleteBatch = db.batch();
            stagingDocs.slice(i, i + BATCH_LIMIT).forEach((doc: FirebaseFirestore.QueryDocumentSnapshot) => deleteBatch.delete(doc.ref));
            await deleteBatch.commit();
        }
        console.log(`${stagingCount}개 staging 청크 삭제 완료`);

        // 6. 성공 응답 (이동된 청크 수 반환)
        return NextResponse.json({
            success: true,
            productId,
            switchedChunksCount: stagingCount,
            archivedChunksCount: previousCount,
        });
    } catch (error: any) {
        console.error('POST /api/admin/insurance/reindex/switch error:', error);
        return NextResponse.json({ error: 'Internal Server Error', message: error.message }, { status: 500 });
    }
}
