> ## Documentation Index
> Fetch the complete documentation index at: https://docs.praison.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Integrate A2UI with Your Frontend

> Connect any UI to PraisonAI agents via the A2UI tool output contract

# Integrate A2UI with Your Frontend

Use this guide when building **your own** chat app, dashboard, or canvas — not only PraisonAIUI.

PraisonAI core emits A2UI via the agent tool `send_a2ui_messages`. Your frontend detects the payload and renders with [Google A2UI renderers](https://github.com/google/A2UI/tree/main/renderers) or a custom mapper.

<Note>
  Core SDK documents the **contract** (`A2UIToolResultProtocol`). Detection helpers for rich UI live in [PraisonAIUI `a2ui_utils`](https://github.com/MervinPraison/PraisonAIUI) as the reference UI implementation — do not expect parsing logic in `praisonaiagents` core.
</Note>

## Prerequisites

```bash theme={"theme":{"light":"vitesse-light","dark":"vitesse-dark"}}
pip install praisonaiagents[a2ui]
```

Optional React renderer:

```bash theme={"theme":{"light":"vitesse-light","dark":"vitesse-dark"}}
npm install @a2ui/react @a2ui/web_core
```

## Four-step contract

### 1. Agent with the A2UI tool

```python theme={"theme":{"light":"vitesse-light","dark":"vitesse-dark"}}
from praisonaiagents import Agent
from praisonaiagents.tools.a2ui_tools import send_a2ui_messages

agent = Agent(
    name="assistant",
    instructions=(
        "When the user asks for UI, call send_a2ui_messages with valid A2UI v0.9 JSON."
    ),
    tools=[send_a2ui_messages],
)
```

### 2. Tool output shape (integrator contract)

`send_a2ui_messages` returns:

```python theme={"theme":{"light":"vitesse-light","dark":"vitesse-dark"}}
{
    "mime_type": "application/json+a2ui",
    "messages": [  # A2UI v0.9 message list
        {"createSurface": {"surfaceId": "main", "catalogId": "basic"}, ...}
    ],
    "a2ui_part": ...  # A2A-wrapped payload
}
```

Type hint in core (zero runtime cost):

```python theme={"theme":{"light":"vitesse-light","dark":"vitesse-dark"}}
from praisonaiagents.ui.a2ui import A2UI_MIME_TYPE, A2UIToolResultProtocol
from praisonaiagents.ui.protocols import A2UI_MIME_TYPE  # same constant
```

### 3. Detect in your UI (minimum)

```python theme={"theme":{"light":"vitesse-light","dark":"vitesse-dark"}}
def handle_tool_result(result):
    if isinstance(result, dict) and result.get("mime_type") == "application/json+a2ui":
        messages = result["messages"]
        # → pass to @a2ui/react or your renderer
        return messages
    return None
```

For richer normalisation (surface id, version fields), use [PraisonAIUI `a2ui_utils.py`](https://github.com/MervinPraison/PraisonAIUI/blob/main/src/praisonaiui/a2ui_utils.py) as a reference — copy or vendor that file in your UI layer.

### 4. Render and handle user actions

**React (Google renderer):**

```tsx theme={"theme":{"light":"vitesse-light","dark":"vitesse-dark"}}
import { A2uiSurface, basicCatalog } from '@a2ui/react/v0_9'
// Process messages with MessageProcessor, render A2uiSurface
```

Wire button clicks back to your agent (POST user action → new agent turn).

## Transport options

| Transport            | Entry point                               | A2UI delivery                                                        |
| -------------------- | ----------------------------------------- | -------------------------------------------------------------------- |
| **Tool result JSON** | Your WebSocket/SSE                        | Parse `mime_type` on `TOOL_CALL_COMPLETED`                           |
| **AG-UI**            | `AGUI(agent).get_router()` → `POST /agui` | `TOOL_CALL_RESULT` (JSON string) + **`CUSTOM` event** `name: "a2ui"` |
| **A2A**              | `A2A(agent)` → `POST /a2a`                | `create_a2ui_part()` / `is_a2ui_part()`                              |
| **PraisonAIUI**      | `aiui run app.py`                         | Reference impl — surfaces, canvas, chat preview                      |

### AG-UI CUSTOM event

When a tool returns A2UI, the AG-UI bridge emits an additive event:

```json theme={"theme":{"light":"vitesse-light","dark":"vitesse-dark"}}
{
  "type": "CUSTOM",
  "name": "a2ui",
  "value": {
    "mime_type": "application/json+a2ui",
    "messages": [...],
    "surface_id": "main"
  }
}
```

The existing `TOOL_CALL_RESULT` with stringified JSON is unchanged for backward compatibility.

## Tiers (pick the simplest)

See [Generative UI](/docs/features/generative-ui) for the full tier list:

| Tier | Use when                                                 |
| ---- | -------------------------------------------------------- |
| 0    | Markdown streaming only                                  |
| 1    | Your frontend owns component mapping (`output_pydantic`) |
| 2    | CopilotKit / AG-UI client                                |
| 3    | Cross-platform A2UI catalog (this guide)                 |

## Reference implementation

[PraisonAIUI example 29 — A2UI canvas](https://github.com/MervinPraison/PraisonAIUI/tree/main/examples/python/29-a2ui-canvas) demonstrates chat + live surface preview.

## Related

* [A2UI Protocol](/docs/features/a2ui)
* [Generative UI](/docs/features/generative-ui)
* [AG-UI Protocol](/docs/deploy/servers/agui)
