/**
 * Lead Qualification Service
 * AI-powered lead qualification, action suggestions, and conversation extraction via Gemini
 */

import { leadsAdapter, leadActivitiesAdapter } from '@/lib/adapters/leads';
import { logger } from '@/lib/logger';
import type {
  QualificationResult,
  SuggestedAction,
  LeadGrade,
} from '@/lib/types/lead-crm.types';
import { getLeadGrade } from '@/lib/types/lead-crm.types';
import { createId } from '@paralleldrive/cuid2';
/** JSON-compatible input value (replaces InputJsonValue) */
type InputJsonValue = string | number | boolean | null | InputJsonValue[] | { [key: string]: InputJsonValue };

const log = logger.scope('LeadQualificationService');

async function getGeminiModel() {
  const { GoogleGenerativeAI } = await import('@google/generative-ai');
  const genAI = new GoogleGenerativeAI(process.env.GOOGLE_API_KEY!);
  return genAI.getGenerativeModel({ model: 'gemini-1.5-flash' });
}

// ═══════════════════════════════════════════════════════════════════════
// AI Qualification
// ═══════════════════════════════════════════════════════════════════════

export async function qualify(userId: string, leadId: string): Promise<QualificationResult> {
  const lead = (await leadsAdapter.findFirst({
    where: { id: leadId, userId },
    include: {
      activities: { orderBy: { createdAt: 'desc' }, take: 20 },
      pipelineStage: true,
    },
  })) as any;
  if (!lead) throw new Error('Lead not found');

  const model = await getGeminiModel();

  const prompt = `You are a lead qualification expert for a B2B SaaS company in the GCC region (Qatar, Saudi Arabia, UAE).
Analyze this lead and provide a qualification assessment.

Lead Data:
- Name: ${lead.name}
- Company: ${lead.company ?? 'Unknown'}
- Email: ${lead.email ?? 'None'}
- Phone: ${lead.phone ?? 'None'}
- Source: ${lead.source}
- Current Score: ${lead.score}
- Status: ${lead.status}
- Pipeline Stage: ${lead.pipelineStage?.name ?? 'None'}
- Deal Value: ${lead.dealValue ?? 0} ${lead.dealCurrency ?? 'QAR'}
- Interest: ${lead.interest ?? 'Not specified'}
- Tags: ${lead.tags.join(', ') || 'None'}
- Touch Count: ${lead.touchCount}
- Last Activity: ${lead.lastActivityAt?.toISOString() ?? 'Never'}

Recent Activities:
${lead.activities.map((a: any) => `- [${a.type}] ${a.title} (${a.createdAt.toISOString()})`).join('\n') || 'No activities'}

Respond in JSON format ONLY (no markdown, no code blocks):
{
  "score": <number 0-100>,
  "summary": "<1-2 sentence assessment>",
  "strengths": ["<strength1>", "<strength2>"],
  "concerns": ["<concern1>", "<concern2>"],
  "suggestedActions": [
    {
      "action": "<action description>",
      "priority": "high|medium|low",
      "description": "<detailed description>",
      "channel": "EMAIL|WHATSAPP|null"
    }
  ]
}`;

  const result = await model.generateContent(prompt);
  const text = result.response.text();

  let parsed: {
    score: number;
    summary: string;
    strengths: string[];
    concerns: string[];
    suggestedActions: SuggestedAction[];
  };

  try {
    // Strip any markdown code blocks
    const cleaned = text.replace(/```json?\n?/g, '').replace(/```/g, '').trim();
    parsed = JSON.parse(cleaned);
  } catch {
    log.warn('Failed to parse AI qualification response', { leadId, text });
    parsed = {
      score: (lead as any).score,
      summary: 'AI qualification analysis unavailable. Manual review recommended.',
      strengths: [],
      concerns: ['AI analysis could not be completed'],
      suggestedActions: [
        { action: 'Manual qualification review', priority: 'high', description: 'Review lead data manually' },
      ],
    };
  }

  const qualScore = Math.max(0, Math.min(100, parsed.score));
  const grade = getLeadGrade(qualScore);
  const now = new Date();

  // Update lead qualification
  await leadsAdapter.update({
    where: { id: leadId },
    data: {
      qualificationScore: qualScore,
      qualifiedAt: now,
      updatedAt: now,
    },
  });

  // Log AI qualification activity
  await leadActivitiesAdapter.create({
    data: {
      id: createId(),
      leadId,
      userId,
      type: 'AI_QUALIFICATION',
      title: `AI Qualification: Grade ${grade} (${qualScore}/100)`,
      description: parsed.summary,
      metadata: { score: qualScore, grade, strengths: parsed.strengths, concerns: parsed.concerns } as unknown as InputJsonValue,
    },
  });

  log.info('Lead qualified by AI', { leadId, score: qualScore, grade });

  return {
    score: qualScore,
    grade: grade as LeadGrade,
    summary: parsed.summary,
    strengths: parsed.strengths,
    concerns: parsed.concerns,
    suggestedActions: parsed.suggestedActions,
    qualifiedAt: now,
  };
}

