adk_ui/tools/
render_chart.rs

1use crate::schema::*;
2use adk_core::{Result, Tool, ToolContext};
3use async_trait::async_trait;
4use schemars::JsonSchema;
5use serde::{Deserialize, Serialize};
6use serde_json::Value;
7use std::collections::HashMap;
8use std::sync::Arc;
9
10/// Parameters for the render_chart tool
11#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema)]
12pub struct RenderChartParams {
13    /// Chart title
14    #[serde(default)]
15    pub title: Option<String>,
16    /// Chart type: bar, line, area, or pie
17    #[serde(rename = "type", default = "default_chart_type")]
18    pub chart_type: String,
19    /// Data points - array of objects with x_key and y_key values
20    pub data: Vec<HashMap<String, Value>>,
21    /// Key for x-axis values
22    pub x_key: String,
23    /// Keys for y-axis values (can be multiple for multi-series)
24    pub y_keys: Vec<String>,
25}
26
27fn default_chart_type() -> String {
28    "bar".to_string()
29}
30
31/// Tool for rendering charts and data visualizations.
32///
33/// Creates interactive charts to display data trends, comparisons, and distributions.
34/// Supports multiple chart types and customizable axis labels, legends, and colors.
35///
36/// # Chart Types
37///
38/// - `bar`: Vertical bar chart (default)
39/// - `line`: Line chart for trends
40/// - `area`: Filled area chart
41/// - `pie`: Pie chart for distributions
42///
43/// # Example JSON Parameters
44///
45/// ```json
46/// {
47///   "title": "Monthly Sales",
48///   "type": "line",
49///   "data": [
50///     { "month": "Jan", "sales": 100 },
51///     { "month": "Feb", "sales": 150 },
52///     { "month": "Mar", "sales": 120 }
53///   ],
54///   "x_key": "month",
55///   "y_keys": ["sales"]
56/// }
57/// ```
58pub struct RenderChartTool;
59
60impl RenderChartTool {
61    pub fn new() -> Self {
62        Self
63    }
64}
65
66impl Default for RenderChartTool {
67    fn default() -> Self {
68        Self::new()
69    }
70}
71
72#[async_trait]
73impl Tool for RenderChartTool {
74    fn name(&self) -> &str {
75        "render_chart"
76    }
77
78    fn description(&self) -> &str {
79        "Render a chart to visualize data. Supports bar, line, area, and pie charts. Use this for showing trends, comparisons, or distributions."
80    }
81
82    fn parameters_schema(&self) -> Option<Value> {
83        Some(super::generate_gemini_schema::<RenderChartParams>())
84    }
85
86    async fn execute(&self, _ctx: Arc<dyn ToolContext>, args: Value) -> Result<Value> {
87        let params: RenderChartParams = serde_json::from_value(args)
88            .map_err(|e| adk_core::AdkError::Tool(format!("Invalid parameters: {}", e)))?;
89
90        let kind = match params.chart_type.as_str() {
91            "line" => ChartKind::Line,
92            "area" => ChartKind::Area,
93            "pie" => ChartKind::Pie,
94            _ => ChartKind::Bar,
95        };
96
97        let ui = UiResponse::new(vec![Component::Chart(Chart {
98            id: None,
99            title: params.title,
100            kind,
101            data: params.data,
102            x_key: params.x_key,
103            y_keys: params.y_keys,
104            x_label: None,
105            y_label: None,
106            show_legend: true,
107            colors: None,
108        })]);
109
110        serde_json::to_value(ui)
111            .map_err(|e| adk_core::AdkError::Tool(format!("Failed to serialize UI: {}", e)))
112    }
113}