vtcode_a2a/cli.rs
1//! A2A Protocol CLI commands
2//!
3//! Provides command-line interface for:
4//! - Serving VT Code as an A2A agent
5//! - Discovering remote A2A agents
6//! - Sending tasks to other agents
7//! - Managing A2A agent connections
8
9use clap::{Parser, Subcommand};
10
11/// A2A Protocol commands
12#[derive(Debug, Subcommand, Clone)]
13pub enum A2aCommands {
14 /// Serve VT Code as an A2A agent (requires a2a-server feature)
15 ///
16 /// Starts an HTTP server exposing A2A endpoints:
17 /// - /.well-known/agent-card.json - Agent discovery
18 /// - /a2a - JSON-RPC endpoint for task management
19 /// - /a2a/stream - Server-Sent Events streaming
20 ///
21 /// Examples:
22 /// vtcode a2a serve --port 8080
23 /// vtcode a2a serve --host 0.0.0.0 --port 8080
24 ///
25 /// Set VTCODE_A2A_TOKEN to use a managed token; otherwise one is generated
26 /// and printed when the server starts.
27 Serve {
28 /// Host to bind the server to
29 #[arg(long, default_value = "127.0.0.1")]
30 host: String,
31
32 /// Port to listen on
33 #[arg(long, default_value_t = 8080)]
34 port: u16,
35
36 /// Base URL for the agent (used in agent card)
37 #[arg(long)]
38 base_url: Option<String>,
39
40 /// Enable push notifications via webhooks
41 #[arg(long)]
42 enable_push: bool,
43 },
44
45 /// Discover and display information about a remote A2A agent
46 ///
47 /// Fetches and displays the agent card from the remote agent,
48 /// showing capabilities, skills, and supported features.
49 ///
50 /// Examples:
51 /// vtcode a2a discover <https://agent.example.com>
52 /// vtcode a2a discover <https://localhost:8080>
53 Discover {
54 /// URL of the remote A2A agent
55 agent_url: String,
56 },
57
58 /// Send a task to a remote A2A agent
59 ///
60 /// Sends a message to a remote agent and returns the task result.
61 /// The agent will process the request and return structured results.
62 ///
63 /// Examples:
64 /// vtcode a2a send-task <https://agent.example.com> "Help me refactor this code"
65 /// vtcode a2a send-task <https://localhost:8080> "Explain this error message"
66 SendTask {
67 /// URL of the remote A2A agent
68 agent_url: String,
69
70 /// The task/message to send to the agent
71 message: String,
72
73 /// Wait for task completion and stream progress
74 #[arg(long)]
75 stream: bool,
76
77 /// Optional context ID for conversation tracking
78 #[arg(long)]
79 context_id: Option<String>,
80 },
81
82 /// List active tasks in a running A2A agent
83 ///
84 /// Queries a remote A2A agent for its current and recent tasks.
85 ///
86 /// Examples:
87 /// vtcode a2a list-tasks <https://agent.example.com>
88 /// vtcode a2a list-tasks <https://localhost:8080> --context-id my-conversation
89 ListTasks {
90 /// URL of the remote A2A agent
91 agent_url: String,
92
93 /// Filter by context ID
94 #[arg(long)]
95 context_id: Option<String>,
96
97 /// Maximum number of tasks to return
98 #[arg(long, default_value_t = 50)]
99 limit: u32,
100 },
101
102 /// Get details about a specific task
103 ///
104 /// Retrieves the current status, artifacts, and history of a task.
105 ///
106 /// Examples:
107 /// vtcode a2a get-task <https://agent.example.com> task-123
108 /// vtcode a2a get-task <https://localhost:8080> task-456
109 GetTask {
110 /// URL of the remote A2A agent
111 agent_url: String,
112
113 /// Task ID to retrieve
114 task_id: String,
115 },
116
117 /// Cancel a running task
118 ///
119 /// Requests cancellation of a task that is currently being processed.
120 ///
121 /// Examples:
122 /// vtcode a2a cancel-task <https://agent.example.com> task-123
123 CancelTask {
124 /// URL of the remote A2A agent
125 agent_url: String,
126
127 /// Task ID to cancel
128 task_id: String,
129 },
130}
131
132/// A2A CLI configuration options
133#[derive(Debug, Parser)]
134pub struct A2aServeConfig {
135 /// Host to bind the server to
136 #[arg(long, default_value = "127.0.0.1")]
137 host: String,
138
139 /// Port to listen on
140 #[arg(long, default_value_t = 8080)]
141 port: u16,
142
143 /// Base URL for the agent (used in agent card)
144 #[arg(long)]
145 base_url: Option<String>,
146
147 /// Enable push notifications via webhooks
148 #[arg(long)]
149 enable_push: bool,
150}
151
152#[cfg(test)]
153mod tests {
154 use super::*;
155
156 #[test]
157 fn test_cli_serve_command() {
158 let cmd = A2aCommands::Serve {
159 host: "127.0.0.1".to_string(),
160 port: 8080,
161 base_url: Some("http://localhost:8080".to_string()),
162 enable_push: false,
163 };
164 match cmd {
165 A2aCommands::Serve { port, .. } => assert_eq!(port, 8080),
166 _ => panic!("Wrong command type"),
167 }
168 }
169
170 #[test]
171 fn test_cli_discover_command() {
172 let cmd = A2aCommands::Discover { agent_url: "https://example.com".to_string() };
173 match cmd {
174 A2aCommands::Discover { agent_url } => {
175 assert_eq!(agent_url, "https://example.com")
176 }
177 _ => panic!("Wrong command type"),
178 }
179 }
180}