Spaces:
Sleeping
Sleeping
| import os | |
| from dotenv import load_dotenv | |
| from groq import Groq | |
| from rag_engine import ( | |
| search_relevant_chunks, | |
| generate_answer, | |
| generate_followup_questions | |
| ) | |
| load_dotenv() | |
| client = Groq(api_key=os.getenv("GROQ_API_KEY")) | |
| def analyze_question(question): | |
| prompt = f"""Analyze this question. | |
| Question: {question} | |
| Reply in this exact format only: | |
| TYPE: [simple/complex] | |
| NEEDS_COMPARISON: [yes/no]""" | |
| try: | |
| response = client.chat.completions.create( | |
| model="llama-3.3-70b-versatile", | |
| messages=[{"role": "user", "content": prompt}], | |
| temperature=0.1, | |
| max_tokens=50 | |
| ) | |
| return response.choices[0].message.content | |
| except Exception: | |
| return "TYPE: simple" | |
| def break_into_subquestions(question): | |
| prompt = f"""Break this question into 2-3 smaller sub-questions | |
| that can be answered from a PDF document. | |
| Only ask questions that can be found in documents. | |
| Do not ask personal questions. | |
| Question: {question} | |
| Reply with only the sub-questions, one per line. Nothing else.""" | |
| try: | |
| response = client.chat.completions.create( | |
| model="llama-3.3-70b-versatile", | |
| messages=[{"role": "user", "content": prompt}], | |
| temperature=0.1, | |
| max_tokens=200 | |
| ) | |
| subquestions = response.choices[0].message.content.strip().split('\n') | |
| return [q.strip() for q in subquestions if q.strip()] | |
| except Exception: | |
| return [question] | |
| def check_answer_quality(answer): | |
| prompt = f"""Does this answer contain actual information or does it say information is not available? | |
| Answer: {answer} | |
| Reply with only: FOUND or NOT_FOUND""" | |
| try: | |
| response = client.chat.completions.create( | |
| model="llama-3.3-70b-versatile", | |
| messages=[{"role": "user", "content": prompt}], | |
| temperature=0.1, | |
| max_tokens=10 | |
| ) | |
| return response.choices[0].message.content.strip() | |
| except Exception: | |
| return "FOUND" | |
| def run_agent(vector_store, question, pdf_names): | |
| # Step 1 β Adaptive behavior | |
| greetings = ["hi", "hello", "hey", "thanks", "thank you", "okay", "ok"] | |
| if question.lower().strip() in greetings: | |
| return "Please ask a question related to your uploaded PDFs!", [], [] | |
| try: | |
| # Step 2 β Decision making | |
| analysis = analyze_question(question) | |
| is_complex = "complex" in analysis.lower() | |
| if is_complex: | |
| # Step 3 β Break into sub-questions | |
| subquestions = break_into_subquestions(question) | |
| all_chunks = [] | |
| all_answers = [] | |
| # Step 4 β Multi-step execution | |
| for subq in subquestions: | |
| chunks = search_relevant_chunks(vector_store, subq, k=6) | |
| all_chunks.extend(chunks) | |
| answer, _ = generate_answer(subq, chunks, pdf_names) | |
| all_answers.append(f"**{subq}**\n{answer}") | |
| # Step 5 β Combine | |
| combined = "\n\n".join(all_answers) | |
| # Step 6 β Gap detection | |
| quality = check_answer_quality(combined) | |
| if quality == "NOT_FOUND": | |
| return "This information is not available in the uploaded documents.", all_chunks, [] | |
| # Step 7 β Follow-up questions | |
| followups = generate_followup_questions(question, combined) | |
| return combined, all_chunks, followups | |
| else: | |
| # Simple question | |
| chunks = search_relevant_chunks(vector_store, question, k=6) | |
| answer, _ = generate_answer(question, chunks, pdf_names) | |
| # Gap detection | |
| quality = check_answer_quality(answer) | |
| if quality == "NOT_FOUND": | |
| return "This information is not available in the uploaded documents.", chunks, [] | |
| # Follow-up questions | |
| followups = generate_followup_questions(question, answer) | |
| return answer, chunks, followups | |
| except Exception as e: | |
| return f"Something went wrong: {str(e)}", [], [] |