Unlock Agentic AI: A Developer's Guide to Autogen
From a simple chat to building powerful tools with the new event-driven framework
Microsoft's AutoGen is a game-changer for anyone serious about building with AI. It’s an open-source framework that lets you move beyond single-shot prompts and create sophisticated teams of AI agents that collaborate to solve complex tasks.
With the recent release of AutoGen v0.4, the framework has undergone a major evolution. It now features a more robust, asynchronous, and event-driven architecture, unlocking a whole new level of power and flexibility.
But what does that mean for you, the developer? In this guide, we'll cut through the jargon and show you how to get started with the new AutoGen. We'll cover:
The new architecture and why it matters.
How to build your first, simple AssistantAgent.
The magic of FunctionTool for giving your agents real-world capabilities.
The New Autogen Architecture: A Quick Tour
Think of the new AutoGen framework as a three-layer stack, designed for both simplicity and power.
Image is sourced from Microsoft
Lets talk more about the Framework Layer:
autogen-core (The Foundation): This is the powerful, unopinionated engine at the heart of AutoGen. It uses an event-driven model (specifically, the Actor model) that allows agents to communicate asynchronously. This is what makes AutoGen scalable, resilient, and ready for complex, distributed systems. For advanced users, this layer offers maximum control.
At the bottom of the stack is the base messaging and routing facilities that enable agents to communicate with each other. These are managed by the agent runtime, and for most applications, developers only need to interact with the high-level APIs provided by the runtime
AgentChat (The Living Room): Built on top of autogen-core, AgentChat is the high-level API that most developers will start with. It abstracts away the complexity of the core, providing a set of pre-built, stateful agents like AssistantAgent. It’s the fastest way to get a multi-agent conversation up and running.
Extensions (The Appliances): AutoGen is designed to be plug-and-play. The autogen-ext package contains ready-made components you can plug into your system. The most common extension is the model client, like OpenAIChatCompletionClient, which acts as the "brain" for your agents by connecting them to LLMs like GPT-4.
Key Features
Asynchronous messaging: Agents communicate through asynchronous messages, supporting both event-driven and request/response interaction patterns.
Modular and extensible: Users can easily customize systems with pluggable components, including custom agents, tools, memory, and models. They can also build proactive and long-running agents.
Observability and debugging: Built-in tools provide tracking, tracing, and debugging agent interactions and workflows, with support for OpenTelemetry for industry-standard observability.
Scalable and distributed: Users can design complex, distributed agent networks that operate seamlessly across organizational boundaries.
Built-in and community extensions: The extensions module enhances the framework’s functionality with advanced model clients, agents, multi-agent teams, and tools for agentic workflows. Support for community extensions allows open-source developers to manage their own extensions.
Cross-language support: This update enables interoperability between agents built in different programming languages, with current support for Python and .NET and additional languages in development.
Full type support: Interfaces now enforce type checks at build time, ensuring robust and cohesive code quality.
Lets code a basic Assistant Agent:
AutoGen AgentChat provides a set of preset Agents, each with variations in how an agent might respond to messages. All agents share the following attributes and methods:
name
: The unique name of the agent.description
: The description of the agent in text.run
: The method that runs the agent given a task as a string or a list of messages, and returns aTaskResult
. Agents are expected to be stateful and this method is expected to be called with new messages, not complete history.run_stream
: Same asrun()
but returns an iterator of messages that subclassBaseAgentEvent
orBaseChatMessage
followed by aTaskResult
as the last item.
One of the agent type that autogen provides is called Assistant Agent which is a built-in agent that uses a language model and has the ability to use tools.
Let’s write a basic function tool which could calculate Monthly EMI. Lets import all the packages
from autogen_agentchat.agents import AssistantAgent
from autogen_ext.models.openai import OpenAIChatCompletionClient
from dotenv import load_dotenv
import asyncio
from autogen_core.tools import FunctionTool
AssistantAgent is part of the AgentChat architecture which abstracts the underlying complexity of an Agent and is built on top of Agent Core Framework
OpenAIChatCompletionClient is part of autogen extensions which is extensible for different LLM providers.
FunctionTool is part of the Autogen Core Architecture.
load_dotenv()
api_key = os.getenv("OPENAI_API_KEY")
if not api_key:
raise ValueError("Please set the OPENAI_API_KEY environment variable.")
model_client=OpenAIChatCompletionClient(model='gpt-4o',api_key=api_key)
The above code is basic code to setup an OpenAI LLM Client
If we consider the Agent as a digital Human and the model_client acts as a brain for an Agent to respond based on the LLM response on the set of instruction the agent has.
Before we dive into a function tool let’s see how we can create a basic Assistant agent.
agent= AssistantAgent
(model_client=model_client,
name="AssistantAgent",
description="An assistant agent that can answer questions and provide information.")
message = "What is the capital of France?"
response= await agent.run(task=message)
print(f"Response: {response}")
The above code we have created an Assistant Agent which has a brain as model_client which interacts with LLM. We can use run method to call the agent with task parameters to contain the task which agent does.
When you run this, the agent.run() method sends the task to the LLM via the model_client. Because AutoGen is asynchronous by default, we use await to get the final result. The response object is a TaskResult that contains a full history of the conversation. We print the content of the last message to see the agent's final answer: The capital of France is Paris.
messages=[TextMessage(id='05a0e608-32c6-4b94-94f3-99c0221fac64', source='user', models_usage=None, metadata={}, created_at=datetime.datetime(2025, 7, 13, 12, 52, 23, 445213, tzinfo=datetime.timezone.utc), content='What is the capital of France?', type='TextMessage'), TextMessage(id='3a687217-276f-449a-ab57-58546a6856e6', source='AssistantAgent', models_usage=RequestUsage(prompt_tokens=43, completion_tokens=7), metadata={}, created_at=datetime.datetime(2025, 7, 13, 12, 52, 25, 149864, tzinfo=datetime.timezone.utc), content='The capital of France is Paris.', type='TextMessage')] stop_reason=None
Supercharging Your Agent with a Function Tool
Answering questions is fine, but the real power of agents comes from giving them tools to interact with the world. Let's create an EMI calculator tool.
Step 1: Define the Python Function
This is a standard Python function. The docstrings and type hints are crucial, as they help the LLM understand what the tool does and what inputs it needs.
def calculate_emi_breakdown(principal_amount: float, annual_interest_rate: float, years: int) -> str:
"""
Calculates the Equated Monthly Instalment (EMI) and the breakdown of the first month's payment.
Args:
principal_amount (float): The total loan amount.
annual_interest_rate (float): The annual interest rate (e.g., 5 for 5%).
years (int): The loan term in years.
Returns:
str: A formatted string detailing the monthly EMI, and the principal and interest
components for the first month.
"""
# Convert annual rate to monthly rate and percentage to decimal
monthly_rate = (annual_interest_rate / 12) / 100
# Convert years to months
months = years * 12
# Handle the edge case of 0% interest
if monthly_rate == 0:
emi = principal_amount / months
interest_first_month = 0.0
else:
# Calculate EMI using the formula
emi = (principal_amount * monthly_rate * (1 + monthly_rate)**months) / ((1 + monthly_rate)**months - 1)
# Calculate the interest component for the first month
interest_first_month = principal_amount * monthly_rate
# Calculate the principal component for the first month
principal_first_month = emi - interest_first_month
# Return a nicely formatted string
return (
f"Total Monthly EMI: ${emi:,.2f}\n"
f"For the first month's payment:\n"
f" - Principal Component: ${principal_first_month:,.2f}\n"
f" - Interest Component: ${interest_first_month:,.2f}"
)
The above tool is basic calculation of an EMI and let us concentrate how we can integrate this tool to the Assistant Agent.
Step 2: Create the Tool-Enabled Agent
Now, we wrap our Python function in a FunctionTool and give it to our agent.
emi_tool = FunctionTool(calculate_emi_breakdown,description='A tool to calculate an EMI for prinicipal amount,Years, Interest rate that user provides')
Let’s create Assistant Agents and we add the emi_tool function tool to the tools list of the Assistant Agent and also provide the description of the Assistant Agent
agent = AssistantAgent(
name="ReverseStringAgent",
model_client= model_client,
system_message='You are a helpful assistant that can calculate an EMI for prinicpal amount,Years, Interest rate that user provides by using the tool calculate_emi_breakdown. The response from the tool is the Breakdown of EMI. Give the result with summary',
tools=[emi_tool]
)
result = await agent.run(task = 'Calculate EMI for a loan of $52000 at 9% annual interest over 10 years')
print(result.messages[-1].content)
When you run this, the agent will:
Read the task and its system message.
Recognize that it needs to use the calculate_emi_breakdown tool.
Intelligently extract the parameters (52000, 9, 10) from the natural language task.
Execute the tool.
Receive the result from the tool and formulate a final, user-friendly answer based on its system message.
We can see the last Messages in the Result would Contain the final response of the Agent.
Total Monthly EMI: $658.71
For the first month's payment:
- Principal Component: $268.71
- Interest Component: $390.00
If we deep dive into all the messages of the Agent Response we have different types like TextMessage, ToolCallRequestEvent, ToolCallExecutionEvent, FunctionExecutionResult, ToolCallSummaryMessage and these are used for communication between Agent and LLM and Function Call.
Code: Github
What's Next?
You've just scratched the surface. With the new event-driven architecture and the power of FunctionTool, you can build agents that query databases, send emails, interact with APIs, and perform almost any task you can code in Python.
The new AutoGen isn't just an update; it's a foundation for the next generation of agentic AI applications.
Thanks for reading! Subscribe for more deep dives into AutoGen and Agentic AI.