Build or update the BlueBubbles external channel plugin for Moltbot (extension package, REST...
npx skills add shuiyuan1223/skillfix_xuetang --skill "a2ui-components"
Install specific skill from multi-skill repository
# Description
Reference for A2UI component API. Use when building pages or UI features to know what components exist and how to use them.
# SKILL.md
name: a2ui-components
description: Reference for A2UI component API. Use when building pages or UI features to know what components exist and how to use them.
A2UI Component Reference
Architecture
Backend (pages.ts) Frontend (Web / TUI)
A2UIGenerator.build() โโโฌโโ WebSocket /ws โโโ A2UIRenderer.tsx (React)
โ tui-renderer.ts (pi-tui)
โ
Agent chat events โโโโโโโดโโ POST /api/ag-ui (SSE) โโโ App.tsx (AG-UI events)
All UI is server-generated. Frontend never contains business logic.
Dual channel: Page updates via WebSocket, chat streaming via SSE.
A2UIGenerator API
const ui = new A2UIGenerator("main"); // surface: "main" | "sidebar" | "modal" | "toast"
Layout
| Method | Usage |
|---|---|
ui.column(children, { gap, padding, align }) |
Vertical stack |
ui.row(children, { gap, justify, align, wrap }) |
Horizontal stack |
ui.grid(children, { columns, gap }) |
Grid layout |
ui.card(children, { title, padding }) |
Card container |
Content
| Method | Usage |
|---|---|
ui.text(text, variant) |
Text. variant: "h1"โ"h2"โ"h3"โ"body"โ"caption"โ"label" |
ui.statCard({ title, value, subtitle, icon, trend, color }) |
Stat card with icon |
ui.chart({ chartType, data, xKey, yKey, height, color }) |
Chart. type: "line"โ"bar"โ"area"โ"pie" |
ui.table(columns, rows) |
Simple table |
ui.dataTable(columns, rows, { pagination, onRowClick }) |
Rich table with sorting/pagination |
ui.badge(text, { variant }) |
Badge. variant: "default"โ"success"โ"warning"โ"error"โ"info" |
ui.progress(value, { maxValue, label, color }) |
Progress bar |
ui.scoreGauge(value, { label, max, size }) |
Score gauge |
ui.codeEditor(value, { language, readonly, height }) |
Code/markdown editor |
ui.collapsible(title, children, { icon, expanded }) |
Collapsible section |
Interactive
| Method | Usage |
|---|---|
ui.button(label, action, { variant, size, payload }) |
Button โ triggers handleAction(action, payload) |
ui.formInput(name, inputType, { label, placeholder, required, options }) |
Input field |
ui.form(children, onSubmit, { submitLabel, cancelLabel }) |
Form wrapper |
ui.nav(items, { activeId }) |
Navigation list |
ui.tabs(tabs, activeTab, contentIds) |
Tab panels |
ui.modal(title, children, { size }) |
Modal dialog |
Evolution Lab
| Method | Usage |
|---|---|
ui.gitTimeline(events, { activeBranch, onEventClick }) |
Git timeline. Events: { id, type, label, description?, timestamp, branch?, score?, status? } |
ui.stepIndicator(steps, { orientation }) |
Pipeline steps. Steps: { id, label, icon?, status } |
ui.fileTree(files, { selectedPath, onFileSelect }) |
File tree. Files: { path, status, additions?, deletions? } |
Building
const root = ui.column([child1, child2], { gap: 24, padding: 24 });
return ui.build(root); // Returns A2UISurfaceData
Chart Constraints
When using ui.chart():
- YAxis domain: For data with small variations (e.g., heart rate 60-100), set explicit yDomain: [min, max] to avoid flat lines
- Dense data: For time-series with many points, consider using area chart type for better readability
- Color: Use semantic colors โ "#ef4444" for heart-related, "#3b82f6" for sleep, "#22c55e" for activity
Icon Rules
MUST use icon names, NEVER emoji. Full list in CLAUDE.md.
// CORRECT
icon: "heart"
icon: "brain"
// WRONG - will render as raw emoji
icon: "โค๏ธ"
icon: "๐ง "
i18n Rules
All user-facing text MUST use t() function.
import { t } from "../locales/index.js";
ui.text(t("health.title"), "h2"); // CORRECT
ui.text("Health Overview", "h2"); // WRONG
Update 3 files: types.ts, zh-CN.ts, en.ts in src/locales/.
Tool Display Names
When Agent calls MCP tools during chat, the frontend shows a Chinese label. Maintain this mapping in ui/src/components/a2ui/A2UIRenderer.tsx:
const TOOL_DISPLAY_NAMES: Record<string, string> = {
get_health_data: "ๅฅๅบทๆฐๆฎ",
get_heart_rate: "ๅฟ็ๆฐๆฎ",
get_sleep: "็ก็ ๆฐๆฎ",
// ... add new tools here
};
Page Assembly Pattern
export function generateXxxPage(data: { ... }): A2UISurfaceData {
const ui = new A2UIGenerator("main");
// 1. Header
const title = ui.text(t("xxx.title"), "h2");
const subtitle = ui.text(t("xxx.subtitle"), "caption");
const header = ui.column([title, subtitle], { gap: 4, padding: 24 });
// 2. Content
const content = ui.column([...], { gap: 24, padding: 24 });
// 3. Root
const root = ui.column([header, content], { gap: 0 });
return ui.build(root);
}
Sending to Frontend
// Full page (sidebar + main) via WebSocket
import { generatePage } from "./pages.js";
send(generatePage("viewName", mainContent));
// Update single surface via WebSocket
send({ type: "a2ui", surface_id: "main", components, root_id });
// Show modal via WebSocket
send({ type: "a2ui", surface_id: "modal", components, root_id });
// Show toast via WebSocket
const toast = generateToast("message", "success");
send({ type: "a2ui", surface_id: "toast", ...toast });
// Close modal via WebSocket
send({ type: "clear_surface", surface_id: "modal" });
Chat messages are NOT sent via A2UI โ they stream via SSE (POST /api/ag-ui) using AG-UI protocol events:
- RunStarted / RunFinished โ Chat lifecycle
- TextMessageStart / TextMessageContent / TextMessageEnd โ Text streaming
- ToolCallStart / ToolCallEnd / ToolCallResult โ Tool invocations
# Supported AI Coding Agents
This skill is compatible with the SKILL.md standard and works with all major AI coding agents:
Learn more about the SKILL.md standard and how to use these skills with your preferred AI coding agent.