""" Autonomous Response Enhancer - 100% LLM-Driven =============================================== NO hardcoded enhancements! Everything is generated by LLM dynamically. Features: - Autonomous insight generation - Dynamic follow-up suggestions - Context-aware tone adjustment - Data-specific formatting """ import json import logging from typing import Dict, List, Optional from core.llm import chat logger = logging.getLogger(__name__) def extract_data_summary_from_response(response: str, currency_symbol: str = "$") -> Dict: """ Extract data summary autonomously using LLM. """ try: prompt = f"""Analyze this data analysis response and extract key metrics. RESPONSE: "{response[:600]}" Return JSON with extracted data: {{ "key_numbers": ["list of important numbers found"], "percentages": ["any percentages mentioned"], "entities": ["entities/names mentioned"], "main_finding": "one sentence summary of main finding" }} JSON:""" result = chat(prompt, temperature=0.1, max_tokens=150) # Parse JSON result = result.strip() if '```' in result: result = result.split('```')[1] if result.startswith('json'): result = result[4:] start = result.find('{') end = result.rfind('}') + 1 if start >= 0 and end > start: result = result[start:end] return json.loads(result) except: return {"key_numbers": [], "percentages": [], "entities": [], "main_finding": ""} def enhance_with_insight( response: str, query: str, data_context: str = "" ) -> str: """ Add insight fully autonomously - NO hardcoded patterns! """ if len(response) < 100 or "💡" in response: return response try: prompt = f"""Based on this data analysis, generate ONE specific insight. QUERY: {query} RESPONSE: {response[:500]} The insight should be: - Specific to THIS data (not generic advice) - Start with 💡 - Be 1-2 sentences max - Provide actionable or surprising information Generate the insight (just the insight text, starting with 💡):""" insight = chat(prompt, temperature=0.7, max_tokens=80) insight = insight.strip() if insight and len(insight) > 10: return response + f"\n\n{insight}" except Exception as e: logger.debug(f"Insight generation error: {e}") return response def enhance_with_suggestions( response: str, query: str, columns: List[str] = None ) -> str: """ Add follow-up suggestions fully autonomously - NO hardcoding! """ if len(response) < 100 or "You might also" in response: return response try: prompt = f"""Based on this analysis, suggest 2 natural follow-up questions. QUERY: {query} RESPONSE: {response[:400]} DATA COLUMNS: {columns or "Unknown"} Generate exactly 2 follow-up questions that would be logical next steps. Format as: 1. [first question] 2. [second question] Questions:""" result = chat(prompt, temperature=0.7, max_tokens=100) # Parse questions lines = result.strip().split('\n') questions = [] for line in lines: line = line.strip() if line and (line[0].isdigit() or line.startswith('-') or line.startswith('•')): # Remove numbering q = line.lstrip('0123456789.-•) ').strip() if q and len(q) > 5: questions.append(q) if questions: suggestion_text = "\n\n---\n**You might also ask:**\n" for q in questions[:2]: suggestion_text += f"• {q}\n" return response + suggestion_text except Exception as e: logger.debug(f"Suggestion generation error: {e}") return response def enhance_tone(response: str, query: str) -> str: """ Enhance tone autonomously - NO hardcoded replacements! """ # Only enhance longer responses if len(response) < 200: return response # Check if tone seems robotic robotic_indicators = ['Based on the data provided', 'According to the information', 'It can be observed', 'The analysis indicates'] needs_enhancement = any(ind in response for ind in robotic_indicators) if not needs_enhancement: return response try: prompt = f"""Rewrite this response to be more natural and conversational, like ChatGPT. Keep all the data and facts exactly the same. Just make the tone warmer and more engaging. ORIGINAL RESPONSE: {response[:800]} REWRITTEN (keep same facts, warmer tone):""" enhanced = chat(prompt, temperature=0.5, max_tokens=800) if enhanced and len(enhanced) > len(response) * 0.5: return enhanced.strip() except: pass return response def enhance_full_response( query: str, response: str, query_type: str = "general", data_summary: Dict = None, entities: List[str] = None, add_insight: bool = True, add_suggestions: bool = True, enhance_tone_flag: bool = True, currency_symbol: str = "$", domain: str = "general", columns: List[str] = None ) -> str: """ Fully autonomous response enhancement. NO hardcoded patterns - everything LLM-driven! """ enhanced = response # Enhance tone first if enhance_tone_flag: enhanced = enhance_tone(enhanced, query) # Add autonomous insight if add_insight: enhanced = enhance_with_insight(enhanced, query) # Add autonomous suggestions if add_suggestions: enhanced = enhance_with_suggestions(enhanced, query, columns) return enhanced def generate_autonomous_summary( data_context: str, columns: List[str], num_rows: int ) -> str: """ Generate data summary fully autonomously. """ try: prompt = f"""Generate a brief, helpful summary of this dataset. COLUMNS: {columns} ROWS: {num_rows} SAMPLE DATA: {data_context[:500]} Generate 2-3 sentences describing: 1. What kind of data this is 2. What analysis would be valuable Summary:""" result = chat(prompt, temperature=0.5, max_tokens=150) return result.strip() except: return f"Dataset with {num_rows} rows and {len(columns)} columns."