import { logger } from '../utils/logger';
import { llmService } from './llmService';

import { CIMReview } from './llmSchemas';

interface DocumentSection {
  id: string;
  type: 'executive_summary' | 'business_description' | 'financial_analysis' | 'market_analysis' | 'management' | 'investment_thesis';
  content: string;
  pageRange: [number, number];
  keyMetrics: Record<string, any>;
  relevanceScore: number;
}

interface RAGQuery {
  section: string;
  context: string;
  specificQuestions: string[];
}

interface RAGAnalysisResult {
  success: boolean;
  summary: string;
  analysisData: CIMReview;
  error?: string;
  processingTime: number;
  apiCalls: number;
}

class RAGDocumentProcessor {
  private sections: DocumentSection[] = [];

  private apiCallCount: number = 0;

  /**
   * Process CIM document using RAG approach
   */
  async processDocument(text: string, documentId: string): Promise<RAGAnalysisResult> {
    const startTime = Date.now();
    this.apiCallCount = 0;
    
    logger.info('Starting RAG-based CIM processing', { documentId });

    try {
      // Step 1: Intelligent document segmentation
      await this.segmentDocument(text);
      
      // Step 2: Extract key metrics and context
      await this.extractKeyMetrics();
      
      // Step 3: Generate comprehensive analysis using RAG
      const analysis = await this.generateRAGAnalysis();
      
      // Step 4: Create final summary
      const summary = await this.createFinalSummary(analysis);

      const processingTime = Date.now() - startTime;
      
      logger.info('RAG processing completed successfully', {
        documentId,
        processingTime,
        apiCalls: this.apiCallCount,
        sections: this.sections.length
      });

      return {
        success: true,
        summary,
        analysisData: analysis,
        processingTime,
        apiCalls: this.apiCallCount
      };

    } catch (error) {
      const processingTime = Date.now() - startTime;
      logger.error('RAG processing failed', {
        documentId,
        error: error instanceof Error ? error.message : 'Unknown error',
        processingTime,
        apiCalls: this.apiCallCount
      });

      return {
        success: false,
        summary: '',
        analysisData: {} as CIMReview,
        error: error instanceof Error ? error.message : 'Unknown error',
        processingTime,
        apiCalls: this.apiCallCount
      };
    }
  }

  /**
   * Segment document into logical sections with metadata
   */
  private async segmentDocument(text: string): Promise<void> {
    logger.info('Segmenting document into logical sections');
    
    // Use LLM to identify and segment document sections
    const segmentationPrompt = `
    Analyze this CIM document and identify its logical sections. For each section, provide:
    1. Section type (executive_summary, business_description, financial_analysis, market_analysis, management, investment_thesis)
    2. Start and end page numbers
    3. Key topics covered
    4. Relevance to investment analysis (1-10 scale)
    
    Document text:
    ${text.substring(0, 50000)} // First 50K chars for section identification
    
    Return as JSON array of sections.
    `;

    const segmentationResult = await this.callLLM({
      prompt: segmentationPrompt,
      systemPrompt: 'You are an expert at analyzing CIM document structure. Identify logical sections accurately.',
      maxTokens: 2000,
      temperature: 0.1
    });

    if (segmentationResult.success) {
      try {
        const sections = JSON.parse(segmentationResult.content);
        this.sections = sections.map((section: any, index: number) => ({
          id: `section_${index}`,
          type: section.type,
          content: this.extractSectionContent(text, section.pageRange),
          pageRange: section.pageRange,
          keyMetrics: {},
          relevanceScore: section.relevanceScore
        }));
      } catch (error) {
        logger.error('Failed to parse section segmentation', { error });
        // Fallback to rule-based segmentation
        this.sections = this.fallbackSegmentation(text);
      }
    }
  }

