AI Agents
The complete guide
From the ReAct Loop to Multi-Agent Systems — everything you need to know to build autonomous digital workers with Python, CrewAI and LangGraph.
On model versions: the code on this page pins gpt-4o, claude-sonnet-5. As of September 2026 providers retire versions and model names change — check the current model list in OpenAI and Anthropic's documentation and swap the string before running. What the code demonstrates does not depend on the version. And on prices: vendor pricing changes often and the figures on this page are not checked automatically. Confirm the current price on the vendor's own pricing page before deciding.
What is an AI Agent?
When you use ChatGPT and ask a question, you get an answer — and that's it. The model takes input, produces output, and it's done. That's a basic language model (LLM). An AI Agent is fundamentally different: it doesn't just answer questions — it plans, decides, invokes external tools, and reacts to the results in an autonomous loop until a goal is reached.
The best way to picture an Agent is as an"autonomous digital worker". Say you ask an Agent to research a market and prepare a report. It will plan the task, search for information online, read files, analyze data, write results to a file, and return an organized report — all without you having to manage each step.
The heart of every Agent is the ReAct loop (Reasoning + Acting): the model thinks about what to do (Thought), performs an action (Action), sees the result (Observation), and then thinks again — until the task is complete. This loop is what distinguishes an Agent from a simple LLM.
Thought: "I need to look up Apple's stock price" → Action: web_search("AAPL stock price") → Observation: "185.20$" → Thought: "Now I can calculate the return" → ...
How does an Agent work? — the components
A modern Agent is made of four main components that work together. Each is essential for true autonomous operation.
1. LLM — the brain
The model itself (GPT-4o, Claude Sonnet, Gemini Pro, etc.) is the decision engine. It reads the current context — goal, memory, previous tool results — and decides the next action. The LLM doesn't "know" how to use tools on its own; what enables that is the Function Calling (or Tool Use) mechanism, which adds tool descriptions to the System Prompt and prompts the model to produce structured output.
2. Tools — the hands
Without Tools, an Agent is just an LLM. Tools are the functions the Agent can call: internet search, running Python code, reading and writing files, sending HTTP requests, SQL queries, sending emails and more. Each Tool is defined with a name, a description, and the parameters it accepts — and the model automatically chooses when and how to call it.
3. Memory
Short-term memory is the Conversation History kept in the Context Window. Long-term memory is information stored outside the Context — usually in a Vector Store like Pinecone or Chroma — and retrieved by relevance when needed. An Agent that wants to "remember" information across different conversations must use Long-term memory.
4. Planning
Complex tasks require breaking down into subtasks. Planning mechanisms like Task Decomposition let the Agent take a broad goal ("write a competitive analysis of the cybersecurity market") and break it into actionable steps. Frameworks like LangGraph and CrewAI add a structured planning layer on top of the LLM.
| Component | Role | Technology examples |
|---|---|---|
| LLM (brain) | Decision-making, reasoning | GPT-4o, Claude, Gemini |
| Tools (hands) | Interaction with the world | Search, Code, APIs, Files |
| Memory | Keeping context and information | Conversation, Vector Store |
| Planning | Breaking down complex tasks | CrewAI, LangGraph, ToT |
Types of Agents — when to use each
Not every Agent is built the same way. There are four main archetypes, each suited to a different kind of task.
| Agent type | When to use | Examples |
|---|---|---|
| ReAct Agent | General tasks with varied tools, search, calculations | Research assistant, Q&A bot |
| Tool Calling Agent | When there is a well-defined tool set and structured output is required | API integrations, CRM bots |
| Plan-and-Execute | Long, complex tasks requiring upfront planning | Writing reports, market analysis |
| Multi-Agent | When a task is too big for a single Agent, or expertise is needed | CrewAI pipelines, AutoGen |
ReAct Agent is the most flexible type and suits most cases. It runs in a Thought-Action-Observation loop and fits when the task isn't known in advance. Tool Calling Agent is more defined — the model chooses from a known list of Tools and returns structured JSON. Plan-and-Execute fits when work can be planned in advance: one Agent creates a plan, a separate Agent executes each step. Multi-Agent is an architecture where several Agents work together — each with a defined role, with a Crew Manager coordinating them.
CrewAI — a Framework for Multi-Agent Systems
CrewAI is the most popular Framework for building Multi-Agent systems in Python. The idea is simple: you define a "Crew" of Agents, each with a role and goal, and define tasks (Tasks). The Framework manages the communication between them.
Installation
pip install crewai crewai-tools
CrewAI's four core components
- Agent: a worker with a role, goal, and a backstory that shapes its behavior
- Task: a defined task with a description, expected output, and the Agent responsible for it
- Crew: the crew — connects Agents and Tasks, manages the execution order
- Process: sequential (each Agent waits for the previous one) or hierarchical (a Manager distributes the work)
A full example — a Crew for writing an article
Here is a Crew of three Agents working together to produce a professional article: a Researcher that gathers information, a Writer that writes, and an Editor that improves it.
from crewai import Agent, Task, Crew, Process
from crewai_tools import SerperDevTool
# search tool (requires SERPER_API_KEY)
search_tool = SerperDevTool()
# --- defining Agents ---
researcher = Agent(
role="Senior Research Analyst",
goal="Search for up-to-date, reliable information on the topic you are given",
backstory="""You are a senior research analyst with 10 years of experience.
You know how to find reliable sources and filter for relevant information.""",
tools=[search_tool],
verbose=True,
llm="gpt-4o"
)
writer = Agent(
role="Content Writer",
goal="Write a deep, engaging and accurate article based on the research",
backstory="""You are an experienced content writer who specializes in making
technical topics accessible to a broad audience. Your style is clear and persuasive.""",
verbose=True,
llm="gpt-4o"
)
editor = Agent(
role="Chief Editor",
goal="Edit the article, improve the flow and clarity, fix errors",
backstory="""You are a chief editor with a sharp eye for detail.
You make sure every article meets the highest standards.""",
verbose=True,
llm="gpt-4o"
)
# --- defining Tasks ---
research_task = Task(
description="Research the topic in depth: {topic}. Gather up-to-date data, statistics and examples.",
expected_output="A detailed research report with at least 5 reliable data points",
agent=researcher
)
write_task = Task(
description="Write an 800-1000 word article based on the research. Include a title, introduction, body, and conclusion.",
expected_output="A complete, formatted article in Markdown",
agent=writer,
context=[research_task] # receives the output of research_task
)
edit_task = Task(
description="Edit the article: improve the wording, verify facts, add subheadings if needed.",
expected_output="A final article ready for publication",
agent=editor,
context=[write_task]
)
# --- running the Crew ---
crew = Crew(
agents=[researcher, writer, editor],
tasks=[research_task, write_task, edit_task],
process=Process.sequential,
verbose=True
)
result = crew.kickoff(inputs={"topic": "The impact of AI Agents on the job market in 2026"})
print(result)
You can replace Process.sequential with Process.hierarchical and define manager_llm="gpt-4o". The Manager will distribute the work to the Agents dynamically as needed — useful when the number of tasks isn't known in advance.
LangGraph — Stateful Agents with a Graph Architecture
LangGraph is a LangChain library that lets you build Agents as aGraph of State. Unlike CrewAI, which is team-oriented, LangGraph fits complex agentic flows that require State management, loops, and Human-in-the-Loop.
The basic idea: you define a StateGraph — a graph where each Node is a function that receives and returns State. Edges are the transitions between nodes, and you can define Conditional Edges that decide the path based on the results.
Code example — a Chatbot with Human-in-the-Loop
from langgraph.graph import StateGraph, END
from langgraph.prebuilt import ToolNode
from langchain_openai import ChatOpenAI
from langchain_core.tools import tool
from typing import TypedDict, Annotated
import operator
# defining the State
class AgentState(TypedDict):
messages: Annotated[list, operator.add]
human_approved: bool
# defining a Tool
@tool
def calculate(expression: str) -> str:
"""Evaluates a math expression. Takes a string of a Python expression."""
try:
return str(eval(expression))
except Exception as e:
return f"Error: {e}"
tools = [calculate]
llm = ChatOpenAI(model="gpt-4o").bind_tools(tools)
tool_node = ToolNode(tools)
# node functions
def agent_node(state: AgentState):
response = llm.invoke(state["messages"])
return {"messages": [response]}
def human_review_node(state: AgentState):
# a stop point — waits for human approval
last_msg = state["messages"][-1]
print(f"\n[Human Review] Agent wants: {last_msg.content}")
approval = input("Approve? (y/n): ")
return {"human_approved": approval.lower() == "y"}
# conditional routing
def should_continue(state: AgentState):
last = state["messages"][-1]
if hasattr(last, "tool_calls") and last.tool_calls:
return "human_review" # requires approval before using tools
return END
def after_review(state: AgentState):
return "tools" if state["human_approved"] else END
# building the graph
workflow = StateGraph(AgentState)
workflow.add_node("agent", agent_node)
workflow.add_node("human_review", human_review_node)
workflow.add_node("tools", tool_node)
workflow.set_entry_point("agent")
workflow.add_conditional_edges("agent", should_continue)
workflow.add_conditional_edges("human_review", after_review)
workflow.add_edge("tools", "agent") # back to the agent after a Tool
app = workflow.compile()
# run
result = app.invoke({
"messages": [{"role": "user", "content": "What is 847 * 293?"}],
"human_approved": False
})
Choose CrewAI when you have a defined business process with clear roles — it's the faster solution. Choose LangGraph when you need precise control over the State, conditional loops, Human-in-the-Loop, or flows a Crew can't represent.
Build your first Agent — 5 minutes with OpenAI Function Calling
Before using Frameworks, it's important to understand how an Agent works at the basic level. Here is a minimal Agent built directly on the OpenAI API with Function Calling — without external Frameworks.
Step 1 — installation
pip install openai
export OPENAI_API_KEY="your-key-here"
Step 2 — defining Tools and running the Agent
from openai import OpenAI
import json
import math
client = OpenAI()
# --- defining Tools ---
tools = [
{
"type": "function",
"function": {
"name": "web_search",
"description": "Searches for current information online. Use when you need information not in memory.",
"parameters": {
"type": "object",
"properties": {
"query": {
"type": "string",
"description": "the search query"
}
},
"required": ["query"]
}
}
},
{
"type": "function",
"function": {
"name": "calculate",
"description": "Performs a math calculation. Takes a valid Python expression.",
"parameters": {
"type": "object",
"properties": {
"expression": {
"type": "string",
"description": "a math expression, e.g.: '2 ** 10' or 'math.sqrt(144)'"
}
},
"required": ["expression"]
}
}
}
]
# --- implementing Tools ---
def web_search(query: str) -> str:
# in Production: connect to Serper, Tavily, or Brave Search API
return f"[search results for '{query}']: sample simulated information"
def calculate(expression: str) -> str:
try:
result = eval(expression, {"math": math, "__builtins__": {}})
return str(result)
except Exception as e:
return f"Calculation error: {e}"
# --- the Agent loop ---
def run_agent(user_message: str, max_steps: int = 10) -> str:
messages = [
{
"role": "system",
"content": "You are a helpful AI assistant that can search for information and perform calculations. "
"Use the tools when needed. Always answer in English."
},
{"role": "user", "content": user_message}
]
for step in range(max_steps):
response = client.chat.completions.create(
model="gpt-4o",
messages=messages,
tools=tools,
tool_choice="auto"
)
message = response.choices[0].message
messages.append(message)
# if there are no Tool Calls — the Agent is done
if not message.tool_calls:
return message.content
# execute each Tool Call
for tool_call in message.tool_calls:
func_name = tool_call.function.name
func_args = json.loads(tool_call.function.arguments)
print(f"[Agent] calling: {func_name}({func_args})")
if func_name == "web_search":
result = web_search(**func_args)
elif func_name == "calculate":
result = calculate(**func_args)
else:
result = f"Unknown tool: {func_name}"
# add the Tool result to the conversation
messages.append({
"role": "tool",
"tool_call_id": tool_call.id,
"content": result
})
return "The Agent could not complete the task within the allowed number of steps"
# --- running examples ---
print(run_agent("What is the square root of 2025?"))
print(run_agent("Search for information about ChatGPT-5 and summarize in bullets"))
Replace the web_search simulated one with a connection to the Tavily API (free up to 1,000 searches/month): pip install tavily-python, and then from tavily import TavilyClient; client = TavilyClient(api_key="..."); results = client.search(query).
5 real use cases for AI Agents
The theory is clear — but where do Agents actually change lives? Here are five real Use Cases you can build today with the tools we described.
1. Research Agent — automatic market research
The problem: Market competitor analysis takes days of manual work. The solution: An Agent that takes a domain name, searches for information about competitors, gathers pricing and feature data, and produces a comparative report. With CrewAI: a Researcher finds competitors, an Analyst analyzes data, a Writer writes the report — the whole crew runs automatically.
Implementation time: 2-3 hours. Savings: 8-16 hours of manual work per report.
2. Code Review Agent — code review on GitHub
The problem: Code Reviews take time and leave bugs behind. The solution: An Agent that takes a GitHub Pull Request webhook, reads the diff, runs static analysis, checks for security vulnerabilities, and adds detailed comments directly to the PR. It uses the GitHub API as a Tool, and Claude Sonnet as the LLM to focus on logical issues.
Implementation time: 4-6 hours. Benefit: Finds about 70% of common issues before Human Review.
3. Customer Support Agent — automatic ticket replies
The problem: Repetitive support consumes engineering time. The solution: An Agent connected to Zendesk/Intercom that reads each new ticket, searches the knowledge base (RAG over Documentation), and writes a tailored reply. If the issue is complex — it flags "human_needed" and hands it off to a rep with a summary.
Implementation time: 1 day. Benefit: Resolves 60-80% of tickets automatically.
4. Content Agent — creating content from a Brief
The problem: Creating high-quality, consistent marketing content takes a lot of time. The solution: A Crew of Agents: an SEO Researcher (finds keywords), a Content Strategist (defines the structure), a Writer (writes), and a Social Media Specialist (adapts for each platform). Input: a short 2-3 line Brief. Output: an article, 3 LinkedIn posts, 5 Tweets.
Implementation time: 3-4 hours. Savings: 3-4 hours of manual work per Brief.
5. Data Analysis Agent — analyzing CSV and generating Insights
The problem: Raw CSV data requires analysis that takes time and expertise. The solution: An Agent that takes a CSV, writes and runs Python code (Pandas, Matplotlib), generates charts, and returns a natural-language report with Insights and Recommendations. It uses a Code Interpreter Tool or an isolated Python environment.
Implementation time: 2-3 hours. Benefit: Makes data analysis accessible to people who aren't Data Scientists.
The ReAct loop — full code from scratch
Before using a Framework like CrewAI or LangGraph, it's important to understand how to build a ReAct Agent from scratch. This gives a deep understanding that will help diagnose issues later.
ReAct Agent with LangChain
from langchain.agents import AgentExecutor, create_react_agent
from langchain_anthropic import ChatAnthropic
from langchain.tools import tool
from langchain_core.prompts import PromptTemplate
@tool
def search_web(query: str) -> str:
"""Search for current information online. Takes a search query in English."""
# in Production: connect to a Tavily / Serper API
return f"search results for: {query} — [sample simulated results]"
@tool
def calculate(expression: str) -> str:
"""Evaluate a math expression. Takes a valid Python expression."""
try:
return str(eval(expression, {"__builtins__": {}}))
except Exception as e:
return f"Error: {e}"
@tool
def read_file(filename: str) -> str:
"""Read the content of a local text file."""
try:
with open(filename, 'r', encoding='utf-8') as f:
return f.read()
except Exception as e:
return f"Error reading file: {e}"
# defining the LLM
llm = ChatAnthropic(model="claude-sonnet-5", temperature=0)
tools = [search_web, calculate, read_file]
# ReAct Prompt Template
react_prompt = PromptTemplate.from_template("""
You are a helpful AI Agent that answers in English. Follow the ReAct Loop:
Thought → Action → Observation → ... → Final Answer
You have access to the following tools:
{tools}
Tool names: {tool_names}
Question: {input}
{agent_scratchpad}
""")
# creating the Agent
agent = create_react_agent(llm, tools, react_prompt)
executor = AgentExecutor(
agent=agent,
tools=tools,
verbose=True,
max_iterations=10,
handle_parsing_errors=True
)
# run
result = executor.invoke({"input": "What is 17 * 23? And what is the name for a number divisible only by 1 and itself?"})
print(result["output"])
LangGraph — State Machine Agents
LangGraph is a library that adds full State Management to LangChain Agents. Instead of a simple ReAct loop, LangGraph lets you build complex Agents with states, Conditional Routing and Human-in-the-Loop.
When is LangGraph better than plain ReAct?
- When the Agent needs to remember State between different steps
- When there is Branching — "if X, go to step A; otherwise to step B"
- When you want Human-in-the-Loop — pausing to approve an action before it runs
- When the Agent's structure consists of several "roles" (Planner, Executor, Critic)
A basic Graph Agent — Research + Write
from langgraph.graph import StateGraph, END
from langchain_anthropic import ChatAnthropic
from typing import TypedDict, List
# defining the State — the data passed between the Nodes
class AgentState(TypedDict):
topic: str
research: str
draft: str
feedback: str
final_article: str
llm = ChatAnthropic(model="claude-sonnet-5")
# Node 1: research
def research_node(state: AgentState) -> AgentState:
prompt = f"Research the topic: {state['topic']}. Provide 5 key facts."
result = llm.invoke(prompt)
return {"research": result.content}
# Node 2: writing
def write_node(state: AgentState) -> AgentState:
prompt = f"""Write an article in English about: {state['topic']}
based on the following research: {state['research']}
The article should be 300-500 words."""
result = llm.invoke(prompt)
return {"draft": result.content}
# Node 3: review and improve
def review_node(state: AgentState) -> AgentState:
prompt = f"""Review the following draft and improve it:
{state['draft']}
The output: the improved draft only."""
result = llm.invoke(prompt)
return {"final_article": result.content}
# building the Graph
workflow = StateGraph(AgentState)
workflow.add_node("research", research_node)
workflow.add_node("write", write_node)
workflow.add_node("review", review_node)
# Edges — defining the flow
workflow.set_entry_point("research")
workflow.add_edge("research", "write")
workflow.add_edge("write", "review")
workflow.add_edge("review", END)
# Compile and run
app = workflow.compile()
result = app.invoke({"topic": "Artificial intelligence and medicine in Israel"})
print(result["final_article"])
In LangGraph, Conditional Edges let you choose a Node based on the result of a previous Node. workflow.add_conditional_edges("review", lambda s: "approved" if len(s["draft"]) > 300 else "rewrite", {"approved": END, "rewrite": "write"})
Memory — memory for Agents
An Agent without memory "forgets" everything between conversations. Memory is the component that lets it remember context, preferences, and organizational information over time.
Short-term Memory — Conversation History
The LLM's Context Window is the short-term memory — everything that happened in the current conversation. LangChain manages this automatically inConversationBufferMemory. Problem: Context Windows are limited (even GPT-4 Turbo is limited to 128K). For long conversations — useConversationSummaryMemory which automatically summarizes old conversations.
from langchain.memory import ConversationSummaryBufferMemory
from langchain_openai import ChatOpenAI
from langchain.agents import AgentExecutor, create_react_agent
llm = ChatOpenAI(model="gpt-4o")
# memory that automatically summarizes old conversations (keeps up to 500 tokens in live memory)
memory = ConversationSummaryBufferMemory(
llm=llm,
max_token_limit=500,
memory_key="chat_history",
return_messages=True
)
# integration with an Agent
agent_executor = AgentExecutor(
agent=agent,
tools=tools,
memory=memory,
verbose=True
)
# the Agent remembers everything from the conversation — even after 50+ messages
r1 = agent_executor.invoke({"input": "My name is Alon and I work at an AI Startup"})
r2 = agent_executor.invoke({"input": "What is my name and where do I work?"})
# r2 will answer "Your name is Alon and you work at an AI Startup"
Long-term Memory — Vector Store
For memory kept across different Sessions, you use a Vector Store. Every important piece of information is stored as an Embedding, and retrieved by relevance when needed.
from langchain_chroma import Chroma
from langchain_openai import OpenAIEmbeddings
from langchain.memory import VectorStoreRetrieverMemory
# creating a Vector Store for memory
embeddings = OpenAIEmbeddings()
vectorstore = Chroma(
collection_name="agent_memory",
embedding_function=embeddings,
persist_directory="./agent_memory_db" # persisted to disk!
)
retriever = vectorstore.as_retriever(search_kwargs={"k": 3})
# memory that searches for the 3 most relevant memories
memory = VectorStoreRetrieverMemory(retriever=retriever)
# saving a memory
memory.save_context(
{"input": "Alon runs an AI Startup in Tel Aviv"},
{"output": "Saved: Alon → AI Startup → Tel Aviv"}
)
# retrieval by relevance — even after a restart of the program!
relevant = memory.load_memory_variables({"prompt": "Tell me about Alon"})
Production — Error Handling and costs
An Agent that works in a Demo doesn't always work in Production. Here are the most important practices for turning an Agent into a reliable tool.
Error Handling and Retry Logic
import time
from tenacity import retry, stop_after_attempt, wait_exponential
@retry(
stop=stop_after_attempt(3),
wait=wait_exponential(multiplier=1, min=4, max=10)
)
def safe_llm_call(prompt: str) -> str:
"""A safe LLM call with automatic retry"""
try:
response = llm.invoke(prompt)
return response.content
except RateLimitError:
print("Rate Limit — waiting and retrying...")
raise # tenacity will handle the retry
except APIError as e:
print(f"API Error: {e}")
raise
# Tool with validation
@tool
def safe_calculate(expression: str) -> str:
"""A safe calculator with Sandboxing"""
ALLOWED = set('0123456789+-*/.(). ')
if not all(c in ALLOWED for c in expression):
return "Error: expression contains disallowed characters"
if len(expression) > 100:
return "Error: expression too long"
try:
result = eval(expression)
if not isinstance(result, (int, float)):
return "Error: invalid result"
return str(round(result, 6))
except Exception as e:
return f"Calculation error: {e}"
Tracking costs and Token Usage
| Model | Input / 1M tokens | Output / 1M tokens | Notes |
|---|---|---|---|
| Claude 3.5 Sonnet retired | $3 | $15 | Recommended for Agents |
| GPT-4o | $5 | $15 | Flexible, excellent function calling |
| GPT-4o mini | $0.15 | $0.60 | Cheap — for simple roles |
| Claude 3 Haiku | $0.25 | $1.25 | Anthropic's cheapest |
Use a strong model (GPT-4o / Claude Sonnet) for Reasoning and a cheap model (Haiku / GPT-4o mini) for mechanical operations like parsing JSON or Classification. A Hybrid Architecture can save 60-80% of the cost.
Cheat sheet — Framework Comparison
| Criterion | CrewAI | LangGraph | OpenAI API direct |
|---|---|---|---|
| Ease of getting started | Very easy | Medium | Medium |
| Multi-Agent | Excellent | Excellent | Manual |
| State Management | Basic | Full | Manual |
| Human-in-Loop | Limited | Built-in | Manual |
| Observability | LangSmith | LangSmith | Manual |
| Best for | Content pipelines, Research | Complex Workflows | Full control |
5 quick-start points
pip install langchain langchain-openai + one tool (calculate) + a basic loop. Takes 30 minutes.pip install crewai crewai-tools + Researcher + Writer + Task. Takes an hour.pip install langgraph + StateGraph + 3 Nodes. Takes 2 hours.@tool decorator + a precise docstring = the LLM will call the tool correctly.LANGCHAIN_TRACING_V2=true + LANGCHAIN_API_KEY = every Trace appears in LangSmith automatically.Summary — tips and best practices
AI Agents are a powerful tool, but with great power comes responsibility. Here are the key tips that will help you build stable, reliable Agents.
- Start simple: Build a basic ReAct Agent before using a Framework. Understanding the low level will help diagnose issues later.
- Limit the number of steps: Always set
max_stepsormax_iterations. An unbounded Agent can run in an infinite loop and waste API calls. - Write precise System Prompts: The Agent is like a new employee — the better the role is explained, the better it performs. Include what to do and what not to do.
- Add Human-in-the-Loop for critical actions: Sending emails, deleting data, publishing content — every irreversible action needs human approval. LangGraph does this easily.
- Logging and Observability: Use LangSmith, Weights & Biases, or Langfuse to track every Trace of the Agent. Without Observability, you can't improve.
- Test each Tool separately: Before connecting a Tool to an Agent, make sure it works as expected with Unit Tests. A broken Tool leads to a broken Agent.
- Cost and tracking: Agents can consume a lot of Tokens. Track the cost at every step, and set Budget limits in OpenAI / Anthropic.
Useful links
- CrewAI Documentation: docs.crewai.com — guides, Examples, and a full Reference
- LangGraph Documentation: langchain-ai.github.io/langgraph — Tutorials and How-to guides
- OpenAI Function Calling Guide: platform.openai.com/docs/guides/function-calling
- Tavily AI Search API: tavily.com — a free Search API for Agents (1,000 req/month)
- LangSmith: smith.langchain.com — Observability and Tracing for Agents
- AutoGen (Microsoft): github.com/microsoft/autogen — another Multi-Agent Framework
The next step
Now that you understand AI Agents — the next step is to combine them with RAG to give them organizational knowledge, or to build visual Workflows with n8n and Make.com.