multiAgentai / app.py
GOKULSINGHSHAH123's picture
Update app.py
9df681f verified
from langgraph.graph import StateGraph, END
from typing import TypedDict, Annotated, List
import operator
from langgraph.checkpoint.sqlite import SqliteSaver
from langchain_core.messages import AnyMessage, SystemMessage, HumanMessage, AIMessage, ChatMessage
from langchain_google_genai import ChatGoogleGenerativeAI
from langchain_core.pydantic_v1 import BaseModel
import os
import gradio as gr
from langgraph.graph import StateGraph, END
from typing import TypedDict, List
from langgraph.checkpoint.sqlite import SqliteSaver
from langchain_core.messages import SystemMessage, HumanMessage
from langchain_openai import ChatOpenAI
from langchain_core.pydantic_v1 import BaseModel
from tavily import TavilyClient
memory = SqliteSaver.from_conn_string(":memory:")
class AgentState(TypedDict):
task: str
plan: str
draft: str
critique: str
content: List[str]
revision_number: int
max_revisions: int
from langchain_openai import ChatOpenAI
try:
model = ChatGoogleGenerativeAI(model="gemini-1.5-pro-latest", google_api_key="AIzaSyD8EQItv3a2p9PNpdgf4nK7vLStWuzwAcg", convert_system_message_to_human=True, temperature=0.6)
except Exception as e:
print("Error",e)
PLAN_PROMPT = """You are an experienced writer tasked with drafting a highly detailed and comprehensive outline for a research report. Your goal is to create an exceptionally structured outline for the user's chosen topic, ensuring it encourages an in-depth examination of recent trends, specific advancements, technical details, and future research directions.
**Outline Requirements:**
1. **Executive Summary:**
- Summarize key findings, significance, and implications.
- Highlight main conclusions and recommendations.
2. **Introduction:**
- Provide background on the topic.
- State research questions or hypotheses.
- Define the scope and objectives of the report.
3. **Recent Trends and Advancements:**
-give resposne according to users topic
4. **Integration of Technologies:**
- Discuss how these technologies intersect and enhance each other.
- Provide examples of synergistic effects and combined applications.
- Address integration challenges and potential solutions.
5. **Privacy and Security Challenges:**
- Identify key privacy and security issues.
- Discuss mitigation strategies and best practices.
- Explore ethical considerations related to these technologies.
6. **Case Studies:**
- Include detailed case studies with specific examples.
- Analyze real-world applications and their outcomes.
- Discuss lessons learned and best practices from each case study.
7. **Future Research Directions:**
- Propose areas for further investigation and development.
- Highlight emerging trends and technologies.
- Discuss potential impact and applications of future research.
8. **Conclusions:**
- Summarize main findings and insights.
- Reflect on the implications for researchers and practitioners.
- Provide actionable recommendations and future outlook.
9. **References:**
- Include a comprehensive list of recent research papers, articles, and other relevant sources.
- Ensure accurate and complete citations to support the analysis.
**Additional Instructions:**
- Break down complex topics into clear sub-sections.
- Ensure each section transitions smoothly to the next.
- Use visual aids where applicable (e.g., charts, graphs, tables).
- Address privacy and security systematically throughout the report.
"""
WRITER_PROMPT = """You are an essay assistant specializing in research reports. Produce a comprehensive research report based on the provided outline and user's requirements. Your report should cover recent trends, specific advancements, technical details, and future research directions in depth.
**Report Requirements:**
1. **Executive Summary:**
- Summarize key findings, significance, and implications.
- Ensure clarity and brevity while covering essential points.
2. **Introduction:**
- Provide detailed background and context.
- State and elaborate on research questions or hypotheses.
3. **Recent Trends and Advancements:**
- Present detailed and up-to-date information on each technology.
- Use concrete examples and recent data to support your analysis.
4. **Integration of Technologies:**
- Discuss how technologies intersect and enhance each other.
- Include specific examples of successful integration and its benefits.
5. **Privacy and Security Challenges:**
- Thoroughly address potential privacy and security issues.
- Provide a balanced view of potential solutions and ongoing research.
6. **Case Studies:**
- Include detailed, well-researched case studies.
- Provide concrete examples and analyze outcomes and lessons learned.
7. **Future Research Directions:**
- Propose and justify areas for further investigation.
- Discuss potential future applications and their significance.
8. **Conclusions:**
- Summarize key insights and recommendations clearly.
- Ensure the conclusions reflect the report’s findings and implications.
9. **References:**
- Accurately cite recent research papers and relevant sources.
- Ensure all references are credible and support the report’s content.
**Additional Instructions:**
- Maintain a clear and logical flow throughout the report.
- Use visual aids to present data effectively.
- Ensure smooth transitions between sections for readability.
- Provide a critical analysis of various perspectives.
{content}
"""
REFLECTION_PROMPT = """You are a seasoned educator evaluating an essay submission. Provide constructive feedback on the user's research report, focusing on depth, comprehensiveness, and clarity.
**Evaluation Criteria:**
1. **Coverage of Recent Trends and Advancements:**
- Assess how well the report addresses recent trends and specific advancements.
- Check for detailed and accurate information on each technology.
2. **Integration and Synergies:**
- Evaluate how effectively the report discusses the integration of technologies and their synergies.
- Look for examples and explanations of how these technologies enhance each other.
3. **Privacy and Security Challenges:**
- Assess the depth of discussion on privacy and security challenges.
- Evaluate the effectiveness of proposed solutions and mitigation strategies.
4. **Case Studies and Real-World Applications:**
- Review the inclusion and analysis of case studies.
- Check for relevance, detail, and real-world applicability of examples.
5. **Future Research Directions:**
- Evaluate the clarity and feasibility of proposed future research directions.
- Assess the potential impact and significance of these directions.
6. **References and Citations:**
- Ensure that the report includes accurate and comprehensive citations.
- Review the relevance and credibility of referenced sources.
**Recommendations:**
- Provide specific suggestions for improving depth and clarity.
- Highlight any gaps or areas needing further development.
- Suggest ways to enhance readability and logical flow.
"""
RESEARCH_PLAN_PROMPT = """As a researcher, your task is to generate effective search queries to gather comprehensive information for the upcoming research report. Provide up to 4 targeted queries to obtain the most relevant and recent data.
**Search Queries:**
1. **Latest Developments in [Technology]:** Focus on recent advancements and breakthroughs in the technology related to your report.
2. **Technical Details and Innovations:** Seek detailed technical information and innovations for the technology in question.
3. **Case Studies and Real-World Applications:** Find concrete examples and case studies that demonstrate the application of the technology.
4. **Integration and Privacy/Security Challenges:** Explore how different technologies integrate, their potential synergies, and address privacy/security challenges.
**Instructions:**
- Use credible sources and evaluate the relevance of the information.
- Ensure queries are specific to the technology and research focus.
- Gather information that supports a thorough and comprehensive analysis.
"""
RESEARCH_CRITIQUE_PROMPT = """You are tasked with gathering updated information to assist in revising the research report. Generate up to 3 focused search queries to find the most relevant and recent data.
**Search Queries:**
1. **Recent Trends in [Technology]:** Identify the latest trends and advancements in the technology relevant to the report.
2. **Detailed Technical Insights:** Obtain detailed technical information and recent innovations for a thorough understanding.
3. **Privacy and Security Challenges:** Find updated discussions on privacy and security challenges related to integrating the technologies.
**Instructions:**
- Ensure the queries target high-quality and credible sources.
- Focus on obtaining comprehensive and relevant data.
- Evaluate the information for its relevance and contribution to the report.
"""
class Queries(BaseModel):
queries: List[str]
client = TavilyClient(api_key="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")
def plan_node(state: AgentState):
print("reached planner node")
messages = [
SystemMessage(content=PLAN_PROMPT),
HumanMessage(content=state['task'])
]
response = model.invoke(messages)
return {"plan": response.content}
def research_plan_node(state: AgentState):
print("reached research_plan_node")
# Send messages to the model without structured output
messages = [
SystemMessage(content=RESEARCH_PLAN_PROMPT),
HumanMessage(content=state['task'])
]
try:
response = model.invoke(messages)
# Extract the text content from the response
response_text = response.content if hasattr(response, 'content') else str(response)
# Parse the queries from the text content
queries_list = parse_queries_from_content(response_text)
print("parsed queries list", queries_list)
# Perform search based on extracted queries
content = state['content'] or []
for q in queries_list:
response = client.search(query=q, max_results=2)
for r in response['results']:
content.append(r['content'])
return {"content": content}
except Exception as e:
print(f"An error occurred: {e}")
return {"content": state['content']}
def parse_queries_from_content(content: str):
# Split the content by newlines
lines = content.split('\n')
# Filter out empty lines and extract queries
queries = [line.strip() for line in lines if line.strip()]
# Remove numbering and quotes if needed
queries = [q.split('. ', 1)[-1].strip('"') for q in queries]
return queries
def generation_node(state: AgentState):
print("reached generation_node")
content = "\n\n".join(state['content'] or [])
user_message = HumanMessage(
content=f"{state['task']}\n\nHere is my plan:\n\n{state['plan']}")
messages = [
SystemMessage(
content=WRITER_PROMPT.format(content=content)
),
user_message
]
response = model.invoke(messages)
return {
"draft": response.content,
"revision_number": state.get("revision_number", 1) + 1
}
def reflection_node(state: AgentState):
print("reached reflection_node")
messages = [
SystemMessage(content=REFLECTION_PROMPT),
HumanMessage(content=state['draft'])
]
response = model.invoke(messages)
return {"critique": response.content}
def research_critique_node(state: AgentState):
print("reached research_critique_node")
# Send messages to the model without structured output
messages = [
SystemMessage(content=RESEARCH_CRITIQUE_PROMPT),
HumanMessage(content=state['critique'])
]
print("passed 1")
try:
response = model.invoke(messages)
print("passed 2")
# Extract content from the response
response_content = response.content if hasattr(response, 'content') else str(response)
print("queries are", response_content)
# Parse queries from the response content
queries_list = parse_queries_from_text(response_content)
print("queries_list", queries_list)
# Perform search based on extracted queries
content = state['content'] or []
for q in queries_list:
response = client.search(query=q, max_results=2)
for r in response['results']:
content.append(r['content'])
return {"content": content}
except Exception as e:
print(f"An error occurred: {e}")
return {"content": state['content']}
def parse_queries_from_text(text):
print(text)
# Assuming the queries are separated by new lines and potentially prefixed by numbers or bullet points
lines = text.split('\n')
# Clean up and filter out empty lines
queries = [line.strip() for line in lines if line.strip()]
# If needed, remove numbering or bullet points
queries = [q.split('. ', 1)[-1].strip('"') for q in queries]
return queries
def should_continue(state):
if state["revision_number"] > state["max_revisions"]:
return END
return "reflect"
builder = StateGraph(AgentState)
builder.add_node("planner", plan_node)
builder.add_node("generate", generation_node)
builder.add_node("reflect", reflection_node)
builder.add_node("research_plan", research_plan_node)
builder.add_node("research_critique", research_critique_node)
builder.set_entry_point("planner")
builder.add_conditional_edges(
"generate",
should_continue,
{END: END, "reflect": "reflect"}
)
builder.add_edge("planner", "research_plan")
builder.add_edge("research_plan", "generate")
builder.add_edge("reflect", "research_critique")
builder.add_edge("research_critique", "generate")
graph = builder.compile(checkpointer=memory)
# (Include all the existing code for AgentState, prompts, and node functions here)
# ... (keep all the existing code up to the graph compilation)
graph = builder.compile(checkpointer=memory)
def process_essay(task, max_revisions):
thread = {"configurable": {"thread_id": "1"}}
results = []
for s in graph.stream({
'task': task,
"max_revisions": max_revisions,
"revision_number": 1,
}, thread):
results.append(s)
return results
def extract_agent_outputs(results):
plan_output = ""
research_output = ""
generation_output = ""
reflection_output = ""
final_essay = ""
for step in results:
if 'planner' in step:
plan_output += f"Plan:\n{step['planner']['plan']}\n\n"
if 'research_plan' in step or 'research_critique' in step:
research_key = 'research_plan' if 'research_plan' in step else 'research_critique'
research_output += f"Research Queries:\n{step[research_key]['content']}\n\n"
if 'generate' in step:
generation_output += f"Draft (Revision {step['generate']['revision_number']}):\n{step['generate']['draft']}\n\n"
final_essay = step['generate']['draft'] # Update final essay
if 'reflect' in step:
reflection_output += f"Critique:\n{step['reflect']['critique']}\n\n"
return plan_output, research_output, generation_output, reflection_output, final_essay
graph = builder.compile(checkpointer=SqliteSaver.from_conn_string(":memory:"))
# Define functions for Gradio
def process_essay(task, max_revisions):
thread = {"configurable": {"thread_id": "1"}}
results = []
for s in graph.stream({
'task': task,
"max_revisions": max_revisions,
"revision_number": 1,
}, thread):
results.append(s)
return results
def extract_agent_outputs(results):
plan_output = ""
research_output = ""
generation_output = ""
reflection_output = ""
final_essay = ""
for step in results:
print("Processing step:", step) # Debug line
if 'planner' in step:
plan_output += f"Plan:\n{step['planner']['plan']}\n\n"
if 'research_plan' in step or 'research_critique' in step:
research_key = 'research_plan' if 'research_plan' in step else 'research_critique'
if step[research_key]:
research_output += f"Research Queries:\n{step[research_key]['content']}\n\n"
else:
research_output += f"Research Queries:\nNo content found.\n\n"
if 'generate' in step:
generation_output += f"Draft (Revision {step['generate']['revision_number']}):\n{step['generate']['draft']}\n\n"
final_essay = step['generate']['draft'] # Update final essay
if 'reflect' in step:
if step['reflect']:
reflection_output += f"Critique:\n{step['reflect']['critique']}\n\n"
else:
reflection_output += f"Critique:\nNo critique found.\n\n"
return plan_output, research_output, generation_output, reflection_output, final_essay
def gradio_interface(task, max_revisions):
results = process_essay(task, max_revisions)
plan, research, generation, reflection, final_essay = extract_agent_outputs(results)
return final_essay, plan, research, generation, reflection
# Create and launch Gradio interface
iface = gr.Interface(
fn=gradio_interface,
inputs=[
gr.Textbox(label="Report Topic", placeholder="Enter the report topic or task here"),
gr.Slider(minimum=1, maximum=5, step=1, label="Max Revisions", value=2)
],
outputs=[
gr.Textbox(label="Final Report"),
gr.Textbox(label="Planning Output", lines=10),
gr.Textbox(label="Research Output", lines=10),
gr.Textbox(label="Generation Output", lines=10),
gr.Textbox(label="Reflection Output", lines=10)
],
title="Multi-Agent Report Writing System",
description="This system uses multiple AI agents to plan, research, write, and revise an research report on the given topic."
)
iface.launch()