  /**
   * Extract key metrics from each section
   */
  private async extractKeyMetrics(): Promise<void> {
    logger.info('Extracting key metrics from document sections');
    
    for (const section of this.sections) {
      const metricsPrompt = `
      Extract key financial and business metrics from this section:
      
      Section Type: ${section.type}
      Content: ${section.content.substring(0, 10000)}
      
      Focus on:
      - Revenue, EBITDA, margins
      - Growth rates, market size
      - Customer metrics, employee count
      - Key risks and opportunities
      
      Return as JSON object.
      `;

      const metricsResult = await this.callLLM({
        prompt: metricsPrompt,
        systemPrompt: 'Extract precise numerical and qualitative metrics from CIM sections.',
        maxTokens: 1500,
        temperature: 0.1
      });

      if (metricsResult.success) {
        try {
          section.keyMetrics = JSON.parse(metricsResult.content);
        } catch (error) {
          logger.warn('Failed to parse metrics for section', { sectionId: section.id, error });
        }
      }
    }
  }

  /**
   * Generate analysis using RAG approach
   */
  private async generateRAGAnalysis(): Promise<CIMReview> {
    logger.info('Generating RAG-based analysis');
    
    // Create queries for each section of the BPCP template
    const queries: RAGQuery[] = [
      {
        section: 'dealOverview',
        context: 'Extract deal-specific information including company name, industry, geography, transaction details',
        specificQuestions: [
          'What is the target company name?',
          'What industry/sector does it operate in?',
          'Where is the company headquartered?',
          'What type of transaction is this?',
          'What is the stated reason for sale?'
        ]
      },
      {
        section: 'businessDescription',
        context: 'Analyze the company\'s core operations, products/services, and customer base',
        specificQuestions: [
          'What are the core operations?',
          'What are the key products/services?',
          'What is the revenue mix?',
          'Who are the key customers?',
          'What is the unique value proposition?'
        ]
      },
      {
        section: 'financialSummary',
        context: 'Extract and analyze financial performance, trends, and quality metrics',
        specificQuestions: [
          'What are the revenue trends?',
          'What are the EBITDA margins?',
          'What is the quality of earnings?',
          'What are the growth drivers?',
          'What is the working capital intensity?'
        ]
      },
      {
        section: 'marketIndustryAnalysis',
        context: 'Analyze market size, growth, competition, and industry trends',
        specificQuestions: [
          'What is the market size (TAM/SAM)?',
          'What is the market growth rate?',
          'Who are the key competitors?',
          'What are the barriers to entry?',
          'What are the key industry trends?'
        ]
      },
      {
        section: 'managementTeamOverview',
        context: 'Evaluate management team quality, experience, and post-transaction intentions',
        specificQuestions: [
          'Who are the key leaders?',
          'What is their experience level?',
          'What are their post-transaction intentions?',
          'How is the organization structured?'
        ]
      },
      {
        section: 'preliminaryInvestmentThesis',
        context: 'Develop investment thesis based on all available information',
        specificQuestions: [
          'What are the key attractions?',
          'What are the potential risks?',
          'What are the value creation levers?',
          'How does this align with BPCP strategy?'
        ]
      }
    ];

    const analysis: any = {};

    // Process each query using RAG
    for (const query of queries) {
      const relevantSections = this.findRelevantSections(query);
      const queryContext = this.buildQueryContext(relevantSections, query);
      
      const analysisResult = await this.callLLM({
        prompt: this.buildRAGPrompt(query, queryContext),
        systemPrompt: 'You are an expert investment analyst. Provide precise, structured analysis based on the provided context.',
        maxTokens: 2000,
        temperature: 0.1
      });

      if (analysisResult.success) {
        try {
          analysis[query.section] = JSON.parse(analysisResult.content);
        } catch (error) {
          logger.warn('Failed to parse analysis for section', { section: query.section, error });
        }
      }
    }

    return analysis as CIMReview;
  }

  /**
   * Find sections relevant to a specific query
   */
  private findRelevantSections(query: RAGQuery): DocumentSection[] {
    const relevanceMap: Record<string, string[]> = {
      dealOverview: ['executive_summary'],
      businessDescription: ['business_description', 'executive_summary'],
      financialSummary: ['financial_analysis', 'executive_summary'],
      marketIndustryAnalysis: ['market_analysis', 'executive_summary'],
      managementTeamOverview: ['management', 'executive_summary'],
      preliminaryInvestmentThesis: ['investment_thesis', 'executive_summary', 'business_description']
    };

    const relevantTypes = relevanceMap[query.section] || [];
    return this.sections.filter(section => 
      relevantTypes.includes(section.type) && section.relevanceScore >= 5
    );
  }

