File size: 7,941 Bytes
b7441eb 9730fbc b7441eb f317ea3 b7441eb f317ea3 b7441eb |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 |
"""
Emergency chat endpoint - Minimal dependencies, maximum reliability
This endpoint ensures the chat always works, even if other services fail
"""
import os
from src.core import json_utils
from datetime import datetime
from typing import Dict, Any, Optional, List
from fastapi import APIRouter, HTTPException
from pydantic import BaseModel, Field
import httpx
import random
from src.core import get_logger
logger = get_logger(__name__)
router = APIRouter(prefix="/api/v1/chat", tags=["chat-emergency"])
# Request/Response models
class ChatRequest(BaseModel):
message: str = Field(..., min_length=1, max_length=1000)
session_id: Optional[str] = None
class ChatResponse(BaseModel):
session_id: str
agent_id: str = "assistant"
agent_name: str = "Assistente Cidadão.AI"
message: str
confidence: float = 0.95
suggested_actions: List[str] = []
metadata: Dict[str, Any] = {}
# Professional responses for common queries
RESPONSES = {
"greeting": [
"Olá! Sou o assistente do Cidadão.AI. Estou aqui para ajudar você a entender e investigar gastos públicos. Como posso ajudar?",
"Bem-vindo ao Cidadão.AI! Posso ajudar você a analisar contratos, investigar gastos e entender melhor a transparência pública.",
"Oi! Sou especializado em transparência pública. Posso investigar contratos, analisar gastos governamentais e muito mais. O que você gostaria de saber?"
],
"investigation": [
"Vou ajudar você a investigar. Posso analisar:\n• Contratos e licitações\n• Gastos por órgão público\n• Pagamentos a fornecedores\n• Evolução temporal de despesas\n\nQual área específica você quer investigar?",
"Entendi que você quer investigar gastos públicos. Tenho acesso a dados de contratos, fornecedores e órgãos públicos. Por onde gostaria de começar?",
"Perfeito! Posso investigar contratos suspeitos, analisar padrões de gastos e identificar anomalias. Me dê mais detalhes sobre o que você procura."
],
"help": [
"Posso ajudar você com:\n\n📊 **Análise de Contratos**: Investigar licitações e contratos públicos\n💰 **Gastos Públicos**: Acompanhar despesas governamentais\n🔍 **Detecção de Anomalias**: Identificar padrões irregulares\n📈 **Relatórios**: Gerar análises detalhadas\n\nO que você gostaria de fazer?",
"O Cidadão.AI oferece várias funcionalidades:\n• Investigar contratos específicos\n• Analisar gastos de órgãos públicos\n• Comparar fornecedores\n• Detectar anomalias em pagamentos\n• Gerar relatórios de transparência\n\nComo posso ajudar?",
"Aqui está o que posso fazer por você:\n1. Buscar informações sobre contratos\n2. Analisar tendências de gastos\n3. Identificar fornecedores frequentes\n4. Detectar possíveis irregularidades\n5. Criar visualizações de dados\n\nQual dessas opções te interessa?"
],
"default": [
"Entendi sua pergunta. Para te ajudar melhor com transparência pública, você pode:\n• Pedir para investigar contratos específicos\n• Solicitar análise de gastos de um órgão\n• Buscar informações sobre fornecedores\n\nComo posso ajudar?",
"Interessante sua questão! No contexto de transparência pública, posso ajudar você a entender gastos governamentais, contratos e licitações. Que tipo de informação você procura?",
"Certo! Como assistente de transparência, posso investigar dados públicos, analisar contratos e identificar padrões. Me conte mais sobre o que você quer descobrir."
]
}
def detect_intent(message: str) -> str:
"""Simple intent detection based on keywords"""
message_lower = message.lower()
if any(word in message_lower for word in ["olá", "oi", "bom dia", "boa tarde", "boa noite", "prazer"]):
return "greeting"
elif any(word in message_lower for word in ["investigar", "verificar", "analisar", "buscar", "procurar"]):
return "investigation"
elif any(word in message_lower for word in ["ajuda", "ajudar", "pode", "consegue", "o que", "como"]):
return "help"
else:
return "default"
async def try_maritaca(message: str) -> Optional[str]:
"""Try to get response from Maritaca AI"""
api_key = os.getenv("MARITACA_API_KEY")
if not api_key:
return None
try:
async with httpx.AsyncClient(timeout=10.0) as client:
response = await client.post(
"https://chat.maritaca.ai/api/chat/inference",
headers={"authorization": f"Bearer {api_key}"},
json={
"messages": [
{
"role": "system",
"content": "Você é um assistente especializado em transparência pública brasileira. Ajude os cidadãos a entender gastos governamentais, contratos e licitações. Seja claro, objetivo e sempre sugira ações específicas."
},
{"role": "user", "content": message}
],
"model": "sabiazinho-3",
"temperature": 0.7,
"max_tokens": 400
}
)
if response.status_code == 200:
data = response.json()
return data.get("answer", None)
except Exception as e:
logger.warning(f"Maritaca request failed: {e}")
return None
@router.post("/emergency", response_model=ChatResponse)
async def chat_emergency(request: ChatRequest) -> ChatResponse:
"""
Emergency chat endpoint - Always returns a valid response
Tries Maritaca AI first, falls back to intelligent responses
"""
session_id = request.session_id or f"emergency_{datetime.now().timestamp()}"
# Try Maritaca first
maritaca_response = await try_maritaca(request.message)
if maritaca_response:
return ChatResponse(
session_id=session_id,
agent_id="maritaca",
agent_name="Assistente Cidadão.AI (Maritaca)",
message=maritaca_response,
confidence=0.95,
suggested_actions=["investigate_contracts", "analyze_expenses", "generate_report"],
metadata={
"model": "sabiazinho-3",
"backend": "maritaca_ai",
"timestamp": datetime.utcnow().isoformat()
}
)
# Fallback to intelligent responses
intent = detect_intent(request.message)
response_list = RESPONSES.get(intent, RESPONSES["default"])
selected_response = random.choice(response_list)
# Determine suggested actions based on intent
if intent == "greeting":
actions = ["start_investigation", "view_recent_contracts", "help"]
elif intent == "investigation":
actions = ["search_contracts", "analyze_supplier", "view_timeline"]
elif intent == "help":
actions = ["examples", "start_investigation", "documentation"]
else:
actions = ["help", "start_investigation", "search"]
return ChatResponse(
session_id=session_id,
agent_id="system",
agent_name="Assistente Cidadão.AI",
message=selected_response,
confidence=0.85,
suggested_actions=actions,
metadata={
"backend": "intelligent_fallback",
"intent": intent,
"timestamp": datetime.utcnow().isoformat()
}
)
@router.get("/emergency/health")
async def emergency_health():
"""Health check for emergency endpoint"""
maritaca_available = bool(os.getenv("MARITACA_API_KEY"))
return {
"status": "operational",
"endpoint": "/api/v1/chat/emergency",
"maritaca_configured": maritaca_available,
"fallback_ready": True,
"timestamp": datetime.utcnow().isoformat()
} |