export async function suggestAction(userId: string, leadId: string): Promise<SuggestedAction[]> {
  const lead = (await leadsAdapter.findFirst({
    where: { id: leadId, userId },
    include: {
      activities: { orderBy: { createdAt: 'desc' }, take: 10 },
      pipelineStage: true,
    },
  })) as any;
  if (!lead) throw new Error('Lead not found');

  const model = await getGeminiModel();

  const prompt = `You are a sales strategy advisor for a B2B SaaS company in the GCC region.
Suggest the next best action for this lead.

Lead: ${lead.name} (${lead.company ?? 'Unknown company'})
Score: ${lead.score}/100 | Stage: ${lead.pipelineStage?.name ?? 'None'} | Status: ${lead.status}
Last Contact: ${lead.lastContactAt?.toISOString() ?? 'Never'}
Activities: ${lead.activities.length} total

Recent activities:
${lead.activities.slice(0, 5).map((a: any) => `- [${a.type}] ${a.title}`).join('\n') || 'None'}

Respond in JSON format ONLY (no markdown, no code blocks):
[
  {
    "action": "<what to do>",
    "priority": "high|medium|low",
    "description": "<why and how>",
    "channel": "EMAIL|WHATSAPP|null"
  }
]
Provide 2-4 suggestions.`;

  const result = await model.generateContent(prompt);
  const text = result.response.text();

  try {
    const cleaned = text.replace(/```json?\n?/g, '').replace(/```/g, '').trim();
    return JSON.parse(cleaned) as SuggestedAction[];
  } catch {
    log.warn('Failed to parse AI suggestion response', { leadId });
    return [
      { action: 'Follow up via WhatsApp', priority: 'high', description: 'Send a personalized follow-up message' },
      { action: 'Schedule a demo call', priority: 'medium', description: 'Book a product demonstration' },
    ];
  }
}

export async function extractLeadFromConversation(
  userId: string,
  conversationData: string,
): Promise<{
  name: string;
  phone?: string;
  email?: string;
  company?: string;
  interest?: string;
  language?: 'ar' | 'en';
}> {
  const model = await getGeminiModel();

  const prompt = `Extract lead information from this customer conversation.
The business operates in the GCC region (Qatar, Saudi Arabia, UAE).

Conversation:
${conversationData}

Respond in JSON format ONLY (no markdown, no code blocks):
{
  "name": "<customer name or 'Unknown'>",
  "phone": "<phone number if mentioned>",
  "email": "<email if mentioned>",
  "company": "<company name if mentioned>",
  "interest": "<what they're interested in>",
  "language": "ar|en"
}`;

  const result = await model.generateContent(prompt);
  const text = result.response.text();

  try {
    const cleaned = text.replace(/```json?\n?/g, '').replace(/```/g, '').trim();
    return JSON.parse(cleaned);
  } catch {
    log.warn('Failed to parse conversation extraction', { userId });
    return { name: 'Unknown', language: 'en' };
  }
}
