Skip to main content

Overview

Agents are the core building blocks of the Qwen-Agent framework. An agent can receive messages and provide responses using LLMs, tools, or specialized workflows. Different agents have distinct processing patterns implemented in their _run method.

Agent Base Class

All agents inherit from the Agent base class, which provides the foundational interface for message processing and tool integration.

Key Components

from qwen_agent import Agent

agent = Agent(
    function_list=['code_interpreter', 'image_gen'],
    llm={'model': 'qwen-plus', 'api_key': 'your-key'},
    system_message='You are a helpful assistant.',
    name='MyAgent',
    description='An agent that can execute code and generate images'
)

Constructor Parameters

function_list
List[Union[str, Dict, BaseTool]]
List of tools the agent can use. Can be:
  • Tool name: 'code_interpreter'
  • Tool configuration: {'name': 'code_interpreter', 'timeout': 10}
  • Tool object: CodeInterpreter()
llm
Union[dict, BaseChatModel]
LLM configuration or model object. Example: {'model': 'qwen-plus', 'api_key': 'your-key'}
system_message
str
System prompt that guides the agent’s behavior
name
str
Agent name, useful for multi-agent scenarios
description
str
Agent description, used in multi-agent routing

Agent Workflow

Running an Agent

Agents provide two main interfaces for execution:
from qwen_agent.llm.schema import Message

messages = [
    Message(role='user', content='What is 2+2?')
]

# Stream responses as they're generated
for responses in agent.run(messages):
    print(responses[-1].content)

Message Flow

Built-in Agent Types

BasicAgent

The simplest agent that only uses the LLM without tools or special workflows.
from qwen_agent import BasicAgent

agent = BasicAgent(
    llm={'model': 'qwen-plus'}
)

responses = agent.run_nonstream([
    {'role': 'user', 'content': 'Hello!'}
])
Source Reference: qwen_agent/agent.py:263-269

FnCallAgent

A function-calling agent that can use tools through the LLM’s function calling capabilities. It automatically handles the tool invocation loop.
from qwen_agent.agents import FnCallAgent

agent = FnCallAgent(
    function_list=['code_interpreter'],
    llm={'model': 'qwen-plus'},
    system_message='You are a coding assistant.'
)

messages = [{'role': 'user', 'content': 'Calculate fibonacci(10)'}]
for responses in agent.run(messages):
    print(responses[-1].content)
Key Features:
  • Automatically detects function calls from LLM responses
  • Executes tools and feeds results back to the LLM
  • Supports iterative tool use (tool → LLM → tool → …)
  • Maximum iterations controlled by MAX_LLM_CALL_PER_RUN
Source Reference: qwen_agent/agents/fncall_agent.py:27-121

Assistant

A comprehensive agent with RAG (Retrieval-Augmented Generation) capabilities and function calling. Ideal for document Q&A and general assistance tasks.
from qwen_agent.agents import Assistant

agent = Assistant(
    function_list=['code_interpreter', 'image_gen'],
    llm={'model': 'qwen-plus'},
    files=['https://example.com/doc.pdf'],
    rag_cfg={
        'max_ref_token': 4000,
        'rag_searchers': ['keyword_search']
    }
)

messages = [
    {'role': 'user', 'content': 'Summarize the uploaded document'}
]
responses = agent.run_nonstream(messages)
Key Features:
  • Built-in document retrieval and knowledge injection
  • Supports multiple file formats (PDF, DOCX, TXT, etc.)
  • Automatically formats retrieved content into context
  • Inherits all FnCallAgent capabilities
Source Reference: qwen_agent/agents/assistant.py:81-149

Router

A multi-agent coordinator that routes requests to specialized sub-agents based on their capabilities.
from qwen_agent.agents import Router, Assistant
from qwen_agent import BasicAgent

# Create specialized agents
coder = Assistant(
    function_list=['code_interpreter'],
    name='Coder',
    description='Expert at writing and executing Python code'
)

writer = BasicAgent(
    name='Writer',
    description='Expert at creative writing and content generation'
)

# Create router
router = Router(
    agents=[coder, writer],
    llm={'model': 'qwen-plus'}
)

messages = [{'role': 'user', 'content': 'Write a Python script to sort a list'}]
for responses in router.run(messages):
    print(f"Agent: {responses[-1].name}")
    print(responses[-1].content)
Key Features:
  • Intelligently routes requests to appropriate sub-agents
  • Falls back to direct response when no agent is needed
  • Supports dynamic agent selection
  • Maintains conversation context across agent switches
Source Reference: qwen_agent/agents/router.py:36-107

Custom Agent Implementation

Create custom agents by implementing the _run method:
from qwen_agent import Agent
from qwen_agent.llm.schema import Message, ASSISTANT
from typing import Iterator, List

class CustomAgent(Agent):
    def _run(self, messages: List[Message], lang: str = 'en', **kwargs) -> Iterator[List[Message]]:
        # Your custom workflow here
        # 1. Process messages
        processed_messages = self.preprocess(messages)
        
        # 2. Call LLM
        response = []
        for response in self._call_llm(processed_messages):
            yield response
        
        # 3. Post-process
        final_response = self.postprocess(response)
        yield [Message(role=ASSISTANT, content=final_response)]
    
    def preprocess(self, messages):
        # Custom preprocessing logic
        return messages
    
    def postprocess(self, response):
        # Custom postprocessing logic
        return response[-1].content if response else ''

Tool Integration

Agents can access tools through the function_map dictionary:
class MyAgent(Agent):
    def _run(self, messages, **kwargs):
        # Check available tools
        tool_names = list(self.function_map.keys())
        
        # Call a tool directly
        result = self._call_tool(
            tool_name='code_interpreter',
            tool_args={'code': 'print("Hello")'}
        )
        
        # Tool detection from LLM response
        for responses in self._call_llm(messages, 
                                        functions=[t.function for t in self.function_map.values()]):
            for msg in responses:
                use_tool, tool_name, tool_args, text = self._detect_tool(msg)
                if use_tool:
                    result = self._call_tool(tool_name, tool_args)

Best Practices

Choose the Right Agent

  • Use BasicAgent for simple LLM chat
  • Use FnCallAgent for tool-enabled workflows
  • Use Assistant for RAG + tools
  • Use Router for multi-agent coordination

Memory Management

  • Agents with RAG capabilities include built-in Memory
  • Memory automatically manages document parsing and retrieval
  • Configure rag_cfg to control retrieval behavior

Streaming

  • Use agent.run() for streaming responses
  • Use agent.run_nonstream() when you need the complete result
  • Streaming provides better UX for long-running tasks

System Messages

  • Always set clear system messages to guide behavior
  • System messages are prepended automatically if not present
  • Keep them concise and specific to the agent’s role

Tools

Learn about the tool system and how to create custom tools

Function Calling

Deep dive into function calling implementation

Memory

Understand the memory system for RAG

LLM Configuration

Configure LLM models and parameters

Build docs developers (and LLMs) love