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

# UI Protocol

## Overview

Charm Store uses a Server-Driven UI architecture.
Agents are required to return either spec-compliant JSON or standard Markdown.
Outputs are rendered into native UI components automatically by the Charm Universal Renderer.

### Standard Markdown

Supports direct string streaming with rich formatting, including titles, lists, code blocks, bold/italic text, and links.

### Structured JSON (Explicit Rendering)

The preferred way to trigger rich UI is to explicitly declare a `_charm_render_type` in your JSON output. This bypasses heuristic guessing and guarantees consistent, robust rendering.

#### Chart Components

```jsonc theme={"theme":{"light":"min-light","dark":"min-dark"}}
// 1. Bar Chart
{
  "_charm_render_type": "bar_chart",
  "title": "Revenue by Region",
  "data": [
    { "name": "NA", "value": 125000 },
    { "name": "EU", "value": 85000 }
  ]
}

// 2. Line Chart (Sparkline style)
{
  "_charm_render_type": "line_chart",
  "title": "User Growth",
  "data": [
    { "name": "Mon", "value": 10 },
    { "name": "Tue", "value": 25 },
    { "name": "Wed", "value": 40 }
  ]
}

// 3. Pie Chart
{
  "_charm_render_type": "pie_chart",
  "title": "Traffic Sources",
  "data": [
    { "name": "Organic", "value": 45 },
    { "name": "Direct", "value": 30 }
  ]
}
```

#### Data Grid

Renders a clean, scrollable table. Automatically extracts column headers from the keys of the first row object.

```jsonc theme={"theme":{"light":"min-light","dark":"min-dark"}}
{
  "_charm_render_type": "data_grid",
  "title": "Recent Transactions",
  "rows": [
    { "id": "TX-1", "amount": "$450", "status": "Paid" },
    { "id": "TX-2", "amount": "$120", "status": "Pending" }
  ]
}
```

#### Metric Card

Renders a dashboard-style grid of metric cards with optional trend indicators.

```jsonc theme={"theme":{"light":"min-light","dark":"min-dark"}}
{
  "_charm_render_type": "metric_card",
  "title": "Performance Dashboard",
  "metrics": [
    { "label": "Active Users", "value": 1204, "change": 12, "unit": "users" },
    { "label": "Churn Rate", "value": "2.4", "change": -0.5, "unit": "%" }
  ]
}
```

### Structured JSON (Heuristic Rendering)

If an explicit `_charm_render_type` is not provided, the Charm Store will attempt to infer the best UI representation based on the presence of certain keys.

#### Viral Card

Purpose-built for sharing and revealing underlying mechanisms.

```json theme={"theme":{"light":"min-light","dark":"min-dark"}}
// Trigger condition: JSON must include "type": "viral_card"

{
  "type": "viral_card",
  "content": {
    "cover_mode": true,        // Whether to enable the “reveal” cover mode
    "cover_data": {
      "title": "CONFIDENTIAL", // Title displayed on the cover (e.g. SECRET, TOP SECRET)
      "subtitle": "VIBE CHECK",// Subtitle displayed on the cover
      "cover_image": "https://..." // (Optional) Background image for the cover
    },
    "image_url": "https://...",    // Final result image shown after reveal (or when downloaded)
    "description": "This is your analysis result...", // Text description displayed below the card
    "action": {
      "type": "smart_share_trigger", // Fixed value, triggers native share/download logic
      "label": "REVEAL & SHARE"      // Button label
    },
    "metadata": {
      "sticker_link": "https://..."  // (Optional) Link automatically copied to clipboard when sharing (e.g. IG “Add Yours”)
    }
  }
}
```

#### Universal Timeline

Render a sequence of events as a vertical timeline.

```jsonc theme={"theme":{"light":"min-light","dark":"min-dark"}}
// Trigger condition (heuristic detection):
// Return an Array where each object contains any of the following keywords: date, time, year, timestamp

[
  {
    "date": "2024-01-15",
    "event": "Project Kickoff",
    "description": "Initial meeting with stakeholders.",
    "location": "Taipei HQ"
  },
  {
    "date": "2024-02-01",
    "event": "Alpha Release",
    "status": "success" // Will automatically render a green check icon
  }
]

// Special style keywords:

// Content containing "error", "fail", "conflict" → Red warning style
// Content containing "success", "complete", "solve" → Green success style
// Content containing "announce", "tweet", "report" → Blue informational style
```

#### Comparison View

Render multiple objects as a responsive comparison table.

```jsonc theme={"theme":{"light":"min-light","dark":"min-dark"}}
// Trigger condition (heuristic detection):
// Return an Array where the object keys contain comparison-related keywords: vs, competitor, price, feature, target

[
  {
    "Feature": "AI Model",
    "Charm_OS": "GPT-4o + Claude 3.5",
    "Competitor_X": "GPT-3.5"
  },
  {
    "Feature": "Viral Sharing",
    "Charm_OS": "Native Support",
    "Competitor_X": "None"
  }
]

// This array will be rendered as a responsive comparison table
```

#### Optimization Diff

Display the differences between content before and after optimization, suitable for copywriting revision or code refactoring agents.

```jsonc theme={"theme":{"light":"min-light","dark":"min-dark"}}
// Trigger condition (heuristic detection):
// Return an Object containing keys related to both "original" and "optimized" content

// Original-related keys: original, before, weakness
// Optimized-related keys: optimized, after, rewrite

{
  "section": "Instagram Bio Rewrite",
  "original_content": "I like coffee and coding.",      // Original content
  "optimized_version": "Fueled by caffeine.\nBuilding the future of AI.\nCheck my vibe below.",  // Optimized content
  "reason": "Added emojis and line breaks for better readability." // Explanation for the optimization
}
```

#### Universal Article

Suitable for long-form content, automatically extracts headings and optimizes formatting.

```jsonc theme={"theme":{"light":"min-light","dark":"min-dark"}}
// Trigger condition (heuristic detection):
// Return an Object containing a title (or headline) and content (or body)
// The content length must exceed 150 characters

{
  "title": "The Future of AI Agents",          // Title or headline
  "author": "Charm Intelligence",            // Optional metadata
  "body": "Artificial Intelligence is evolving from chatbots to autonomous agents...",  // Main content (long-form, >150 characters)
  "key_takeaways": [                          // Array will be automatically rendered as a list
    "Agents act autonomously",
    "Memory is crucial"
  ]
}
```

### Custom UI (HTML & SVG via Markdown)

The Charm Universal Renderer is built on top of Markdown. The renderer natively supports **HTML and SVG elements**, safely sanitized via DOMPurify. This enables agents to deliver custom UI by returning valid HTML or SVG strings inside their markdown response.

*For code examples on how to dynamically stream HTML or SVG strings from your agent, see the [How to Render Rich UI](/guides/output-renderers) guide.*

> **Security Note:** The Charm Store frontend uses DOMPurify to strip `<script>`, `<iframe>`, and other potentially malicious vectors. Supported capabilities are constrained to static HTML, CSS classes (Tailwind is supported on the Store), and SVGs.

### Best Practices

* **Explicit is better than implicit:** Use `_charm_render_type` whenever possible instead of relying on heuristics.
* **Keep JSON flat:** Minimize deep nesting. The Universal Renderer performs best with flat objects.
* **Use standard keywords:** When using heuristic detection, using standard English field names (e.g., `date` instead of `d_time`) ensures the correct UI is triggered.
* **Mix in Markdown:** You can still use Markdown syntax in JSON string values. The renderer will parse it correctly.
