agent_client_protocol_schema/
agent.rs

1//! Methods and notifications the agent handles/receives.
2//!
3//! This module defines the Agent trait and all associated types for implementing
4//! an AI coding agent that follows the Agent Client Protocol (ACP).
5
6use std::{path::PathBuf, sync::Arc};
7
8use derive_more::{Display, From};
9use schemars::JsonSchema;
10use serde::{Deserialize, Serialize};
11
12use crate::{
13    ClientCapabilities, ContentBlock, ExtNotification, ExtRequest, ExtResponse, IntoOption, Meta,
14    ProtocolVersion, SessionId,
15};
16
17// Initialize
18
19/// Request parameters for the initialize method.
20///
21/// Sent by the client to establish connection and negotiate capabilities.
22///
23/// See protocol docs: [Initialization](https://agentclientprotocol.com/protocol/initialization)
24#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
25#[schemars(extend("x-side" = "agent", "x-method" = INITIALIZE_METHOD_NAME))]
26#[serde(rename_all = "camelCase")]
27#[non_exhaustive]
28pub struct InitializeRequest {
29    /// The latest protocol version supported by the client.
30    pub protocol_version: ProtocolVersion,
31    /// Capabilities supported by the client.
32    #[serde(default)]
33    pub client_capabilities: ClientCapabilities,
34    /// Information about the Client name and version sent to the Agent.
35    ///
36    /// Note: in future versions of the protocol, this will be required.
37    #[serde(skip_serializing_if = "Option::is_none")]
38    pub client_info: Option<Implementation>,
39    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
40    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
41    /// these keys.
42    ///
43    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
44    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
45    pub meta: Option<Meta>,
46}
47
48impl InitializeRequest {
49    #[must_use]
50    pub fn new(protocol_version: ProtocolVersion) -> Self {
51        Self {
52            protocol_version,
53            client_capabilities: ClientCapabilities::default(),
54            client_info: None,
55            meta: None,
56        }
57    }
58
59    /// Capabilities supported by the client.
60    #[must_use]
61    pub fn client_capabilities(mut self, client_capabilities: ClientCapabilities) -> Self {
62        self.client_capabilities = client_capabilities;
63        self
64    }
65
66    /// Information about the Client name and version sent to the Agent.
67    #[must_use]
68    pub fn client_info(mut self, client_info: impl IntoOption<Implementation>) -> Self {
69        self.client_info = client_info.into_option();
70        self
71    }
72
73    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
74    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
75    /// these keys.
76    ///
77    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
78    #[must_use]
79    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
80        self.meta = meta.into_option();
81        self
82    }
83}
84
85/// Response to the `initialize` method.
86///
87/// Contains the negotiated protocol version and agent capabilities.
88///
89/// See protocol docs: [Initialization](https://agentclientprotocol.com/protocol/initialization)
90#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
91#[schemars(extend("x-side" = "agent", "x-method" = INITIALIZE_METHOD_NAME))]
92#[serde(rename_all = "camelCase")]
93#[non_exhaustive]
94pub struct InitializeResponse {
95    /// The protocol version the client specified if supported by the agent,
96    /// or the latest protocol version supported by the agent.
97    ///
98    /// The client should disconnect, if it doesn't support this version.
99    pub protocol_version: ProtocolVersion,
100    /// Capabilities supported by the agent.
101    #[serde(default)]
102    pub agent_capabilities: AgentCapabilities,
103    /// Authentication methods supported by the agent.
104    #[serde(default)]
105    pub auth_methods: Vec<AuthMethod>,
106    /// Information about the Agent name and version sent to the Client.
107    ///
108    /// Note: in future versions of the protocol, this will be required.
109    #[serde(skip_serializing_if = "Option::is_none")]
110    pub agent_info: Option<Implementation>,
111    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
112    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
113    /// these keys.
114    ///
115    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
116    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
117    pub meta: Option<Meta>,
118}
119
120impl InitializeResponse {
121    #[must_use]
122    pub fn new(protocol_version: ProtocolVersion) -> Self {
123        Self {
124            protocol_version,
125            agent_capabilities: AgentCapabilities::default(),
126            auth_methods: vec![],
127            agent_info: None,
128            meta: None,
129        }
130    }
131
132    /// Capabilities supported by the agent.
133    #[must_use]
134    pub fn agent_capabilities(mut self, agent_capabilities: AgentCapabilities) -> Self {
135        self.agent_capabilities = agent_capabilities;
136        self
137    }
138
139    /// Authentication methods supported by the agent.
140    #[must_use]
141    pub fn auth_methods(mut self, auth_methods: Vec<AuthMethod>) -> Self {
142        self.auth_methods = auth_methods;
143        self
144    }
145
146    /// Information about the Agent name and version sent to the Client.
147    #[must_use]
148    pub fn agent_info(mut self, agent_info: impl IntoOption<Implementation>) -> Self {
149        self.agent_info = agent_info.into_option();
150        self
151    }
152
153    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
154    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
155    /// these keys.
156    ///
157    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
158    #[must_use]
159    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
160        self.meta = meta.into_option();
161        self
162    }
163}
164
165/// Metadata about the implementation of the client or agent.
166/// Describes the name and version of an MCP implementation, with an optional
167/// title for UI representation.
168#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
169#[serde(rename_all = "camelCase")]
170#[non_exhaustive]
171pub struct Implementation {
172    /// Intended for programmatic or logical use, but can be used as a display
173    /// name fallback if title isn’t present.
174    pub name: String,
175    /// Intended for UI and end-user contexts — optimized to be human-readable
176    /// and easily understood.
177    ///
178    /// If not provided, the name should be used for display.
179    pub title: Option<String>,
180    /// Version of the implementation. Can be displayed to the user or used
181    /// for debugging or metrics purposes. (e.g. "1.0.0").
182    pub version: String,
183    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
184    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
185    /// these keys.
186    ///
187    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
188    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
189    pub meta: Option<Meta>,
190}
191
192impl Implementation {
193    pub fn new(name: impl Into<String>, version: impl Into<String>) -> Self {
194        Self {
195            name: name.into(),
196            title: None,
197            version: version.into(),
198            meta: None,
199        }
200    }
201
202    /// Intended for UI and end-user contexts — optimized to be human-readable
203    /// and easily understood.
204    ///
205    /// If not provided, the name should be used for display.
206    #[must_use]
207    pub fn title(mut self, title: impl IntoOption<String>) -> Self {
208        self.title = title.into_option();
209        self
210    }
211
212    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
213    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
214    /// these keys.
215    ///
216    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
217    #[must_use]
218    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
219        self.meta = meta.into_option();
220        self
221    }
222}
223
224// Authentication
225
226/// Request parameters for the authenticate method.
227///
228/// Specifies which authentication method to use.
229#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
230#[schemars(extend("x-side" = "agent", "x-method" = AUTHENTICATE_METHOD_NAME))]
231#[serde(rename_all = "camelCase")]
232#[non_exhaustive]
233pub struct AuthenticateRequest {
234    /// The ID of the authentication method to use.
235    /// Must be one of the methods advertised in the initialize response.
236    pub method_id: AuthMethodId,
237    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
238    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
239    /// these keys.
240    ///
241    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
242    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
243    pub meta: Option<Meta>,
244}
245
246impl AuthenticateRequest {
247    #[must_use]
248    pub fn new(method_id: impl Into<AuthMethodId>) -> Self {
249        Self {
250            method_id: method_id.into(),
251            meta: None,
252        }
253    }
254
255    #[must_use]
256    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
257        self.meta = meta.into_option();
258        self
259    }
260}
261
262/// Response to the `authenticate` method.
263#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
264#[serde(rename_all = "camelCase")]
265#[schemars(extend("x-side" = "agent", "x-method" = AUTHENTICATE_METHOD_NAME))]
266#[non_exhaustive]
267pub struct AuthenticateResponse {
268    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
269    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
270    /// these keys.
271    ///
272    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
273    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
274    pub meta: Option<Meta>,
275}
276
277impl AuthenticateResponse {
278    #[must_use]
279    pub fn new() -> Self {
280        Self::default()
281    }
282
283    #[must_use]
284    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
285        self.meta = meta.into_option();
286        self
287    }
288}
289
290#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq, Hash, Display, From)]
291#[serde(transparent)]
292#[from(Arc<str>, String, &'static str)]
293#[non_exhaustive]
294pub struct AuthMethodId(pub Arc<str>);
295
296impl AuthMethodId {
297    pub fn new(id: impl Into<Arc<str>>) -> Self {
298        Self(id.into())
299    }
300}
301
302/// Describes an available authentication method.
303#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
304#[serde(rename_all = "camelCase")]
305#[non_exhaustive]
306pub struct AuthMethod {
307    /// Unique identifier for this authentication method.
308    pub id: AuthMethodId,
309    /// Human-readable name of the authentication method.
310    pub name: String,
311    /// Optional description providing more details about this authentication method.
312    pub description: Option<String>,
313    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
314    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
315    /// these keys.
316    ///
317    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
318    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
319    pub meta: Option<Meta>,
320}
321
322impl AuthMethod {
323    pub fn new(id: impl Into<AuthMethodId>, name: impl Into<String>) -> Self {
324        Self {
325            id: id.into(),
326            name: name.into(),
327            description: None,
328            meta: None,
329        }
330    }
331
332    /// Optional description providing more details about this authentication method.
333    #[must_use]
334    pub fn description(mut self, description: impl IntoOption<String>) -> Self {
335        self.description = description.into_option();
336        self
337    }
338
339    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
340    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
341    /// these keys.
342    ///
343    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
344    #[must_use]
345    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
346        self.meta = meta.into_option();
347        self
348    }
349}
350
351// New session
352
353/// Request parameters for creating a new session.
354///
355/// See protocol docs: [Creating a Session](https://agentclientprotocol.com/protocol/session-setup#creating-a-session)
356#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
357#[schemars(extend("x-side" = "agent", "x-method" = SESSION_NEW_METHOD_NAME))]
358#[serde(rename_all = "camelCase")]
359#[non_exhaustive]
360pub struct NewSessionRequest {
361    /// The working directory for this session. Must be an absolute path.
362    pub cwd: PathBuf,
363    /// List of MCP (Model Context Protocol) servers the agent should connect to.
364    pub mcp_servers: Vec<McpServer>,
365    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
366    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
367    /// these keys.
368    ///
369    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
370    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
371    pub meta: Option<Meta>,
372}
373
374impl NewSessionRequest {
375    pub fn new(cwd: impl Into<PathBuf>) -> Self {
376        Self {
377            cwd: cwd.into(),
378            mcp_servers: vec![],
379            meta: None,
380        }
381    }
382
383    /// List of MCP (Model Context Protocol) servers the agent should connect to.
384    #[must_use]
385    pub fn mcp_servers(mut self, mcp_servers: Vec<McpServer>) -> Self {
386        self.mcp_servers = mcp_servers;
387        self
388    }
389
390    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
391    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
392    /// these keys.
393    ///
394    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
395    #[must_use]
396    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
397        self.meta = meta.into_option();
398        self
399    }
400}
401
402/// Response from creating a new session.
403///
404/// See protocol docs: [Creating a Session](https://agentclientprotocol.com/protocol/session-setup#creating-a-session)
405#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
406#[schemars(extend("x-side" = "agent", "x-method" = SESSION_NEW_METHOD_NAME))]
407#[serde(rename_all = "camelCase")]
408#[non_exhaustive]
409pub struct NewSessionResponse {
410    /// Unique identifier for the created session.
411    ///
412    /// Used in all subsequent requests for this conversation.
413    pub session_id: SessionId,
414    /// Initial mode state if supported by the Agent
415    ///
416    /// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
417    #[serde(skip_serializing_if = "Option::is_none")]
418    pub modes: Option<SessionModeState>,
419    /// **UNSTABLE**
420    ///
421    /// This capability is not part of the spec yet, and may be removed or changed at any point.
422    ///
423    /// Initial model state if supported by the Agent
424    #[cfg(feature = "unstable_session_model")]
425    #[serde(skip_serializing_if = "Option::is_none")]
426    pub models: Option<SessionModelState>,
427    /// **UNSTABLE**
428    ///
429    /// This capability is not part of the spec yet, and may be removed or changed at any point.
430    ///
431    /// Initial session configuration options if supported by the Agent.
432    #[cfg(feature = "unstable_session_config_options")]
433    #[serde(skip_serializing_if = "Option::is_none")]
434    pub config_options: Option<Vec<SessionConfigOption>>,
435    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
436    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
437    /// these keys.
438    ///
439    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
440    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
441    pub meta: Option<Meta>,
442}
443
444impl NewSessionResponse {
445    #[must_use]
446    pub fn new(session_id: impl Into<SessionId>) -> Self {
447        Self {
448            session_id: session_id.into(),
449            modes: None,
450            #[cfg(feature = "unstable_session_model")]
451            models: None,
452            #[cfg(feature = "unstable_session_config_options")]
453            config_options: None,
454            meta: None,
455        }
456    }
457
458    /// Initial mode state if supported by the Agent
459    ///
460    /// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
461    #[must_use]
462    pub fn modes(mut self, modes: impl IntoOption<SessionModeState>) -> Self {
463        self.modes = modes.into_option();
464        self
465    }
466
467    /// **UNSTABLE**
468    ///
469    /// This capability is not part of the spec yet, and may be removed or changed at any point.
470    ///
471    /// Initial model state if supported by the Agent
472    #[cfg(feature = "unstable_session_model")]
473    #[must_use]
474    pub fn models(mut self, models: impl IntoOption<SessionModelState>) -> Self {
475        self.models = models.into_option();
476        self
477    }
478
479    /// **UNSTABLE**
480    ///
481    /// This capability is not part of the spec yet, and may be removed or changed at any point.
482    ///
483    /// Initial session configuration options if supported by the Agent.
484    #[cfg(feature = "unstable_session_config_options")]
485    #[must_use]
486    pub fn config_options(
487        mut self,
488        config_options: impl IntoOption<Vec<SessionConfigOption>>,
489    ) -> Self {
490        self.config_options = config_options.into_option();
491        self
492    }
493
494    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
495    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
496    /// these keys.
497    ///
498    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
499    #[must_use]
500    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
501        self.meta = meta.into_option();
502        self
503    }
504}
505
506// Load session
507
508/// Request parameters for loading an existing session.
509///
510/// Only available if the Agent supports the `loadSession` capability.
511///
512/// See protocol docs: [Loading Sessions](https://agentclientprotocol.com/protocol/session-setup#loading-sessions)
513#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
514#[schemars(extend("x-side" = "agent", "x-method" = SESSION_LOAD_METHOD_NAME))]
515#[serde(rename_all = "camelCase")]
516#[non_exhaustive]
517pub struct LoadSessionRequest {
518    /// List of MCP servers to connect to for this session.
519    pub mcp_servers: Vec<McpServer>,
520    /// The working directory for this session.
521    pub cwd: PathBuf,
522    /// The ID of the session to load.
523    pub session_id: SessionId,
524    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
525    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
526    /// these keys.
527    ///
528    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
529    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
530    pub meta: Option<Meta>,
531}
532
533impl LoadSessionRequest {
534    pub fn new(session_id: impl Into<SessionId>, cwd: impl Into<PathBuf>) -> Self {
535        Self {
536            mcp_servers: vec![],
537            cwd: cwd.into(),
538            session_id: session_id.into(),
539            meta: None,
540        }
541    }
542
543    /// List of MCP servers to connect to for this session.
544    #[must_use]
545    pub fn mcp_servers(mut self, mcp_servers: Vec<McpServer>) -> Self {
546        self.mcp_servers = mcp_servers;
547        self
548    }
549
550    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
551    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
552    /// these keys.
553    ///
554    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
555    #[must_use]
556    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
557        self.meta = meta.into_option();
558        self
559    }
560}
561
562/// Response from loading an existing session.
563#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
564#[schemars(extend("x-side" = "agent", "x-method" = SESSION_LOAD_METHOD_NAME))]
565#[serde(rename_all = "camelCase")]
566#[non_exhaustive]
567pub struct LoadSessionResponse {
568    /// Initial mode state if supported by the Agent
569    ///
570    /// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
571    #[serde(default, skip_serializing_if = "Option::is_none")]
572    pub modes: Option<SessionModeState>,
573    /// **UNSTABLE**
574    ///
575    /// This capability is not part of the spec yet, and may be removed or changed at any point.
576    ///
577    /// Initial model state if supported by the Agent
578    #[cfg(feature = "unstable_session_model")]
579    #[serde(default, skip_serializing_if = "Option::is_none")]
580    pub models: Option<SessionModelState>,
581    /// **UNSTABLE**
582    ///
583    /// This capability is not part of the spec yet, and may be removed or changed at any point.
584    ///
585    /// Initial session configuration options if supported by the Agent.
586    #[cfg(feature = "unstable_session_config_options")]
587    #[serde(default, skip_serializing_if = "Option::is_none")]
588    pub config_options: Option<Vec<SessionConfigOption>>,
589    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
590    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
591    /// these keys.
592    ///
593    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
594    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
595    pub meta: Option<Meta>,
596}
597
598impl LoadSessionResponse {
599    #[must_use]
600    pub fn new() -> Self {
601        Self::default()
602    }
603
604    /// Initial mode state if supported by the Agent
605    ///
606    /// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
607    #[must_use]
608    pub fn modes(mut self, modes: impl IntoOption<SessionModeState>) -> Self {
609        self.modes = modes.into_option();
610        self
611    }
612
613    /// **UNSTABLE**
614    ///
615    /// This capability is not part of the spec yet, and may be removed or changed at any point.
616    ///
617    /// Initial model state if supported by the Agent
618    #[cfg(feature = "unstable_session_model")]
619    #[must_use]
620    pub fn models(mut self, models: impl IntoOption<SessionModelState>) -> Self {
621        self.models = models.into_option();
622        self
623    }
624
625    /// **UNSTABLE**
626    ///
627    /// This capability is not part of the spec yet, and may be removed or changed at any point.
628    ///
629    /// Initial session configuration options if supported by the Agent.
630    #[cfg(feature = "unstable_session_config_options")]
631    #[must_use]
632    pub fn config_options(
633        mut self,
634        config_options: impl IntoOption<Vec<SessionConfigOption>>,
635    ) -> Self {
636        self.config_options = config_options.into_option();
637        self
638    }
639
640    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
641    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
642    /// these keys.
643    ///
644    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
645    #[must_use]
646    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
647        self.meta = meta.into_option();
648        self
649    }
650}
651
652// Fork session
653
654/// **UNSTABLE**
655///
656/// This capability is not part of the spec yet, and may be removed or changed at any point.
657///
658/// Request parameters for forking an existing session.
659///
660/// Creates a new session based on the context of an existing one, allowing
661/// operations like generating summaries without affecting the original session's history.
662///
663/// Only available if the Agent supports the `session.fork` capability.
664#[cfg(feature = "unstable_session_fork")]
665#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
666#[schemars(extend("x-side" = "agent", "x-method" = SESSION_FORK_METHOD_NAME))]
667#[serde(rename_all = "camelCase")]
668#[non_exhaustive]
669pub struct ForkSessionRequest {
670    /// The ID of the session to fork.
671    pub session_id: SessionId,
672    /// The working directory for this session.
673    pub cwd: PathBuf,
674    /// List of MCP servers to connect to for this session.
675    #[serde(default, skip_serializing_if = "Vec::is_empty")]
676    pub mcp_servers: Vec<McpServer>,
677    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
678    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
679    /// these keys.
680    ///
681    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
682    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
683    pub meta: Option<Meta>,
684}
685
686#[cfg(feature = "unstable_session_fork")]
687impl ForkSessionRequest {
688    pub fn new(session_id: impl Into<SessionId>, cwd: impl Into<PathBuf>) -> Self {
689        Self {
690            session_id: session_id.into(),
691            cwd: cwd.into(),
692            mcp_servers: vec![],
693            meta: None,
694        }
695    }
696
697    /// List of MCP servers to connect to for this session.
698    #[must_use]
699    pub fn mcp_servers(mut self, mcp_servers: Vec<McpServer>) -> Self {
700        self.mcp_servers = mcp_servers;
701        self
702    }
703
704    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
705    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
706    /// these keys.
707    ///
708    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
709    #[must_use]
710    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
711        self.meta = meta.into_option();
712        self
713    }
714}
715
716/// **UNSTABLE**
717///
718/// This capability is not part of the spec yet, and may be removed or changed at any point.
719///
720/// Response from forking an existing session.
721#[cfg(feature = "unstable_session_fork")]
722#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
723#[schemars(extend("x-side" = "agent", "x-method" = SESSION_FORK_METHOD_NAME))]
724#[serde(rename_all = "camelCase")]
725#[non_exhaustive]
726pub struct ForkSessionResponse {
727    /// Unique identifier for the newly created forked session.
728    pub session_id: SessionId,
729    /// Initial mode state if supported by the Agent
730    ///
731    /// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
732    #[serde(skip_serializing_if = "Option::is_none")]
733    pub modes: Option<SessionModeState>,
734    /// **UNSTABLE**
735    ///
736    /// This capability is not part of the spec yet, and may be removed or changed at any point.
737    ///
738    /// Initial model state if supported by the Agent
739    #[cfg(feature = "unstable_session_model")]
740    #[serde(skip_serializing_if = "Option::is_none")]
741    pub models: Option<SessionModelState>,
742    /// **UNSTABLE**
743    ///
744    /// This capability is not part of the spec yet, and may be removed or changed at any point.
745    ///
746    /// Initial session configuration options if supported by the Agent.
747    #[cfg(feature = "unstable_session_config_options")]
748    #[serde(skip_serializing_if = "Option::is_none")]
749    pub config_options: Option<Vec<SessionConfigOption>>,
750    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
751    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
752    /// these keys.
753    ///
754    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
755    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
756    pub meta: Option<Meta>,
757}
758
759#[cfg(feature = "unstable_session_fork")]
760impl ForkSessionResponse {
761    #[must_use]
762    pub fn new(session_id: impl Into<SessionId>) -> Self {
763        Self {
764            session_id: session_id.into(),
765            modes: None,
766            #[cfg(feature = "unstable_session_model")]
767            models: None,
768            #[cfg(feature = "unstable_session_config_options")]
769            config_options: None,
770            meta: None,
771        }
772    }
773
774    /// Initial mode state if supported by the Agent
775    ///
776    /// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
777    #[must_use]
778    pub fn modes(mut self, modes: impl IntoOption<SessionModeState>) -> Self {
779        self.modes = modes.into_option();
780        self
781    }
782
783    /// **UNSTABLE**
784    ///
785    /// This capability is not part of the spec yet, and may be removed or changed at any point.
786    ///
787    /// Initial model state if supported by the Agent
788    #[cfg(feature = "unstable_session_model")]
789    #[must_use]
790    pub fn models(mut self, models: impl IntoOption<SessionModelState>) -> Self {
791        self.models = models.into_option();
792        self
793    }
794
795    /// **UNSTABLE**
796    ///
797    /// This capability is not part of the spec yet, and may be removed or changed at any point.
798    ///
799    /// Initial session configuration options if supported by the Agent.
800    #[cfg(feature = "unstable_session_config_options")]
801    #[must_use]
802    pub fn config_options(
803        mut self,
804        config_options: impl IntoOption<Vec<SessionConfigOption>>,
805    ) -> Self {
806        self.config_options = config_options.into_option();
807        self
808    }
809
810    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
811    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
812    /// these keys.
813    ///
814    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
815    #[must_use]
816    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
817        self.meta = meta.into_option();
818        self
819    }
820}
821
822// Resume session
823
824/// **UNSTABLE**
825///
826/// This capability is not part of the spec yet, and may be removed or changed at any point.
827///
828/// Request parameters for resuming an existing session.
829///
830/// Resumes an existing session without returning previous messages (unlike `session/load`).
831/// This is useful for agents that can resume sessions but don't implement full session loading.
832///
833/// Only available if the Agent supports the `session.resume` capability.
834#[cfg(feature = "unstable_session_resume")]
835#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
836#[schemars(extend("x-side" = "agent", "x-method" = SESSION_RESUME_METHOD_NAME))]
837#[serde(rename_all = "camelCase")]
838#[non_exhaustive]
839pub struct ResumeSessionRequest {
840    /// The ID of the session to resume.
841    pub session_id: SessionId,
842    /// The working directory for this session.
843    pub cwd: PathBuf,
844    /// List of MCP servers to connect to for this session.
845    #[serde(default, skip_serializing_if = "Vec::is_empty")]
846    pub mcp_servers: Vec<McpServer>,
847    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
848    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
849    /// these keys.
850    ///
851    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
852    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
853    pub meta: Option<Meta>,
854}
855
856#[cfg(feature = "unstable_session_resume")]
857impl ResumeSessionRequest {
858    pub fn new(session_id: impl Into<SessionId>, cwd: impl Into<PathBuf>) -> Self {
859        Self {
860            session_id: session_id.into(),
861            cwd: cwd.into(),
862            mcp_servers: vec![],
863            meta: None,
864        }
865    }
866
867    /// List of MCP servers to connect to for this session.
868    #[must_use]
869    pub fn mcp_servers(mut self, mcp_servers: Vec<McpServer>) -> Self {
870        self.mcp_servers = mcp_servers;
871        self
872    }
873
874    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
875    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
876    /// these keys.
877    ///
878    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
879    #[must_use]
880    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
881        self.meta = meta.into_option();
882        self
883    }
884}
885
886/// **UNSTABLE**
887///
888/// This capability is not part of the spec yet, and may be removed or changed at any point.
889///
890/// Response from resuming an existing session.
891#[cfg(feature = "unstable_session_resume")]
892#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
893#[schemars(extend("x-side" = "agent", "x-method" = SESSION_RESUME_METHOD_NAME))]
894#[serde(rename_all = "camelCase")]
895#[non_exhaustive]
896pub struct ResumeSessionResponse {
897    /// Initial mode state if supported by the Agent
898    ///
899    /// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
900    #[serde(default, skip_serializing_if = "Option::is_none")]
901    pub modes: Option<SessionModeState>,
902    /// **UNSTABLE**
903    ///
904    /// This capability is not part of the spec yet, and may be removed or changed at any point.
905    ///
906    /// Initial model state if supported by the Agent
907    #[cfg(feature = "unstable_session_model")]
908    #[serde(default, skip_serializing_if = "Option::is_none")]
909    pub models: Option<SessionModelState>,
910    /// **UNSTABLE**
911    ///
912    /// This capability is not part of the spec yet, and may be removed or changed at any point.
913    ///
914    /// Initial session configuration options if supported by the Agent.
915    #[cfg(feature = "unstable_session_config_options")]
916    #[serde(default, skip_serializing_if = "Option::is_none")]
917    pub config_options: Option<Vec<SessionConfigOption>>,
918    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
919    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
920    /// these keys.
921    ///
922    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
923    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
924    pub meta: Option<Meta>,
925}
926
927#[cfg(feature = "unstable_session_resume")]
928impl ResumeSessionResponse {
929    #[must_use]
930    pub fn new() -> Self {
931        Self::default()
932    }
933
934    /// Initial mode state if supported by the Agent
935    ///
936    /// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
937    #[must_use]
938    pub fn modes(mut self, modes: impl IntoOption<SessionModeState>) -> Self {
939        self.modes = modes.into_option();
940        self
941    }
942
943    /// **UNSTABLE**
944    ///
945    /// This capability is not part of the spec yet, and may be removed or changed at any point.
946    ///
947    /// Initial model state if supported by the Agent
948    #[cfg(feature = "unstable_session_model")]
949    #[must_use]
950    pub fn models(mut self, models: impl IntoOption<SessionModelState>) -> Self {
951        self.models = models.into_option();
952        self
953    }
954
955    /// **UNSTABLE**
956    ///
957    /// This capability is not part of the spec yet, and may be removed or changed at any point.
958    ///
959    /// Initial session configuration options if supported by the Agent.
960    #[cfg(feature = "unstable_session_config_options")]
961    #[must_use]
962    pub fn config_options(
963        mut self,
964        config_options: impl IntoOption<Vec<SessionConfigOption>>,
965    ) -> Self {
966        self.config_options = config_options.into_option();
967        self
968    }
969
970    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
971    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
972    /// these keys.
973    ///
974    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
975    #[must_use]
976    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
977        self.meta = meta.into_option();
978        self
979    }
980}
981
982// List sessions
983
984/// **UNSTABLE**
985///
986/// This capability is not part of the spec yet, and may be removed or changed at any point.
987///
988/// Request parameters for listing existing sessions.
989///
990/// Only available if the Agent supports the `listSessions` capability.
991#[cfg(feature = "unstable_session_list")]
992#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
993#[schemars(extend("x-side" = "agent", "x-method" = SESSION_LIST_METHOD_NAME))]
994#[serde(rename_all = "camelCase")]
995#[non_exhaustive]
996pub struct ListSessionsRequest {
997    /// Filter sessions by working directory. Must be an absolute path.
998    #[serde(skip_serializing_if = "Option::is_none")]
999    pub cwd: Option<PathBuf>,
1000    /// Opaque cursor token from a previous response's nextCursor field for cursor-based pagination
1001    #[serde(skip_serializing_if = "Option::is_none")]
1002    pub cursor: Option<String>,
1003    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1004    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1005    /// these keys.
1006    ///
1007    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1008    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1009    pub meta: Option<Meta>,
1010}
1011
1012#[cfg(feature = "unstable_session_list")]
1013impl ListSessionsRequest {
1014    #[must_use]
1015    pub fn new() -> Self {
1016        Self::default()
1017    }
1018
1019    /// Filter sessions by working directory. Must be an absolute path.
1020    #[must_use]
1021    pub fn cwd(mut self, cwd: impl IntoOption<PathBuf>) -> Self {
1022        self.cwd = cwd.into_option();
1023        self
1024    }
1025
1026    /// Opaque cursor token from a previous response's nextCursor field for cursor-based pagination
1027    #[must_use]
1028    pub fn cursor(mut self, cursor: impl IntoOption<String>) -> Self {
1029        self.cursor = cursor.into_option();
1030        self
1031    }
1032
1033    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1034    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1035    /// these keys.
1036    ///
1037    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1038    #[must_use]
1039    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1040        self.meta = meta.into_option();
1041        self
1042    }
1043}
1044
1045/// **UNSTABLE**
1046///
1047/// This capability is not part of the spec yet, and may be removed or changed at any point.
1048///
1049/// Response from listing sessions.
1050#[cfg(feature = "unstable_session_list")]
1051#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1052#[schemars(extend("x-side" = "agent", "x-method" = SESSION_LIST_METHOD_NAME))]
1053#[serde(rename_all = "camelCase")]
1054#[non_exhaustive]
1055pub struct ListSessionsResponse {
1056    /// Array of session information objects
1057    pub sessions: Vec<SessionInfo>,
1058    /// Opaque cursor token. If present, pass this in the next request's cursor parameter
1059    /// to fetch the next page. If absent, there are no more results.
1060    #[serde(skip_serializing_if = "Option::is_none")]
1061    pub next_cursor: Option<String>,
1062    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1063    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1064    /// these keys.
1065    ///
1066    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1067    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1068    pub meta: Option<Meta>,
1069}
1070
1071#[cfg(feature = "unstable_session_list")]
1072impl ListSessionsResponse {
1073    #[must_use]
1074    pub fn new(sessions: Vec<SessionInfo>) -> Self {
1075        Self {
1076            sessions,
1077            next_cursor: None,
1078            meta: None,
1079        }
1080    }
1081
1082    #[must_use]
1083    pub fn next_cursor(mut self, next_cursor: impl IntoOption<String>) -> Self {
1084        self.next_cursor = next_cursor.into_option();
1085        self
1086    }
1087
1088    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1089    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1090    /// these keys.
1091    ///
1092    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1093    #[must_use]
1094    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1095        self.meta = meta.into_option();
1096        self
1097    }
1098}
1099
1100/// **UNSTABLE**
1101///
1102/// This capability is not part of the spec yet, and may be removed or changed at any point.
1103///
1104/// Information about a session returned by session/list
1105#[cfg(feature = "unstable_session_list")]
1106#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1107#[serde(rename_all = "camelCase")]
1108#[non_exhaustive]
1109pub struct SessionInfo {
1110    /// Unique identifier for the session
1111    pub session_id: SessionId,
1112    /// The working directory for this session. Must be an absolute path.
1113    pub cwd: PathBuf,
1114    /// Human-readable title for the session
1115    #[serde(skip_serializing_if = "Option::is_none")]
1116    pub title: Option<String>,
1117    /// ISO 8601 timestamp of last activity
1118    #[serde(skip_serializing_if = "Option::is_none")]
1119    pub updated_at: Option<String>,
1120    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1121    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1122    /// these keys.
1123    ///
1124    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1125    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1126    pub meta: Option<Meta>,
1127}
1128
1129#[cfg(feature = "unstable_session_list")]
1130impl SessionInfo {
1131    pub fn new(session_id: impl Into<SessionId>, cwd: impl Into<PathBuf>) -> Self {
1132        Self {
1133            session_id: session_id.into(),
1134            cwd: cwd.into(),
1135            title: None,
1136            updated_at: None,
1137            meta: None,
1138        }
1139    }
1140
1141    /// Human-readable title for the session
1142    #[must_use]
1143    pub fn title(mut self, title: impl IntoOption<String>) -> Self {
1144        self.title = title.into_option();
1145        self
1146    }
1147
1148    /// ISO 8601 timestamp of last activity
1149    #[must_use]
1150    pub fn updated_at(mut self, updated_at: impl IntoOption<String>) -> Self {
1151        self.updated_at = updated_at.into_option();
1152        self
1153    }
1154
1155    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1156    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1157    /// these keys.
1158    ///
1159    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1160    #[must_use]
1161    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1162        self.meta = meta.into_option();
1163        self
1164    }
1165}
1166
1167// Session modes
1168
1169/// The set of modes and the one currently active.
1170#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1171#[serde(rename_all = "camelCase")]
1172#[non_exhaustive]
1173pub struct SessionModeState {
1174    /// The current mode the Agent is in.
1175    pub current_mode_id: SessionModeId,
1176    /// The set of modes that the Agent can operate in
1177    pub available_modes: Vec<SessionMode>,
1178    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1179    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1180    /// these keys.
1181    ///
1182    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1183    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1184    pub meta: Option<Meta>,
1185}
1186
1187impl SessionModeState {
1188    #[must_use]
1189    pub fn new(
1190        current_mode_id: impl Into<SessionModeId>,
1191        available_modes: Vec<SessionMode>,
1192    ) -> Self {
1193        Self {
1194            current_mode_id: current_mode_id.into(),
1195            available_modes,
1196            meta: None,
1197        }
1198    }
1199
1200    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1201    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1202    /// these keys.
1203    ///
1204    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1205    #[must_use]
1206    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1207        self.meta = meta.into_option();
1208        self
1209    }
1210}
1211
1212/// A mode the agent can operate in.
1213///
1214/// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
1215#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1216#[serde(rename_all = "camelCase")]
1217#[non_exhaustive]
1218pub struct SessionMode {
1219    pub id: SessionModeId,
1220    pub name: String,
1221    #[serde(default, skip_serializing_if = "Option::is_none")]
1222    pub description: Option<String>,
1223    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1224    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1225    /// these keys.
1226    ///
1227    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1228    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1229    pub meta: Option<Meta>,
1230}
1231
1232impl SessionMode {
1233    pub fn new(id: impl Into<SessionModeId>, name: impl Into<String>) -> Self {
1234        Self {
1235            id: id.into(),
1236            name: name.into(),
1237            description: None,
1238            meta: None,
1239        }
1240    }
1241
1242    #[must_use]
1243    pub fn description(mut self, description: impl IntoOption<String>) -> Self {
1244        self.description = description.into_option();
1245        self
1246    }
1247
1248    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1249    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1250    /// these keys.
1251    ///
1252    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1253    #[must_use]
1254    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1255        self.meta = meta.into_option();
1256        self
1257    }
1258}
1259
1260/// Unique identifier for a Session Mode.
1261#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq, Hash, From, Display)]
1262#[serde(transparent)]
1263#[from(Arc<str>, String, &'static str)]
1264#[non_exhaustive]
1265pub struct SessionModeId(pub Arc<str>);
1266
1267impl SessionModeId {
1268    pub fn new(id: impl Into<Arc<str>>) -> Self {
1269        Self(id.into())
1270    }
1271}
1272
1273/// Request parameters for setting a session mode.
1274#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1275#[schemars(extend("x-side" = "agent", "x-method" = SESSION_SET_MODE_METHOD_NAME))]
1276#[serde(rename_all = "camelCase")]
1277#[non_exhaustive]
1278pub struct SetSessionModeRequest {
1279    /// The ID of the session to set the mode for.
1280    pub session_id: SessionId,
1281    /// The ID of the mode to set.
1282    pub mode_id: SessionModeId,
1283    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1284    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1285    /// these keys.
1286    ///
1287    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1288    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1289    pub meta: Option<Meta>,
1290}
1291
1292impl SetSessionModeRequest {
1293    #[must_use]
1294    pub fn new(session_id: impl Into<SessionId>, mode_id: impl Into<SessionModeId>) -> Self {
1295        Self {
1296            session_id: session_id.into(),
1297            mode_id: mode_id.into(),
1298            meta: None,
1299        }
1300    }
1301
1302    #[must_use]
1303    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1304        self.meta = meta.into_option();
1305        self
1306    }
1307}
1308
1309/// Response to `session/set_mode` method.
1310#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1311#[schemars(extend("x-side" = "agent", "x-method" = SESSION_SET_MODE_METHOD_NAME))]
1312#[serde(rename_all = "camelCase")]
1313#[non_exhaustive]
1314pub struct SetSessionModeResponse {
1315    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1316    pub meta: Option<Meta>,
1317}
1318
1319impl SetSessionModeResponse {
1320    #[must_use]
1321    pub fn new() -> Self {
1322        Self::default()
1323    }
1324
1325    #[must_use]
1326    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1327        self.meta = meta.into_option();
1328        self
1329    }
1330}
1331
1332// Session config options
1333
1334/// **UNSTABLE**
1335///
1336/// This capability is not part of the spec yet, and may be removed or changed at any point.
1337///
1338/// Unique identifier for a session configuration option.
1339#[cfg(feature = "unstable_session_config_options")]
1340#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq, Hash, From, Display)]
1341#[serde(transparent)]
1342#[from(Arc<str>, String, &'static str)]
1343#[non_exhaustive]
1344pub struct SessionConfigId(pub Arc<str>);
1345
1346#[cfg(feature = "unstable_session_config_options")]
1347impl SessionConfigId {
1348    pub fn new(id: impl Into<Arc<str>>) -> Self {
1349        Self(id.into())
1350    }
1351}
1352
1353/// **UNSTABLE**
1354///
1355/// This capability is not part of the spec yet, and may be removed or changed at any point.
1356///
1357/// Unique identifier for a session configuration option value.
1358#[cfg(feature = "unstable_session_config_options")]
1359#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq, Hash, From, Display)]
1360#[serde(transparent)]
1361#[from(Arc<str>, String, &'static str)]
1362#[non_exhaustive]
1363pub struct SessionConfigValueId(pub Arc<str>);
1364
1365#[cfg(feature = "unstable_session_config_options")]
1366impl SessionConfigValueId {
1367    pub fn new(id: impl Into<Arc<str>>) -> Self {
1368        Self(id.into())
1369    }
1370}
1371
1372/// **UNSTABLE**
1373///
1374/// This capability is not part of the spec yet, and may be removed or changed at any point.
1375///
1376/// Unique identifier for a session configuration option value group.
1377#[cfg(feature = "unstable_session_config_options")]
1378#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq, Hash, From, Display)]
1379#[serde(transparent)]
1380#[from(Arc<str>, String, &'static str)]
1381#[non_exhaustive]
1382pub struct SessionConfigGroupId(pub Arc<str>);
1383
1384#[cfg(feature = "unstable_session_config_options")]
1385impl SessionConfigGroupId {
1386    pub fn new(id: impl Into<Arc<str>>) -> Self {
1387        Self(id.into())
1388    }
1389}
1390
1391/// **UNSTABLE**
1392///
1393/// This capability is not part of the spec yet, and may be removed or changed at any point.
1394///
1395/// A possible value for a session configuration option.
1396#[cfg(feature = "unstable_session_config_options")]
1397#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1398#[serde(rename_all = "camelCase")]
1399#[non_exhaustive]
1400pub struct SessionConfigSelectOption {
1401    /// Unique identifier for this option value.
1402    pub value: SessionConfigValueId,
1403    /// Human-readable label for this option value.
1404    pub name: String,
1405    /// Optional description for this option value.
1406    #[serde(default, skip_serializing_if = "Option::is_none")]
1407    pub description: Option<String>,
1408    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1409    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1410    /// these keys.
1411    ///
1412    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1413    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1414    pub meta: Option<Meta>,
1415}
1416
1417#[cfg(feature = "unstable_session_config_options")]
1418impl SessionConfigSelectOption {
1419    #[must_use]
1420    pub fn new(value: impl Into<SessionConfigValueId>, name: impl Into<String>) -> Self {
1421        Self {
1422            value: value.into(),
1423            name: name.into(),
1424            description: None,
1425            meta: None,
1426        }
1427    }
1428
1429    #[must_use]
1430    pub fn description(mut self, description: impl IntoOption<String>) -> Self {
1431        self.description = description.into_option();
1432        self
1433    }
1434
1435    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1436    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1437    /// these keys.
1438    ///
1439    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1440    #[must_use]
1441    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1442        self.meta = meta.into_option();
1443        self
1444    }
1445}
1446
1447/// **UNSTABLE**
1448///
1449/// This capability is not part of the spec yet, and may be removed or changed at any point.
1450///
1451/// A group of possible values for a session configuration option.
1452#[cfg(feature = "unstable_session_config_options")]
1453#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1454#[serde(rename_all = "camelCase")]
1455#[non_exhaustive]
1456pub struct SessionConfigSelectGroup {
1457    /// Unique identifier for this group.
1458    pub group: SessionConfigGroupId,
1459    /// Human-readable label for this group.
1460    pub name: String,
1461    /// The set of option values in this group.
1462    pub options: Vec<SessionConfigSelectOption>,
1463    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1464    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1465    /// these keys.
1466    ///
1467    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1468    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1469    pub meta: Option<Meta>,
1470}
1471
1472#[cfg(feature = "unstable_session_config_options")]
1473impl SessionConfigSelectGroup {
1474    #[must_use]
1475    pub fn new(
1476        group: impl Into<SessionConfigGroupId>,
1477        name: impl Into<String>,
1478        options: Vec<SessionConfigSelectOption>,
1479    ) -> Self {
1480        Self {
1481            group: group.into(),
1482            name: name.into(),
1483            options,
1484            meta: None,
1485        }
1486    }
1487
1488    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1489    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1490    /// these keys.
1491    ///
1492    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1493    #[must_use]
1494    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1495        self.meta = meta.into_option();
1496        self
1497    }
1498}
1499
1500/// **UNSTABLE**
1501///
1502/// This capability is not part of the spec yet, and may be removed or changed at any point.
1503///
1504/// Possible values for a session configuration option.
1505#[cfg(feature = "unstable_session_config_options")]
1506#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1507#[serde(untagged)]
1508#[non_exhaustive]
1509pub enum SessionConfigSelectOptions {
1510    /// A flat list of options with no grouping.
1511    Ungrouped(Vec<SessionConfigSelectOption>),
1512    /// A list of options grouped under headers.
1513    Grouped(Vec<SessionConfigSelectGroup>),
1514}
1515
1516#[cfg(feature = "unstable_session_config_options")]
1517impl From<Vec<SessionConfigSelectOption>> for SessionConfigSelectOptions {
1518    fn from(options: Vec<SessionConfigSelectOption>) -> Self {
1519        SessionConfigSelectOptions::Ungrouped(options)
1520    }
1521}
1522
1523#[cfg(feature = "unstable_session_config_options")]
1524impl From<Vec<SessionConfigSelectGroup>> for SessionConfigSelectOptions {
1525    fn from(groups: Vec<SessionConfigSelectGroup>) -> Self {
1526        SessionConfigSelectOptions::Grouped(groups)
1527    }
1528}
1529
1530/// **UNSTABLE**
1531///
1532/// This capability is not part of the spec yet, and may be removed or changed at any point.
1533///
1534/// A single-value selector (dropdown) session configuration option payload.
1535#[cfg(feature = "unstable_session_config_options")]
1536#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1537#[serde(rename_all = "camelCase")]
1538#[non_exhaustive]
1539pub struct SessionConfigSelect {
1540    /// The currently selected value.
1541    pub current_value: SessionConfigValueId,
1542    /// The set of selectable options.
1543    pub options: SessionConfigSelectOptions,
1544}
1545
1546#[cfg(feature = "unstable_session_config_options")]
1547impl SessionConfigSelect {
1548    #[must_use]
1549    pub fn new(
1550        current_value: impl Into<SessionConfigValueId>,
1551        options: impl Into<SessionConfigSelectOptions>,
1552    ) -> Self {
1553        Self {
1554            current_value: current_value.into(),
1555            options: options.into(),
1556        }
1557    }
1558}
1559
1560/// **UNSTABLE**
1561///
1562/// This capability is not part of the spec yet, and may be removed or changed at any point.
1563///
1564/// Semantic category for a session configuration option.
1565///
1566/// This is intended to help Clients distinguish broadly common selectors (e.g. model selector vs
1567/// session mode selector vs thought/reasoning level) for UX purposes (keyboard shortcuts, icons,
1568/// placement). It MUST NOT be required for correctness. Clients MUST handle missing or unknown
1569/// categories gracefully (treat as `Other`).
1570#[cfg(feature = "unstable_session_config_options")]
1571#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1572#[serde(rename_all = "snake_case")]
1573#[non_exhaustive]
1574pub enum SessionConfigOptionCategory {
1575    /// Session mode selector.
1576    Mode,
1577    /// Model selector.
1578    Model,
1579    /// Thought/reasoning level selector.
1580    ThoughtLevel,
1581    /// Unknown / uncategorized selector.
1582    #[serde(other)]
1583    Other,
1584}
1585
1586/// **UNSTABLE**
1587///
1588/// This capability is not part of the spec yet, and may be removed or changed at any point.
1589///
1590/// Type-specific session configuration option payload.
1591#[cfg(feature = "unstable_session_config_options")]
1592#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1593#[serde(tag = "type", rename_all = "snake_case")]
1594#[schemars(extend("discriminator" = {"propertyName": "type"}))]
1595#[non_exhaustive]
1596pub enum SessionConfigKind {
1597    /// Single-value selector (dropdown).
1598    Select(SessionConfigSelect),
1599}
1600
1601/// **UNSTABLE**
1602///
1603/// This capability is not part of the spec yet, and may be removed or changed at any point.
1604///
1605/// A session configuration option selector and its current state.
1606#[cfg(feature = "unstable_session_config_options")]
1607#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1608#[serde(rename_all = "camelCase")]
1609#[non_exhaustive]
1610pub struct SessionConfigOption {
1611    /// Unique identifier for the configuration option.
1612    pub id: SessionConfigId,
1613    /// Human-readable label for the option.
1614    pub name: String,
1615    /// Optional description for the Client to display to the user.
1616    #[serde(default, skip_serializing_if = "Option::is_none")]
1617    pub description: Option<String>,
1618    /// Optional semantic category for this option (UX only).
1619    #[serde(default, skip_serializing_if = "Option::is_none")]
1620    pub category: Option<SessionConfigOptionCategory>,
1621    /// Type-specific fields for this configuration option.
1622    #[serde(flatten)]
1623    pub kind: SessionConfigKind,
1624    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1625    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1626    /// these keys.
1627    ///
1628    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1629    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1630    pub meta: Option<Meta>,
1631}
1632
1633#[cfg(feature = "unstable_session_config_options")]
1634impl SessionConfigOption {
1635    #[must_use]
1636    pub fn new(
1637        id: impl Into<SessionConfigId>,
1638        name: impl Into<String>,
1639        kind: SessionConfigKind,
1640    ) -> Self {
1641        Self {
1642            id: id.into(),
1643            name: name.into(),
1644            description: None,
1645            category: None,
1646            kind,
1647            meta: None,
1648        }
1649    }
1650
1651    #[must_use]
1652    pub fn select(
1653        id: impl Into<SessionConfigId>,
1654        name: impl Into<String>,
1655        current_value: impl Into<SessionConfigValueId>,
1656        options: impl Into<SessionConfigSelectOptions>,
1657    ) -> Self {
1658        Self::new(
1659            id,
1660            name,
1661            SessionConfigKind::Select(SessionConfigSelect::new(current_value, options)),
1662        )
1663    }
1664
1665    #[must_use]
1666    pub fn description(mut self, description: impl IntoOption<String>) -> Self {
1667        self.description = description.into_option();
1668        self
1669    }
1670
1671    #[must_use]
1672    pub fn category(mut self, category: impl IntoOption<SessionConfigOptionCategory>) -> Self {
1673        self.category = category.into_option();
1674        self
1675    }
1676
1677    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1678    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1679    /// these keys.
1680    ///
1681    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1682    #[must_use]
1683    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1684        self.meta = meta.into_option();
1685        self
1686    }
1687}
1688
1689/// **UNSTABLE**
1690///
1691/// This capability is not part of the spec yet, and may be removed or changed at any point.
1692///
1693/// Request parameters for setting a session configuration option.
1694#[cfg(feature = "unstable_session_config_options")]
1695#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1696#[schemars(extend("x-side" = "agent", "x-method" = SESSION_SET_CONFIG_OPTION_METHOD_NAME))]
1697#[serde(rename_all = "camelCase")]
1698#[non_exhaustive]
1699pub struct SetSessionConfigOptionRequest {
1700    /// The ID of the session to set the configuration option for.
1701    pub session_id: SessionId,
1702    /// The ID of the configuration option to set.
1703    pub config_id: SessionConfigId,
1704    /// The ID of the configuration option value to set.
1705    pub value: SessionConfigValueId,
1706    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1707    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1708    /// these keys.
1709    ///
1710    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1711    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1712    pub meta: Option<Meta>,
1713}
1714
1715#[cfg(feature = "unstable_session_config_options")]
1716impl SetSessionConfigOptionRequest {
1717    #[must_use]
1718    pub fn new(
1719        session_id: impl Into<SessionId>,
1720        config_id: impl Into<SessionConfigId>,
1721        value: impl Into<SessionConfigValueId>,
1722    ) -> Self {
1723        Self {
1724            session_id: session_id.into(),
1725            config_id: config_id.into(),
1726            value: value.into(),
1727            meta: None,
1728        }
1729    }
1730
1731    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1732    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1733    /// these keys.
1734    ///
1735    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1736    #[must_use]
1737    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1738        self.meta = meta.into_option();
1739        self
1740    }
1741}
1742
1743/// **UNSTABLE**
1744///
1745/// This capability is not part of the spec yet, and may be removed or changed at any point.
1746///
1747/// Response to `session/set_config_option` method.
1748#[cfg(feature = "unstable_session_config_options")]
1749#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1750#[schemars(extend("x-side" = "agent", "x-method" = SESSION_SET_CONFIG_OPTION_METHOD_NAME))]
1751#[serde(rename_all = "camelCase")]
1752#[non_exhaustive]
1753pub struct SetSessionConfigOptionResponse {
1754    /// The full set of configuration options and their current values.
1755    pub config_options: Vec<SessionConfigOption>,
1756    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1757    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1758    /// these keys.
1759    ///
1760    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1761    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1762    pub meta: Option<Meta>,
1763}
1764
1765#[cfg(feature = "unstable_session_config_options")]
1766impl SetSessionConfigOptionResponse {
1767    #[must_use]
1768    pub fn new(config_options: Vec<SessionConfigOption>) -> Self {
1769        Self {
1770            config_options,
1771            meta: None,
1772        }
1773    }
1774
1775    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1776    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1777    /// these keys.
1778    ///
1779    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1780    #[must_use]
1781    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1782        self.meta = meta.into_option();
1783        self
1784    }
1785}
1786
1787// MCP
1788
1789/// Configuration for connecting to an MCP (Model Context Protocol) server.
1790///
1791/// MCP servers provide tools and context that the agent can use when
1792/// processing prompts.
1793///
1794/// See protocol docs: [MCP Servers](https://agentclientprotocol.com/protocol/session-setup#mcp-servers)
1795#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1796#[serde(tag = "type", rename_all = "snake_case")]
1797#[non_exhaustive]
1798pub enum McpServer {
1799    /// HTTP transport configuration
1800    ///
1801    /// Only available when the Agent capabilities indicate `mcp_capabilities.http` is `true`.
1802    Http(McpServerHttp),
1803    /// SSE transport configuration
1804    ///
1805    /// Only available when the Agent capabilities indicate `mcp_capabilities.sse` is `true`.
1806    Sse(McpServerSse),
1807    /// Stdio transport configuration
1808    ///
1809    /// All Agents MUST support this transport.
1810    #[serde(untagged)]
1811    Stdio(McpServerStdio),
1812}
1813
1814/// HTTP transport configuration for MCP.
1815#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1816#[serde(rename_all = "camelCase")]
1817#[non_exhaustive]
1818pub struct McpServerHttp {
1819    /// Human-readable name identifying this MCP server.
1820    pub name: String,
1821    /// URL to the MCP server.
1822    pub url: String,
1823    /// HTTP headers to set when making requests to the MCP server.
1824    pub headers: Vec<HttpHeader>,
1825    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1826    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1827    /// these keys.
1828    ///
1829    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1830    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1831    pub meta: Option<Meta>,
1832}
1833
1834impl McpServerHttp {
1835    pub fn new(name: impl Into<String>, url: impl Into<String>) -> Self {
1836        Self {
1837            name: name.into(),
1838            url: url.into(),
1839            headers: Vec::new(),
1840            meta: None,
1841        }
1842    }
1843
1844    /// HTTP headers to set when making requests to the MCP server.
1845    #[must_use]
1846    pub fn headers(mut self, headers: Vec<HttpHeader>) -> Self {
1847        self.headers = headers;
1848        self
1849    }
1850
1851    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1852    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1853    /// these keys.
1854    ///
1855    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1856    #[must_use]
1857    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1858        self.meta = meta.into_option();
1859        self
1860    }
1861}
1862
1863/// SSE transport configuration for MCP.
1864#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1865#[serde(rename_all = "camelCase")]
1866#[non_exhaustive]
1867pub struct McpServerSse {
1868    /// Human-readable name identifying this MCP server.
1869    pub name: String,
1870    /// URL to the MCP server.
1871    pub url: String,
1872    /// HTTP headers to set when making requests to the MCP server.
1873    pub headers: Vec<HttpHeader>,
1874    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1875    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1876    /// these keys.
1877    ///
1878    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1879    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1880    pub meta: Option<Meta>,
1881}
1882
1883impl McpServerSse {
1884    pub fn new(name: impl Into<String>, url: impl Into<String>) -> Self {
1885        Self {
1886            name: name.into(),
1887            url: url.into(),
1888            headers: Vec::new(),
1889            meta: None,
1890        }
1891    }
1892
1893    /// HTTP headers to set when making requests to the MCP server.
1894    #[must_use]
1895    pub fn headers(mut self, headers: Vec<HttpHeader>) -> Self {
1896        self.headers = headers;
1897        self
1898    }
1899
1900    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1901    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1902    /// these keys.
1903    ///
1904    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1905    #[must_use]
1906    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1907        self.meta = meta.into_option();
1908        self
1909    }
1910}
1911
1912/// Stdio transport configuration for MCP.
1913#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1914#[serde(rename_all = "camelCase")]
1915#[non_exhaustive]
1916pub struct McpServerStdio {
1917    /// Human-readable name identifying this MCP server.
1918    pub name: String,
1919    /// Path to the MCP server executable.
1920    pub command: PathBuf,
1921    /// Command-line arguments to pass to the MCP server.
1922    pub args: Vec<String>,
1923    /// Environment variables to set when launching the MCP server.
1924    pub env: Vec<EnvVariable>,
1925    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1926    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1927    /// these keys.
1928    ///
1929    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1930    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1931    pub meta: Option<Meta>,
1932}
1933
1934impl McpServerStdio {
1935    pub fn new(name: impl Into<String>, command: impl Into<PathBuf>) -> Self {
1936        Self {
1937            name: name.into(),
1938            command: command.into(),
1939            args: Vec::new(),
1940            env: Vec::new(),
1941            meta: None,
1942        }
1943    }
1944
1945    /// Command-line arguments to pass to the MCP server.
1946    #[must_use]
1947    pub fn args(mut self, args: Vec<String>) -> Self {
1948        self.args = args;
1949        self
1950    }
1951
1952    /// Environment variables to set when launching the MCP server.
1953    #[must_use]
1954    pub fn env(mut self, env: Vec<EnvVariable>) -> Self {
1955        self.env = env;
1956        self
1957    }
1958
1959    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1960    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1961    /// these keys.
1962    ///
1963    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1964    #[must_use]
1965    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
1966        self.meta = meta.into_option();
1967        self
1968    }
1969}
1970
1971/// An environment variable to set when launching an MCP server.
1972#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
1973#[serde(rename_all = "camelCase")]
1974#[non_exhaustive]
1975pub struct EnvVariable {
1976    /// The name of the environment variable.
1977    pub name: String,
1978    /// The value to set for the environment variable.
1979    pub value: String,
1980    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1981    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
1982    /// these keys.
1983    ///
1984    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
1985    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
1986    pub meta: Option<Meta>,
1987}
1988
1989impl EnvVariable {
1990    pub fn new(name: impl Into<String>, value: impl Into<String>) -> Self {
1991        Self {
1992            name: name.into(),
1993            value: value.into(),
1994            meta: None,
1995        }
1996    }
1997
1998    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
1999    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2000    /// these keys.
2001    ///
2002    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2003    #[must_use]
2004    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2005        self.meta = meta.into_option();
2006        self
2007    }
2008}
2009
2010/// An HTTP header to set when making requests to the MCP server.
2011#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2012#[serde(rename_all = "camelCase")]
2013#[non_exhaustive]
2014pub struct HttpHeader {
2015    /// The name of the HTTP header.
2016    pub name: String,
2017    /// The value to set for the HTTP header.
2018    pub value: String,
2019    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2020    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2021    /// these keys.
2022    ///
2023    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2024    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2025    pub meta: Option<Meta>,
2026}
2027
2028impl HttpHeader {
2029    pub fn new(name: impl Into<String>, value: impl Into<String>) -> Self {
2030        Self {
2031            name: name.into(),
2032            value: value.into(),
2033            meta: None,
2034        }
2035    }
2036
2037    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2038    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2039    /// these keys.
2040    ///
2041    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2042    #[must_use]
2043    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2044        self.meta = meta.into_option();
2045        self
2046    }
2047}
2048
2049// Prompt
2050
2051/// Request parameters for sending a user prompt to the agent.
2052///
2053/// Contains the user's message and any additional context.
2054///
2055/// See protocol docs: [User Message](https://agentclientprotocol.com/protocol/prompt-turn#1-user-message)
2056#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq)]
2057#[schemars(extend("x-side" = "agent", "x-method" = SESSION_PROMPT_METHOD_NAME))]
2058#[serde(rename_all = "camelCase")]
2059#[non_exhaustive]
2060pub struct PromptRequest {
2061    /// The ID of the session to send this user message to
2062    pub session_id: SessionId,
2063    /// The blocks of content that compose the user's message.
2064    ///
2065    /// As a baseline, the Agent MUST support [`ContentBlock::Text`] and [`ContentBlock::ResourceLink`],
2066    /// while other variants are optionally enabled via [`PromptCapabilities`].
2067    ///
2068    /// The Client MUST adapt its interface according to [`PromptCapabilities`].
2069    ///
2070    /// The client MAY include referenced pieces of context as either
2071    /// [`ContentBlock::Resource`] or [`ContentBlock::ResourceLink`].
2072    ///
2073    /// When available, [`ContentBlock::Resource`] is preferred
2074    /// as it avoids extra round-trips and allows the message to include
2075    /// pieces of context from sources the agent may not have access to.
2076    pub prompt: Vec<ContentBlock>,
2077    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2078    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2079    /// these keys.
2080    ///
2081    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2082    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2083    pub meta: Option<Meta>,
2084}
2085
2086impl PromptRequest {
2087    #[must_use]
2088    pub fn new(session_id: impl Into<SessionId>, prompt: Vec<ContentBlock>) -> Self {
2089        Self {
2090            session_id: session_id.into(),
2091            prompt,
2092            meta: None,
2093        }
2094    }
2095
2096    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2097    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2098    /// these keys.
2099    ///
2100    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2101    #[must_use]
2102    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2103        self.meta = meta.into_option();
2104        self
2105    }
2106}
2107
2108/// Response from processing a user prompt.
2109///
2110/// See protocol docs: [Check for Completion](https://agentclientprotocol.com/protocol/prompt-turn#4-check-for-completion)
2111#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2112#[schemars(extend("x-side" = "agent", "x-method" = SESSION_PROMPT_METHOD_NAME))]
2113#[serde(rename_all = "camelCase")]
2114#[non_exhaustive]
2115pub struct PromptResponse {
2116    /// Indicates why the agent stopped processing the turn.
2117    pub stop_reason: StopReason,
2118    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2119    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2120    /// these keys.
2121    ///
2122    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2123    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2124    pub meta: Option<Meta>,
2125}
2126
2127impl PromptResponse {
2128    #[must_use]
2129    pub fn new(stop_reason: StopReason) -> Self {
2130        Self {
2131            stop_reason,
2132            meta: None,
2133        }
2134    }
2135
2136    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2137    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2138    /// these keys.
2139    ///
2140    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2141    #[must_use]
2142    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2143        self.meta = meta.into_option();
2144        self
2145    }
2146}
2147
2148/// Reasons why an agent stops processing a prompt turn.
2149///
2150/// See protocol docs: [Stop Reasons](https://agentclientprotocol.com/protocol/prompt-turn#stop-reasons)
2151#[derive(Debug, Copy, Clone, Eq, PartialEq, Serialize, Deserialize, JsonSchema)]
2152#[serde(rename_all = "snake_case")]
2153#[non_exhaustive]
2154pub enum StopReason {
2155    /// The turn ended successfully.
2156    EndTurn,
2157    /// The turn ended because the agent reached the maximum number of tokens.
2158    MaxTokens,
2159    /// The turn ended because the agent reached the maximum number of allowed
2160    /// agent requests between user turns.
2161    MaxTurnRequests,
2162    /// The turn ended because the agent refused to continue. The user prompt
2163    /// and everything that comes after it won't be included in the next
2164    /// prompt, so this should be reflected in the UI.
2165    Refusal,
2166    /// The turn was cancelled by the client via `session/cancel`.
2167    ///
2168    /// This stop reason MUST be returned when the client sends a `session/cancel`
2169    /// notification, even if the cancellation causes exceptions in underlying operations.
2170    /// Agents should catch these exceptions and return this semantically meaningful
2171    /// response to confirm successful cancellation.
2172    Cancelled,
2173}
2174
2175// Model
2176
2177/// **UNSTABLE**
2178///
2179/// This capability is not part of the spec yet, and may be removed or changed at any point.
2180///
2181/// The set of models and the one currently active.
2182#[cfg(feature = "unstable_session_model")]
2183#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2184#[serde(rename_all = "camelCase")]
2185#[non_exhaustive]
2186pub struct SessionModelState {
2187    /// The current model the Agent is in.
2188    pub current_model_id: ModelId,
2189    /// The set of models that the Agent can use
2190    pub available_models: Vec<ModelInfo>,
2191    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2192    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2193    /// these keys.
2194    ///
2195    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2196    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2197    pub meta: Option<Meta>,
2198}
2199
2200#[cfg(feature = "unstable_session_model")]
2201impl SessionModelState {
2202    #[must_use]
2203    pub fn new(current_model_id: impl Into<ModelId>, available_models: Vec<ModelInfo>) -> Self {
2204        Self {
2205            current_model_id: current_model_id.into(),
2206            available_models,
2207            meta: None,
2208        }
2209    }
2210
2211    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2212    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2213    /// these keys.
2214    ///
2215    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2216    #[must_use]
2217    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2218        self.meta = meta.into_option();
2219        self
2220    }
2221}
2222
2223/// **UNSTABLE**
2224///
2225/// This capability is not part of the spec yet, and may be removed or changed at any point.
2226///
2227/// A unique identifier for a model.
2228#[cfg(feature = "unstable_session_model")]
2229#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq, Hash, Display, From)]
2230#[serde(transparent)]
2231#[from(Arc<str>, String, &'static str)]
2232#[non_exhaustive]
2233pub struct ModelId(pub Arc<str>);
2234
2235#[cfg(feature = "unstable_session_model")]
2236impl ModelId {
2237    pub fn new(id: impl Into<Arc<str>>) -> Self {
2238        Self(id.into())
2239    }
2240}
2241
2242/// **UNSTABLE**
2243///
2244/// This capability is not part of the spec yet, and may be removed or changed at any point.
2245///
2246/// Information about a selectable model.
2247#[cfg(feature = "unstable_session_model")]
2248#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2249#[serde(rename_all = "camelCase")]
2250#[non_exhaustive]
2251pub struct ModelInfo {
2252    /// Unique identifier for the model.
2253    pub model_id: ModelId,
2254    /// Human-readable name of the model.
2255    pub name: String,
2256    /// Optional description of the model.
2257    #[serde(default, skip_serializing_if = "Option::is_none")]
2258    pub description: Option<String>,
2259    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2260    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2261    /// these keys.
2262    ///
2263    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2264    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2265    pub meta: Option<Meta>,
2266}
2267
2268#[cfg(feature = "unstable_session_model")]
2269impl ModelInfo {
2270    pub fn new(model_id: impl Into<ModelId>, name: impl Into<String>) -> Self {
2271        Self {
2272            model_id: model_id.into(),
2273            name: name.into(),
2274            description: None,
2275            meta: None,
2276        }
2277    }
2278
2279    /// Optional description of the model.
2280    #[must_use]
2281    pub fn description(mut self, description: impl IntoOption<String>) -> Self {
2282        self.description = description.into_option();
2283        self
2284    }
2285
2286    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2287    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2288    /// these keys.
2289    ///
2290    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2291    #[must_use]
2292    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2293        self.meta = meta.into_option();
2294        self
2295    }
2296}
2297
2298/// **UNSTABLE**
2299///
2300/// This capability is not part of the spec yet, and may be removed or changed at any point.
2301///
2302/// Request parameters for setting a session model.
2303#[cfg(feature = "unstable_session_model")]
2304#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2305#[schemars(extend("x-side" = "agent", "x-method" = SESSION_SET_MODEL_METHOD_NAME))]
2306#[serde(rename_all = "camelCase")]
2307#[non_exhaustive]
2308pub struct SetSessionModelRequest {
2309    /// The ID of the session to set the model for.
2310    pub session_id: SessionId,
2311    /// The ID of the model to set.
2312    pub model_id: ModelId,
2313    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2314    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2315    /// these keys.
2316    ///
2317    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2318    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2319    pub meta: Option<Meta>,
2320}
2321
2322#[cfg(feature = "unstable_session_model")]
2323impl SetSessionModelRequest {
2324    #[must_use]
2325    pub fn new(session_id: impl Into<SessionId>, model_id: impl Into<ModelId>) -> Self {
2326        Self {
2327            session_id: session_id.into(),
2328            model_id: model_id.into(),
2329            meta: None,
2330        }
2331    }
2332
2333    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2334    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2335    /// these keys.
2336    ///
2337    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2338    #[must_use]
2339    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2340        self.meta = meta.into_option();
2341        self
2342    }
2343}
2344
2345/// **UNSTABLE**
2346///
2347/// This capability is not part of the spec yet, and may be removed or changed at any point.
2348///
2349/// Response to `session/set_model` method.
2350#[cfg(feature = "unstable_session_model")]
2351#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2352#[schemars(extend("x-side" = "agent", "x-method" = SESSION_SET_MODEL_METHOD_NAME))]
2353#[serde(rename_all = "camelCase")]
2354#[non_exhaustive]
2355pub struct SetSessionModelResponse {
2356    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2357    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2358    /// these keys.
2359    ///
2360    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2361    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2362    pub meta: Option<Meta>,
2363}
2364
2365#[cfg(feature = "unstable_session_model")]
2366impl SetSessionModelResponse {
2367    #[must_use]
2368    pub fn new() -> Self {
2369        Self::default()
2370    }
2371
2372    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2373    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2374    /// these keys.
2375    ///
2376    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2377    #[must_use]
2378    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2379        self.meta = meta.into_option();
2380        self
2381    }
2382}
2383
2384// Capabilities
2385
2386/// Capabilities supported by the agent.
2387///
2388/// Advertised during initialization to inform the client about
2389/// available features and content types.
2390///
2391/// See protocol docs: [Agent Capabilities](https://agentclientprotocol.com/protocol/initialization#agent-capabilities)
2392#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2393#[serde(rename_all = "camelCase")]
2394#[non_exhaustive]
2395pub struct AgentCapabilities {
2396    /// Whether the agent supports `session/load`.
2397    #[serde(default)]
2398    pub load_session: bool,
2399    /// Prompt capabilities supported by the agent.
2400    #[serde(default)]
2401    pub prompt_capabilities: PromptCapabilities,
2402    /// MCP capabilities supported by the agent.
2403    #[serde(default)]
2404    pub mcp_capabilities: McpCapabilities,
2405    #[serde(default)]
2406    pub session_capabilities: SessionCapabilities,
2407    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2408    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2409    /// these keys.
2410    ///
2411    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2412    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2413    pub meta: Option<Meta>,
2414}
2415
2416impl AgentCapabilities {
2417    #[must_use]
2418    pub fn new() -> Self {
2419        Self::default()
2420    }
2421
2422    /// Whether the agent supports `session/load`.
2423    #[must_use]
2424    pub fn load_session(mut self, load_session: bool) -> Self {
2425        self.load_session = load_session;
2426        self
2427    }
2428
2429    /// Prompt capabilities supported by the agent.
2430    #[must_use]
2431    pub fn prompt_capabilities(mut self, prompt_capabilities: PromptCapabilities) -> Self {
2432        self.prompt_capabilities = prompt_capabilities;
2433        self
2434    }
2435
2436    /// MCP capabilities supported by the agent.
2437    #[must_use]
2438    pub fn mcp_capabilities(mut self, mcp_capabilities: McpCapabilities) -> Self {
2439        self.mcp_capabilities = mcp_capabilities;
2440        self
2441    }
2442
2443    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2444    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2445    /// these keys.
2446    ///
2447    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2448    #[must_use]
2449    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2450        self.meta = meta.into_option();
2451        self
2452    }
2453}
2454
2455/// Session capabilities supported by the agent.
2456///
2457/// As a baseline, all Agents **MUST** support `session/new`, `session/prompt`, `session/cancel`, and `session/update`.
2458///
2459/// Optionally, they **MAY** support other session methods and notifications by specifying additional capabilities.
2460///
2461/// Note: `session/load` is still handled by the top-level `load_session` capability. This will be unified in future versions of the protocol.
2462///
2463/// See protocol docs: [Session Capabilities](https://agentclientprotocol.com/protocol/initialization#session-capabilities)
2464#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2465#[non_exhaustive]
2466pub struct SessionCapabilities {
2467    /// **UNSTABLE**
2468    ///
2469    /// This capability is not part of the spec yet, and may be removed or changed at any point.
2470    ///
2471    /// Whether the agent supports `session/list`.
2472    #[cfg(feature = "unstable_session_list")]
2473    #[serde(skip_serializing_if = "Option::is_none")]
2474    pub list: Option<SessionListCapabilities>,
2475    /// **UNSTABLE**
2476    ///
2477    /// This capability is not part of the spec yet, and may be removed or changed at any point.
2478    ///
2479    /// Whether the agent supports `session/fork`.
2480    #[cfg(feature = "unstable_session_fork")]
2481    #[serde(skip_serializing_if = "Option::is_none")]
2482    pub fork: Option<SessionForkCapabilities>,
2483    /// **UNSTABLE**
2484    ///
2485    /// This capability is not part of the spec yet, and may be removed or changed at any point.
2486    ///
2487    /// Whether the agent supports `session/resume`.
2488    #[cfg(feature = "unstable_session_resume")]
2489    #[serde(skip_serializing_if = "Option::is_none")]
2490    pub resume: Option<SessionResumeCapabilities>,
2491    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2492    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2493    /// these keys.
2494    ///
2495    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2496    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2497    pub meta: Option<Meta>,
2498}
2499
2500impl SessionCapabilities {
2501    #[must_use]
2502    pub fn new() -> Self {
2503        Self::default()
2504    }
2505
2506    #[cfg(feature = "unstable_session_list")]
2507    /// Whether the agent supports `session/list`.
2508    #[must_use]
2509    pub fn list(mut self, list: impl IntoOption<SessionListCapabilities>) -> Self {
2510        self.list = list.into_option();
2511        self
2512    }
2513
2514    #[cfg(feature = "unstable_session_fork")]
2515    /// Whether the agent supports `session/fork`.
2516    #[must_use]
2517    pub fn fork(mut self, fork: impl IntoOption<SessionForkCapabilities>) -> Self {
2518        self.fork = fork.into_option();
2519        self
2520    }
2521
2522    #[cfg(feature = "unstable_session_resume")]
2523    /// Whether the agent supports `session/resume`.
2524    #[must_use]
2525    pub fn resume(mut self, resume: impl IntoOption<SessionResumeCapabilities>) -> Self {
2526        self.resume = resume.into_option();
2527        self
2528    }
2529
2530    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2531    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2532    /// these keys.
2533    ///
2534    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2535    #[must_use]
2536    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2537        self.meta = meta.into_option();
2538        self
2539    }
2540}
2541
2542/// Capabilities for the `session/list` method.
2543///
2544/// By supplying `{}` it means that the agent supports listing of sessions.
2545///
2546/// Further capabilities can be added in the future for other means of filtering or searching the list.
2547#[cfg(feature = "unstable_session_list")]
2548#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2549#[non_exhaustive]
2550pub struct SessionListCapabilities {
2551    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2552    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2553    /// these keys.
2554    ///
2555    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2556    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2557    pub meta: Option<Meta>,
2558}
2559
2560#[cfg(feature = "unstable_session_list")]
2561impl SessionListCapabilities {
2562    #[must_use]
2563    pub fn new() -> Self {
2564        Self::default()
2565    }
2566    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2567    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2568    /// these keys.
2569    ///
2570    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2571    #[must_use]
2572    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2573        self.meta = meta.into_option();
2574        self
2575    }
2576}
2577
2578/// **UNSTABLE**
2579///
2580/// This capability is not part of the spec yet, and may be removed or changed at any point.
2581///
2582/// Capabilities for the `session/fork` method.
2583///
2584/// By supplying `{}` it means that the agent supports forking of sessions.
2585#[cfg(feature = "unstable_session_fork")]
2586#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2587#[non_exhaustive]
2588pub struct SessionForkCapabilities {
2589    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2590    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2591    /// these keys.
2592    ///
2593    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2594    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2595    pub meta: Option<Meta>,
2596}
2597
2598#[cfg(feature = "unstable_session_fork")]
2599impl SessionForkCapabilities {
2600    #[must_use]
2601    pub fn new() -> Self {
2602        Self::default()
2603    }
2604
2605    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2606    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2607    /// these keys.
2608    ///
2609    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2610    #[must_use]
2611    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2612        self.meta = meta.into_option();
2613        self
2614    }
2615}
2616
2617/// **UNSTABLE**
2618///
2619/// This capability is not part of the spec yet, and may be removed or changed at any point.
2620///
2621/// Capabilities for the `session/resume` method.
2622///
2623/// By supplying `{}` it means that the agent supports resuming of sessions.
2624#[cfg(feature = "unstable_session_resume")]
2625#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2626#[non_exhaustive]
2627pub struct SessionResumeCapabilities {
2628    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2629    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2630    /// these keys.
2631    ///
2632    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2633    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2634    pub meta: Option<Meta>,
2635}
2636
2637#[cfg(feature = "unstable_session_resume")]
2638impl SessionResumeCapabilities {
2639    #[must_use]
2640    pub fn new() -> Self {
2641        Self::default()
2642    }
2643
2644    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2645    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2646    /// these keys.
2647    ///
2648    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2649    #[must_use]
2650    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2651        self.meta = meta.into_option();
2652        self
2653    }
2654}
2655
2656/// Prompt capabilities supported by the agent in `session/prompt` requests.
2657///
2658/// Baseline agent functionality requires support for [`ContentBlock::Text`]
2659/// and [`ContentBlock::ResourceLink`] in prompt requests.
2660///
2661/// Other variants must be explicitly opted in to.
2662/// Capabilities for different types of content in prompt requests.
2663///
2664/// Indicates which content types beyond the baseline (text and resource links)
2665/// the agent can process.
2666///
2667/// See protocol docs: [Prompt Capabilities](https://agentclientprotocol.com/protocol/initialization#prompt-capabilities)
2668#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2669#[serde(rename_all = "camelCase")]
2670#[non_exhaustive]
2671pub struct PromptCapabilities {
2672    /// Agent supports [`ContentBlock::Image`].
2673    #[serde(default)]
2674    pub image: bool,
2675    /// Agent supports [`ContentBlock::Audio`].
2676    #[serde(default)]
2677    pub audio: bool,
2678    /// Agent supports embedded context in `session/prompt` requests.
2679    ///
2680    /// When enabled, the Client is allowed to include [`ContentBlock::Resource`]
2681    /// in prompt requests for pieces of context that are referenced in the message.
2682    #[serde(default)]
2683    pub embedded_context: bool,
2684    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2685    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2686    /// these keys.
2687    ///
2688    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2689    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2690    pub meta: Option<Meta>,
2691}
2692
2693impl PromptCapabilities {
2694    #[must_use]
2695    pub fn new() -> Self {
2696        Self::default()
2697    }
2698
2699    /// Agent supports [`ContentBlock::Image`].
2700    #[must_use]
2701    pub fn image(mut self, image: bool) -> Self {
2702        self.image = image;
2703        self
2704    }
2705
2706    /// Agent supports [`ContentBlock::Audio`].
2707    #[must_use]
2708    pub fn audio(mut self, audio: bool) -> Self {
2709        self.audio = audio;
2710        self
2711    }
2712
2713    /// Agent supports embedded context in `session/prompt` requests.
2714    ///
2715    /// When enabled, the Client is allowed to include [`ContentBlock::Resource`]
2716    /// in prompt requests for pieces of context that are referenced in the message.
2717    #[must_use]
2718    pub fn embedded_context(mut self, embedded_context: bool) -> Self {
2719        self.embedded_context = embedded_context;
2720        self
2721    }
2722
2723    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2724    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2725    /// these keys.
2726    ///
2727    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2728    #[must_use]
2729    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2730        self.meta = meta.into_option();
2731        self
2732    }
2733}
2734
2735/// MCP capabilities supported by the agent
2736#[derive(Default, Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
2737#[serde(rename_all = "camelCase")]
2738#[non_exhaustive]
2739pub struct McpCapabilities {
2740    /// Agent supports [`McpServer::Http`].
2741    #[serde(default)]
2742    pub http: bool,
2743    /// Agent supports [`McpServer::Sse`].
2744    #[serde(default)]
2745    pub sse: bool,
2746    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2747    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2748    /// these keys.
2749    ///
2750    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2751    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
2752    pub meta: Option<Meta>,
2753}
2754
2755impl McpCapabilities {
2756    #[must_use]
2757    pub fn new() -> Self {
2758        Self::default()
2759    }
2760
2761    /// Agent supports [`McpServer::Http`].
2762    #[must_use]
2763    pub fn http(mut self, http: bool) -> Self {
2764        self.http = http;
2765        self
2766    }
2767
2768    /// Agent supports [`McpServer::Sse`].
2769    #[must_use]
2770    pub fn sse(mut self, sse: bool) -> Self {
2771        self.sse = sse;
2772        self
2773    }
2774
2775    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
2776    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
2777    /// these keys.
2778    ///
2779    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
2780    #[must_use]
2781    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
2782        self.meta = meta.into_option();
2783        self
2784    }
2785}
2786
2787// Method schema
2788
2789/// Names of all methods that agents handle.
2790///
2791/// Provides a centralized definition of method names used in the protocol.
2792#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
2793#[non_exhaustive]
2794pub struct AgentMethodNames {
2795    /// Method for initializing the connection.
2796    pub initialize: &'static str,
2797    /// Method for authenticating with the agent.
2798    pub authenticate: &'static str,
2799    /// Method for creating a new session.
2800    pub session_new: &'static str,
2801    /// Method for loading an existing session.
2802    pub session_load: &'static str,
2803    /// Method for setting the mode for a session.
2804    pub session_set_mode: &'static str,
2805    /// Method for setting a configuration option for a session.
2806    #[cfg(feature = "unstable_session_config_options")]
2807    pub session_set_config_option: &'static str,
2808    /// Method for sending a prompt to the agent.
2809    pub session_prompt: &'static str,
2810    /// Notification for cancelling operations.
2811    pub session_cancel: &'static str,
2812    /// Method for selecting a model for a given session.
2813    #[cfg(feature = "unstable_session_model")]
2814    pub session_set_model: &'static str,
2815    /// Method for listing existing sessions.
2816    #[cfg(feature = "unstable_session_list")]
2817    pub session_list: &'static str,
2818    /// Method for forking an existing session.
2819    #[cfg(feature = "unstable_session_fork")]
2820    pub session_fork: &'static str,
2821    /// Method for resuming an existing session.
2822    #[cfg(feature = "unstable_session_resume")]
2823    pub session_resume: &'static str,
2824}
2825
2826/// Constant containing all agent method names.
2827pub const AGENT_METHOD_NAMES: AgentMethodNames = AgentMethodNames {
2828    initialize: INITIALIZE_METHOD_NAME,
2829    authenticate: AUTHENTICATE_METHOD_NAME,
2830    session_new: SESSION_NEW_METHOD_NAME,
2831    session_load: SESSION_LOAD_METHOD_NAME,
2832    session_set_mode: SESSION_SET_MODE_METHOD_NAME,
2833    #[cfg(feature = "unstable_session_config_options")]
2834    session_set_config_option: SESSION_SET_CONFIG_OPTION_METHOD_NAME,
2835    session_prompt: SESSION_PROMPT_METHOD_NAME,
2836    session_cancel: SESSION_CANCEL_METHOD_NAME,
2837    #[cfg(feature = "unstable_session_model")]
2838    session_set_model: SESSION_SET_MODEL_METHOD_NAME,
2839    #[cfg(feature = "unstable_session_list")]
2840    session_list: SESSION_LIST_METHOD_NAME,
2841    #[cfg(feature = "unstable_session_fork")]
2842    session_fork: SESSION_FORK_METHOD_NAME,
2843    #[cfg(feature = "unstable_session_resume")]
2844    session_resume: SESSION_RESUME_METHOD_NAME,
2845};
2846
2847/// Method name for the initialize request.
2848pub(crate) const INITIALIZE_METHOD_NAME: &str = "initialize";
2849/// Method name for the authenticate request.
2850pub(crate) const AUTHENTICATE_METHOD_NAME: &str = "authenticate";
2851/// Method name for creating a new session.
2852pub(crate) const SESSION_NEW_METHOD_NAME: &str = "session/new";
2853/// Method name for loading an existing session.
2854pub(crate) const SESSION_LOAD_METHOD_NAME: &str = "session/load";
2855/// Method name for setting the mode for a session.
2856pub(crate) const SESSION_SET_MODE_METHOD_NAME: &str = "session/set_mode";
2857/// Method name for setting a configuration option for a session.
2858#[cfg(feature = "unstable_session_config_options")]
2859pub(crate) const SESSION_SET_CONFIG_OPTION_METHOD_NAME: &str = "session/set_config_option";
2860/// Method name for sending a prompt.
2861pub(crate) const SESSION_PROMPT_METHOD_NAME: &str = "session/prompt";
2862/// Method name for the cancel notification.
2863pub(crate) const SESSION_CANCEL_METHOD_NAME: &str = "session/cancel";
2864/// Method name for selecting a model for a given session.
2865#[cfg(feature = "unstable_session_model")]
2866pub(crate) const SESSION_SET_MODEL_METHOD_NAME: &str = "session/set_model";
2867/// Method name for listing existing sessions.
2868#[cfg(feature = "unstable_session_list")]
2869pub(crate) const SESSION_LIST_METHOD_NAME: &str = "session/list";
2870/// Method name for forking an existing session.
2871#[cfg(feature = "unstable_session_fork")]
2872pub(crate) const SESSION_FORK_METHOD_NAME: &str = "session/fork";
2873/// Method name for resuming an existing session.
2874#[cfg(feature = "unstable_session_resume")]
2875pub(crate) const SESSION_RESUME_METHOD_NAME: &str = "session/resume";
2876
2877/// All possible requests that a client can send to an agent.
2878///
2879/// This enum is used internally for routing RPC requests. You typically won't need
2880/// to use this directly - instead, use the methods on the [`Agent`] trait.
2881///
2882/// This enum encompasses all method calls from client to agent.
2883#[derive(Clone, Debug, Serialize, Deserialize, JsonSchema)]
2884#[serde(untagged)]
2885#[schemars(inline)]
2886#[non_exhaustive]
2887pub enum ClientRequest {
2888    /// Establishes the connection with a client and negotiates protocol capabilities.
2889    ///
2890    /// This method is called once at the beginning of the connection to:
2891    /// - Negotiate the protocol version to use
2892    /// - Exchange capability information between client and agent
2893    /// - Determine available authentication methods
2894    ///
2895    /// The agent should respond with its supported protocol version and capabilities.
2896    ///
2897    /// See protocol docs: [Initialization](https://agentclientprotocol.com/protocol/initialization)
2898    InitializeRequest(InitializeRequest),
2899    /// Authenticates the client using the specified authentication method.
2900    ///
2901    /// Called when the agent requires authentication before allowing session creation.
2902    /// The client provides the authentication method ID that was advertised during initialization.
2903    ///
2904    /// After successful authentication, the client can proceed to create sessions with
2905    /// `new_session` without receiving an `auth_required` error.
2906    ///
2907    /// See protocol docs: [Initialization](https://agentclientprotocol.com/protocol/initialization)
2908    AuthenticateRequest(AuthenticateRequest),
2909    /// Creates a new conversation session with the agent.
2910    ///
2911    /// Sessions represent independent conversation contexts with their own history and state.
2912    ///
2913    /// The agent should:
2914    /// - Create a new session context
2915    /// - Connect to any specified MCP servers
2916    /// - Return a unique session ID for future requests
2917    ///
2918    /// May return an `auth_required` error if the agent requires authentication.
2919    ///
2920    /// See protocol docs: [Session Setup](https://agentclientprotocol.com/protocol/session-setup)
2921    NewSessionRequest(NewSessionRequest),
2922    /// Loads an existing session to resume a previous conversation.
2923    ///
2924    /// This method is only available if the agent advertises the `loadSession` capability.
2925    ///
2926    /// The agent should:
2927    /// - Restore the session context and conversation history
2928    /// - Connect to the specified MCP servers
2929    /// - Stream the entire conversation history back to the client via notifications
2930    ///
2931    /// See protocol docs: [Loading Sessions](https://agentclientprotocol.com/protocol/session-setup#loading-sessions)
2932    LoadSessionRequest(LoadSessionRequest),
2933    #[cfg(feature = "unstable_session_list")]
2934    /// **UNSTABLE**
2935    ///
2936    /// This capability is not part of the spec yet, and may be removed or changed at any point.
2937    ///
2938    /// Lists existing sessions known to the agent.
2939    ///
2940    /// This method is only available if the agent advertises the `listSessions` capability.
2941    ///
2942    /// The agent should return metadata about sessions with optional filtering and pagination support.
2943    ListSessionsRequest(ListSessionsRequest),
2944    #[cfg(feature = "unstable_session_fork")]
2945    /// **UNSTABLE**
2946    ///
2947    /// This capability is not part of the spec yet, and may be removed or changed at any point.
2948    ///
2949    /// Forks an existing session to create a new independent session.
2950    ///
2951    /// This method is only available if the agent advertises the `session.fork` capability.
2952    ///
2953    /// The agent should create a new session with the same conversation context as the
2954    /// original, allowing operations like generating summaries without affecting the
2955    /// original session's history.
2956    ForkSessionRequest(ForkSessionRequest),
2957    #[cfg(feature = "unstable_session_resume")]
2958    /// **UNSTABLE**
2959    ///
2960    /// This capability is not part of the spec yet, and may be removed or changed at any point.
2961    ///
2962    /// Resumes an existing session without returning previous messages.
2963    ///
2964    /// This method is only available if the agent advertises the `session.resume` capability.
2965    ///
2966    /// The agent should resume the session context, allowing the conversation to continue
2967    /// without replaying the message history (unlike `session/load`).
2968    ResumeSessionRequest(ResumeSessionRequest),
2969    /// Sets the current mode for a session.
2970    ///
2971    /// Allows switching between different agent modes (e.g., "ask", "architect", "code")
2972    /// that affect system prompts, tool availability, and permission behaviors.
2973    ///
2974    /// The mode must be one of the modes advertised in `availableModes` during session
2975    /// creation or loading. Agents may also change modes autonomously and notify the
2976    /// client via `current_mode_update` notifications.
2977    ///
2978    /// This method can be called at any time during a session, whether the Agent is
2979    /// idle or actively generating a response.
2980    ///
2981    /// See protocol docs: [Session Modes](https://agentclientprotocol.com/protocol/session-modes)
2982    SetSessionModeRequest(SetSessionModeRequest),
2983    #[cfg(feature = "unstable_session_config_options")]
2984    /// **UNSTABLE**
2985    ///
2986    /// This capability is not part of the spec yet, and may be removed or changed at any point.
2987    ///
2988    /// Sets the current value for a session configuration option.
2989    SetSessionConfigOptionRequest(SetSessionConfigOptionRequest),
2990    /// Processes a user prompt within a session.
2991    ///
2992    /// This method handles the whole lifecycle of a prompt:
2993    /// - Receives user messages with optional context (files, images, etc.)
2994    /// - Processes the prompt using language models
2995    /// - Reports language model content and tool calls to the Clients
2996    /// - Requests permission to run tools
2997    /// - Executes any requested tool calls
2998    /// - Returns when the turn is complete with a stop reason
2999    ///
3000    /// See protocol docs: [Prompt Turn](https://agentclientprotocol.com/protocol/prompt-turn)
3001    PromptRequest(PromptRequest),
3002    #[cfg(feature = "unstable_session_model")]
3003    /// **UNSTABLE**
3004    ///
3005    /// This capability is not part of the spec yet, and may be removed or changed at any point.
3006    ///
3007    /// Select a model for a given session.
3008    SetSessionModelRequest(SetSessionModelRequest),
3009    /// Handles extension method requests from the client.
3010    ///
3011    /// Extension methods provide a way to add custom functionality while maintaining
3012    /// protocol compatibility.
3013    ///
3014    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
3015    ExtMethodRequest(ExtRequest),
3016}
3017
3018impl ClientRequest {
3019    /// Returns the corresponding method name of the request.
3020    #[must_use]
3021    pub fn method(&self) -> &str {
3022        match self {
3023            Self::InitializeRequest(_) => AGENT_METHOD_NAMES.initialize,
3024            Self::AuthenticateRequest(_) => AGENT_METHOD_NAMES.authenticate,
3025            Self::NewSessionRequest(_) => AGENT_METHOD_NAMES.session_new,
3026            Self::LoadSessionRequest(_) => AGENT_METHOD_NAMES.session_load,
3027            #[cfg(feature = "unstable_session_list")]
3028            Self::ListSessionsRequest(_) => AGENT_METHOD_NAMES.session_list,
3029            #[cfg(feature = "unstable_session_fork")]
3030            Self::ForkSessionRequest(_) => AGENT_METHOD_NAMES.session_fork,
3031            #[cfg(feature = "unstable_session_resume")]
3032            Self::ResumeSessionRequest(_) => AGENT_METHOD_NAMES.session_resume,
3033            Self::SetSessionModeRequest(_) => AGENT_METHOD_NAMES.session_set_mode,
3034            #[cfg(feature = "unstable_session_config_options")]
3035            Self::SetSessionConfigOptionRequest(_) => AGENT_METHOD_NAMES.session_set_config_option,
3036            Self::PromptRequest(_) => AGENT_METHOD_NAMES.session_prompt,
3037            #[cfg(feature = "unstable_session_model")]
3038            Self::SetSessionModelRequest(_) => AGENT_METHOD_NAMES.session_set_model,
3039            Self::ExtMethodRequest(ext_request) => &ext_request.method,
3040        }
3041    }
3042}
3043
3044/// All possible responses that an agent can send to a client.
3045///
3046/// This enum is used internally for routing RPC responses. You typically won't need
3047/// to use this directly - the responses are handled automatically by the connection.
3048///
3049/// These are responses to the corresponding `ClientRequest` variants.
3050#[derive(Clone, Debug, Serialize, Deserialize, JsonSchema)]
3051#[serde(untagged)]
3052#[schemars(inline)]
3053#[non_exhaustive]
3054pub enum AgentResponse {
3055    InitializeResponse(InitializeResponse),
3056    AuthenticateResponse(#[serde(default)] AuthenticateResponse),
3057    NewSessionResponse(NewSessionResponse),
3058    LoadSessionResponse(#[serde(default)] LoadSessionResponse),
3059    #[cfg(feature = "unstable_session_list")]
3060    ListSessionsResponse(ListSessionsResponse),
3061    #[cfg(feature = "unstable_session_fork")]
3062    ForkSessionResponse(ForkSessionResponse),
3063    #[cfg(feature = "unstable_session_resume")]
3064    ResumeSessionResponse(#[serde(default)] ResumeSessionResponse),
3065    SetSessionModeResponse(#[serde(default)] SetSessionModeResponse),
3066    #[cfg(feature = "unstable_session_config_options")]
3067    SetSessionConfigOptionResponse(SetSessionConfigOptionResponse),
3068    PromptResponse(PromptResponse),
3069    #[cfg(feature = "unstable_session_model")]
3070    SetSessionModelResponse(SetSessionModelResponse),
3071    ExtMethodResponse(ExtResponse),
3072}
3073
3074/// All possible notifications that a client can send to an agent.
3075///
3076/// This enum is used internally for routing RPC notifications. You typically won't need
3077/// to use this directly - use the notification methods on the [`Agent`] trait instead.
3078///
3079/// Notifications do not expect a response.
3080#[derive(Clone, Debug, Serialize, Deserialize, JsonSchema)]
3081#[serde(untagged)]
3082#[schemars(inline)]
3083#[non_exhaustive]
3084pub enum ClientNotification {
3085    /// Cancels ongoing operations for a session.
3086    ///
3087    /// This is a notification sent by the client to cancel an ongoing prompt turn.
3088    ///
3089    /// Upon receiving this notification, the Agent SHOULD:
3090    /// - Stop all language model requests as soon as possible
3091    /// - Abort all tool call invocations in progress
3092    /// - Send any pending `session/update` notifications
3093    /// - Respond to the original `session/prompt` request with `StopReason::Cancelled`
3094    ///
3095    /// See protocol docs: [Cancellation](https://agentclientprotocol.com/protocol/prompt-turn#cancellation)
3096    CancelNotification(CancelNotification),
3097    /// Handles extension notifications from the client.
3098    ///
3099    /// Extension notifications provide a way to send one-way messages for custom functionality
3100    /// while maintaining protocol compatibility.
3101    ///
3102    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
3103    ExtNotification(ExtNotification),
3104}
3105
3106impl ClientNotification {
3107    /// Returns the corresponding method name of the notification.
3108    #[must_use]
3109    pub fn method(&self) -> &str {
3110        match self {
3111            Self::CancelNotification(_) => AGENT_METHOD_NAMES.session_cancel,
3112            Self::ExtNotification(ext_notification) => &ext_notification.method,
3113        }
3114    }
3115}
3116
3117/// Notification to cancel ongoing operations for a session.
3118///
3119/// See protocol docs: [Cancellation](https://agentclientprotocol.com/protocol/prompt-turn#cancellation)
3120#[derive(Debug, Clone, Serialize, Deserialize, JsonSchema, PartialEq, Eq)]
3121#[schemars(extend("x-side" = "agent", "x-method" = SESSION_CANCEL_METHOD_NAME))]
3122#[serde(rename_all = "camelCase")]
3123#[non_exhaustive]
3124pub struct CancelNotification {
3125    /// The ID of the session to cancel operations for.
3126    pub session_id: SessionId,
3127    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
3128    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
3129    /// these keys.
3130    ///
3131    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
3132    #[serde(skip_serializing_if = "Option::is_none", rename = "_meta")]
3133    pub meta: Option<Meta>,
3134}
3135
3136impl CancelNotification {
3137    #[must_use]
3138    pub fn new(session_id: impl Into<SessionId>) -> Self {
3139        Self {
3140            session_id: session_id.into(),
3141            meta: None,
3142        }
3143    }
3144
3145    /// The _meta property is reserved by ACP to allow clients and agents to attach additional
3146    /// metadata to their interactions. Implementations MUST NOT make assumptions about values at
3147    /// these keys.
3148    ///
3149    /// See protocol docs: [Extensibility](https://agentclientprotocol.com/protocol/extensibility)
3150    #[must_use]
3151    pub fn meta(mut self, meta: impl IntoOption<Meta>) -> Self {
3152        self.meta = meta.into_option();
3153        self
3154    }
3155}
3156
3157#[cfg(test)]
3158mod test_serialization {
3159    use super::*;
3160    use serde_json::json;
3161
3162    #[test]
3163    fn test_mcp_server_stdio_serialization() {
3164        let server = McpServer::Stdio(
3165            McpServerStdio::new("test-server", "/usr/bin/server")
3166                .args(vec!["--port".to_string(), "3000".to_string()])
3167                .env(vec![EnvVariable::new("API_KEY", "secret123")]),
3168        );
3169
3170        let json = serde_json::to_value(&server).unwrap();
3171        assert_eq!(
3172            json,
3173            json!({
3174                "name": "test-server",
3175                "command": "/usr/bin/server",
3176                "args": ["--port", "3000"],
3177                "env": [
3178                    {
3179                        "name": "API_KEY",
3180                        "value": "secret123"
3181                    }
3182                ]
3183            })
3184        );
3185
3186        let deserialized: McpServer = serde_json::from_value(json).unwrap();
3187        match deserialized {
3188            McpServer::Stdio(McpServerStdio {
3189                name,
3190                command,
3191                args,
3192                env,
3193                meta: _,
3194            }) => {
3195                assert_eq!(name, "test-server");
3196                assert_eq!(command, PathBuf::from("/usr/bin/server"));
3197                assert_eq!(args, vec!["--port", "3000"]);
3198                assert_eq!(env.len(), 1);
3199                assert_eq!(env[0].name, "API_KEY");
3200                assert_eq!(env[0].value, "secret123");
3201            }
3202            _ => panic!("Expected Stdio variant"),
3203        }
3204    }
3205
3206    #[test]
3207    fn test_mcp_server_http_serialization() {
3208        let server = McpServer::Http(
3209            McpServerHttp::new("http-server", "https://api.example.com").headers(vec![
3210                HttpHeader::new("Authorization", "Bearer token123"),
3211                HttpHeader::new("Content-Type", "application/json"),
3212            ]),
3213        );
3214
3215        let json = serde_json::to_value(&server).unwrap();
3216        assert_eq!(
3217            json,
3218            json!({
3219                "type": "http",
3220                "name": "http-server",
3221                "url": "https://api.example.com",
3222                "headers": [
3223                    {
3224                        "name": "Authorization",
3225                        "value": "Bearer token123"
3226                    },
3227                    {
3228                        "name": "Content-Type",
3229                        "value": "application/json"
3230                    }
3231                ]
3232            })
3233        );
3234
3235        let deserialized: McpServer = serde_json::from_value(json).unwrap();
3236        match deserialized {
3237            McpServer::Http(McpServerHttp {
3238                name,
3239                url,
3240                headers,
3241                meta: _,
3242            }) => {
3243                assert_eq!(name, "http-server");
3244                assert_eq!(url, "https://api.example.com");
3245                assert_eq!(headers.len(), 2);
3246                assert_eq!(headers[0].name, "Authorization");
3247                assert_eq!(headers[0].value, "Bearer token123");
3248                assert_eq!(headers[1].name, "Content-Type");
3249                assert_eq!(headers[1].value, "application/json");
3250            }
3251            _ => panic!("Expected Http variant"),
3252        }
3253    }
3254
3255    #[test]
3256    fn test_mcp_server_sse_serialization() {
3257        let server = McpServer::Sse(
3258            McpServerSse::new("sse-server", "https://sse.example.com/events")
3259                .headers(vec![HttpHeader::new("X-API-Key", "apikey456")]),
3260        );
3261
3262        let json = serde_json::to_value(&server).unwrap();
3263        assert_eq!(
3264            json,
3265            json!({
3266                "type": "sse",
3267                "name": "sse-server",
3268                "url": "https://sse.example.com/events",
3269                "headers": [
3270                    {
3271                        "name": "X-API-Key",
3272                        "value": "apikey456"
3273                    }
3274                ]
3275            })
3276        );
3277
3278        let deserialized: McpServer = serde_json::from_value(json).unwrap();
3279        match deserialized {
3280            McpServer::Sse(McpServerSse {
3281                name,
3282                url,
3283                headers,
3284                meta: _,
3285            }) => {
3286                assert_eq!(name, "sse-server");
3287                assert_eq!(url, "https://sse.example.com/events");
3288                assert_eq!(headers.len(), 1);
3289                assert_eq!(headers[0].name, "X-API-Key");
3290                assert_eq!(headers[0].value, "apikey456");
3291            }
3292            _ => panic!("Expected Sse variant"),
3293        }
3294    }
3295}