AnukulChandra/Mini-AI_Assistant
0
1import logging2 3from fastapi import APIRouter, HTTPException4from pydantic import BaseModel5 6from services.llm import generate_response7from services.memory import add_to_memory, get_history8from services.prompt_builder import build_prompt9from services.retrieval import retrieve_context10from services.tools import detect_intent11 12logger = logging.getLogger(__name__)13 14router = APIRouter(prefix="/chat")15 16 17class QuestionRequest(BaseModel):18 question: str19 20 21def _build_history() -> str:22 questions, answers = get_history()23 if not questions:24 return ""25 26 lines = ["Previous conversation:"]27 for q, a in zip(questions, answers):28 lines.append(f"User: {q}")29 lines.append(f"Assistant: {a}")30 31 return "\n".join(lines)32 33 34@router.post("/ask")35async def ask_question(body: QuestionRequest):36 history = _build_history()37 38 intent, tool_result = None, None39 try:40 intent, tool_result = detect_intent(body.question)41 except Exception as e:42 logger.warning("Intent detection failed: %s", e)43 44 if intent == "order":45 logger.info("Detected intent: ORDER")46 status = tool_result.get("status", "unknown").capitalize()47 delivery = tool_result.get("estimated_delivery", "N/A")48 answer = f"Order {tool_result['order_id']} is {status}. Estimated delivery: {delivery}."49 add_to_memory(body.question, answer)50 return {51 "type": "order",52 "answer": answer,53 "data": tool_result,54 }55 56 if intent == "product":57 logger.info("Detected intent: PRODUCT")58 if isinstance(tool_result, list) and len(tool_result) > 0:59 product = tool_result[0]60 name = product.get("name", "Unknown")61 price = product.get("price", 0)62 stock = product.get("stock", 0)63 answer = f"{name} costs ${price} and {stock} units are in stock."64 else:65 answer = "No product found."66 add_to_memory(body.question, answer)67 return {68 "type": "product",69 "answer": answer,70 "data": tool_result if isinstance(tool_result, list) else [tool_result],71 }72 73 if history:74 logger.info("Detected intent: MEMORY")75 76 chunks = []77 try:78 chunks = retrieve_context(body.question)79 if chunks:80 logger.info("Detected intent: KNOWLEDGE")81 except ValueError as e:82 logger.info("No vector store available, proceeding without RAG context: %s", e)83 84 prompt = build_prompt(body.question, chunks, history)85 86 try:87 answer = generate_response(prompt)88 except ValueError as e:89 raise HTTPException(status_code=400, detail=str(e))90 91 add_to_memory(body.question, answer)92 93 return {94 "type": "knowledge",95 "answer": answer,96 "retrieved_chunks": chunks,97 }