import { NextResponse } from 'next/server';
import { insertMessage, insertEvent, getDb } from '@/lib/db';
import { sendSms } from '@/lib/twilio-client';
import { broadcast } from '@/lib/sse';
import { generateId } from '@/lib/utils';

export const dynamic = 'force-dynamic';

interface CloseBotPayload {
  message?: string;
  response?: string; // Some CloseBot versions use 'response' instead of 'message'
  state?: string;
  leadId?: string;
  sourceId?: string;
}

interface ParsedState {
  twilioNumber: string;
  phoneFrom: string;
  routeId: string;
  contactId: string;
}

export async function POST(request: Request) {
  let payload: CloseBotPayload;

  try {
    payload = await request.json();
  } catch (parseError) {
    console.error('[closebot-response] Failed to parse request body:', parseError);
    return NextResponse.json({ error: 'Invalid JSON body' }, { status: 400 });
  }

  try {
    // CloseBot may send the reply as 'message' or 'response'
    const botMessage = payload.message || payload.response;
    const stateStr = payload.state;

    if (!botMessage) {
      console.warn('[closebot-response] No message in CloseBot payload:', JSON.stringify(payload).slice(0, 200));
      return NextResponse.json({ error: 'No message in payload' }, { status: 400 });
    }

    if (!stateStr) {
      console.error('[closebot-response] No state in CloseBot payload — cannot route reply');
      return NextResponse.json({ error: 'No state in payload, cannot determine recipient' }, { status: 400 });
    }

    // ── Step 1: Parse state ──
    let state: ParsedState;
    try {
      state = JSON.parse(stateStr);
    } catch (stateError) {
      console.error('[closebot-response] Failed to parse state JSON:', stateStr);
      return NextResponse.json({ error: 'Invalid state JSON' }, { status: 400 });
    }

    const { twilioNumber, phoneFrom, routeId, contactId } = state;

    if (!twilioNumber || !phoneFrom) {
      console.error('[closebot-response] Missing twilioNumber or phoneFrom in state:', state);
      return NextResponse.json({ error: 'Incomplete state: missing routing info' }, { status: 400 });
    }

    console.log(`[closebot-response] Bot reply for ${phoneFrom} via ${twilioNumber}: "${botMessage.slice(0, 80)}"`);

    // ── Step 2: Send SMS via Twilio ──
    let twilioSid = '';
    try {
      twilioSid = await sendSms(phoneFrom, twilioNumber, botMessage);
      console.log(`[closebot-response] SMS sent: ${twilioSid}`);
    } catch (twilioError) {
      console.error('[closebot-response] Failed to send SMS via Twilio:', twilioError);
      return NextResponse.json(
        { error: 'Failed to send SMS via Twilio', details: String(twilioError) },
        { status: 500 }
      );
    }

    // ── Step 3: Log outbound message ──
    const msgId = generateId();
    try {
      insertMessage({
        id: msgId,
        contact_id: contactId,
        route_id: routeId,
        direction: 'outbound',
        source: 'bot',
        body: botMessage,
        twilio_sid: twilioSid,
      });
    } catch (dbError) {
      console.error('[closebot-response] Failed to log message to DB:', dbError);
      // Don't fail — the SMS was already sent
    }

    // ── Step 4: Insert event ──
    try {
      insertEvent({
        type: 'message_out',
        contact_id: contactId,
        route_id: routeId,
        data_json: JSON.stringify({
          body: botMessage.slice(0, 200),
          twilio_sid: twilioSid,
          source: 'bot',
        }),
      });
    } catch (eventError) {
      console.error('[closebot-response] Failed to insert event:', eventError);
    }

    // ── Step 5: Broadcast via SSE ──
    try {
      // Get bot name and contact info for the activity feed
      const db = getDb();
      const route = db.prepare('SELECT bot_name FROM routes WHERE id = ?').get(routeId) as { bot_name: string | null } | undefined;
      const contact = db.prepare('SELECT name, phone FROM contacts WHERE id = ?').get(contactId) as { name: string | null; phone: string } | undefined;

      broadcast('activity', {
        type: 'message_out',
        contact_id: contactId,
        phone: contact?.phone || phoneFrom,
        name: contact?.name,
        bot_name: route?.bot_name,
        body: botMessage.slice(0, 100),
        created_at: new Date().toISOString(),
      });

      broadcast('message', {
        id: msgId,
        contact_id: contactId,
        route_id: routeId,
        direction: 'outbound',
        source: 'bot',
        body: botMessage,
        twilio_sid: twilioSid,
        created_at: new Date().toISOString(),
      });
    } catch (sseError) {
      console.error('[closebot-response] Failed to broadcast SSE:', sseError);
    }

    return NextResponse.json({ success: true, twilio_sid: twilioSid });
  } catch (error) {
    console.error('[closebot-response] Unhandled error:', error);
    return NextResponse.json(
      { error: 'Internal server error processing CloseBot response' },
      { status: 500 }
    );
  }
}