  /**
   * Build context for a specific query
   */
  private buildQueryContext(sections: DocumentSection[], query: RAGQuery): string {
    let context = `Query: ${query.context}\n\n`;
    context += `Specific Questions:\n${query.specificQuestions.map(q => `- ${q}`).join('\n')}\n\n`;
    context += `Relevant Document Sections:\n\n`;

    for (const section of sections) {
      context += `Section: ${section.type}\n`;
      context += `Relevance Score: ${section.relevanceScore}/10\n`;
      context += `Key Metrics: ${JSON.stringify(section.keyMetrics, null, 2)}\n`;
      context += `Content: ${section.content.substring(0, 5000)}\n\n`;
    }

    return context;
  }

  /**
   * Build RAG prompt for specific analysis
   */
  private buildRAGPrompt(query: RAGQuery, context: string): string {
    return `
    Based on the following context from a CIM document, provide a comprehensive analysis for the ${query.section} section.
    
    ${context}
    
    Please provide your analysis in the exact JSON format required for the BPCP CIM Review Template.
    Focus on answering the specific questions listed above.
    Use "Not specified in CIM" for any information not available in the provided context.
    `;
  }

  /**
   * Create final summary from RAG analysis
   */
  private async createFinalSummary(analysis: CIMReview): Promise<string> {
    logger.info('Creating final summary from RAG analysis');
    
    const summaryPrompt = `
    Create a comprehensive markdown summary from the following BPCP CIM analysis:
    
    ${JSON.stringify(analysis, null, 2)}
    
    Format as a professional BPCP CIM Review Template with proper markdown structure.
    `;

    const summaryResult = await this.callLLM({
      prompt: summaryPrompt,
      systemPrompt: 'Create a professional, well-structured markdown summary for BPCP investment committee.',
      maxTokens: 3000,
      temperature: 0.1
    });

    return summaryResult.success ? summaryResult.content : 'Summary generation failed';
  }

  /**
   * Fallback segmentation if LLM segmentation fails
   */
  private fallbackSegmentation(text: string): DocumentSection[] {
    // Rule-based segmentation as fallback
    const sections: DocumentSection[] = [];
    const patterns = [
      { type: 'executive_summary', pattern: /(?:executive\s+summary|overview|introduction)/i },
      { type: 'business_description', pattern: /(?:business\s+description|company\s+overview|operations)/i },
      { type: 'financial_analysis', pattern: /(?:financial|financials|performance|results)/i },
      { type: 'market_analysis', pattern: /(?:market|industry|competitive)/i },
      { type: 'management', pattern: /(?:management|leadership|team)/i },
      { type: 'investment_thesis', pattern: /(?:investment|opportunity|thesis)/i }
    ];

    // Simple text splitting based on patterns
    const textLength = text.length;
    const sectionSize = Math.floor(textLength / patterns.length);

    patterns.forEach((pattern, index) => {
      const start = index * sectionSize;
      const end = Math.min((index + 1) * sectionSize, textLength);
      
      sections.push({
        id: `section_${index}`,
        type: pattern.type as any,
        content: text.substring(start, end),
        pageRange: [Math.floor(start / 1000), Math.floor(end / 1000)],
        keyMetrics: {},
        relevanceScore: 7
      });
    });

    return sections;
  }

  /**
   * Extract content for specific page range
   */
  private extractSectionContent(text: string, pageRange: [number, number]): string {
    // Rough estimation: 1000 characters per page
    const startChar = pageRange[0] * 1000;
    const endChar = pageRange[1] * 1000;
    return text.substring(startChar, endChar);
  }

  /**
   * Wrapper for LLM calls to track API usage
   */
  private async callLLM(request: any): Promise<any> {
    this.apiCallCount++;
    return await llmService.processCIMDocument(request.prompt, '', {});
  }
}

export const ragDocumentProcessor = new RAGDocumentProcessor(); 