Skip to main content
In Agent Stack, you communicate with the client by yielding data. This concept consists of two parts:
  1. Yielding data: Sending data from your agent implementation to the client.
  2. The Wrapper: Using convenience objects like AgentMessage to simplify the underlying A2A Protocol requirements.

Choosing Your Message Type

TypeBest For…Key Benefit
Simple Data (str, dict)Simple text or JSONAutomatic conversion
AgentMessageStandard conversational responsesAuto-generates IDs and handles TextPart wrapping
AgentArtifactReturning files, documents, or assetsAutomatically wraps content into A2A Part objects
A2A ComponentsAdvanced protocol-level controlFull control over Role, UUID, and Part lists
TaskStatusTracking stateful progressAllows you to signal specific states like input_required

Simplified Yielding

The Agent Stack SDK allows you to yield simple Python types. These are automatically converted into textual A2A Message objects for ease of use.

Plain Strings

yield "Hello, world!"

Plain Dictionaries

yield {"status": "processing", "progress": 50}

Convenience Wrappers

Wrappers provide a balance between ease of use and metadata support.

AgentMessage

The most common way to respond with text. It simplifies creating A2A Message objects and supports metadata.
yield AgentMessage(text="This is my text", metadata={"foo": "bar"})

AgentArtifact

Similar to AgentMessage, but specifically designed to simplify the creation and handling of Artifacts (tangible outputs).
yield AgentArtifact(
        parts=[
            TextPart(text="Here is the documentation you requested."),
            FilePart(file=FileWithUri(
                uri="https://example.com/report.pdf", 
                mime_type="application/pdf", 
                name="Report.pdf"
            ))
        ]
    )

Direct A2A Components

For advanced use cases, you can yield direct A2A protocol components.
While yielding plain A2A components is supported, the Agent Stack is optimized for convenience wrappers. Using wrappers ensures the best UX in the GUI.

Message

The basic unit representing a single turn in a conversation.
import uuid
from a2a.types import Message, TextPart, Part, Role

# @server.agent(...)
async def example_agent():
    yield Message(role=Role.agent, message_id=str(uuid.uuid4()), parts=[Part(root=TextPart(text="Hello from the agent!"))])

Part

The fundamental unit of content. A Message consists of multiple Part objects such as TextPart, FilePart, or DataPart.
from a2a.types import TextPart

# @server.agent(...)
async def example_agent():
    yield TextPart(text="Hello from the agent!")

Artifact

Tangible outputs produced by the agent, such as documents or other generated content.
import uuid
from a2a.types import Artifact, FilePart, FileWithUri, Part

# @server.agent(...)
async def example_agent():
    yield Artifact(
        artifact_id=str(uuid.uuid4()),
        parts=[Part(root=FilePart(file=FileWithUri(uri="https://www.ibm.com/us-en", mime_type="text/html", name="IBM Website")))],
    )

TaskStatus

A stateful unit of work used to annotate a transaction spanning multiple messages (e.g., tracking progress or requiring input).
import uuid
from a2a.types import TaskStatus, TextPart, Message, TaskState, Part, Role

# @server.agent(...)
async def example_agent():
    yield TaskStatus(
        message=Message(message_id=str(uuid.uuid4()), role=Role.agent, parts=[Part(root=TextPart(text="Please provide some input."))]),
        state=TaskState.input_required,
    )