use agent_client_protocol_schema::v1;
pub use v1::AuthenticateRequest;
pub use v1::CloseSessionRequest;
pub use v1::DeleteSessionRequest;
pub use v1::InitializeRequest;
pub use v1::ListSessionsRequest;
pub use v1::LoadSessionRequest;
pub use v1::LogoutRequest;
pub use v1::NewSessionRequest;
pub use v1::PromptRequest;
pub use v1::ResumeSessionRequest;
pub use v1::SetSessionConfigOptionRequest;
pub use v1::SetSessionModeRequest;
pub use v1::AuthenticateResponse;
pub use v1::CloseSessionResponse;
pub use v1::DeleteSessionResponse;
pub use v1::InitializeResponse;
pub use v1::ListSessionsResponse;
pub use v1::LoadSessionResponse;
pub use v1::LogoutResponse;
pub use v1::NewSessionResponse;
pub use v1::PromptResponse;
pub use v1::ResumeSessionResponse;
pub use v1::SetSessionConfigOptionResponse;
pub use v1::SetSessionModeResponse;
pub use v1::AgentNotification;
pub use v1::CancelNotification;
pub use v1::CancelRequestNotification;
pub use v1::ClientNotification;
pub use v1::ExtNotification;
pub use v1::ProtocolLevelNotification;
pub use v1::SessionNotification;
pub use v1::AgentRequest;
pub use v1::AgentResponse;
pub use v1::ClientRequest;
pub use v1::ClientResponse;
pub use v1::ToolCall;
pub use v1::ToolCallContent;
pub use v1::ToolCallId;
pub use v1::ToolCallLocation;
pub use v1::ToolCallStatus;
pub use v1::ToolCallUpdate;
pub use v1::ToolCallUpdateFields;
pub use v1::AudioContent;
pub use v1::BlobResourceContents;
pub use v1::ContentBlock;
pub use v1::ContentChunk;
pub use v1::EmbeddedResource;
pub use v1::EmbeddedResourceResource;
pub use v1::ImageContent;
pub use v1::ResourceLink;
pub use v1::Role;
pub use v1::TextContent;
pub use v1::TextResourceContents;
pub use v1::Annotations;
pub use v1::Cost;
pub use v1::Meta;
pub use v1::UsageUpdate;
pub use v1::AgentCapabilities;
pub use v1::BooleanConfigOptionCapabilities;
pub use v1::ClientCapabilities;
pub use v1::ClientSessionCapabilities;
pub use v1::FileSystemCapabilities;
pub use v1::McpCapabilities;
pub use v1::PromptCapabilities;
pub use v1::SessionAdditionalDirectoriesCapabilities;
pub use v1::SessionCapabilities;
pub use v1::SessionCloseCapabilities;
pub use v1::SessionConfigOptionsCapabilities;
pub use v1::SessionDeleteCapabilities;
pub use v1::SessionListCapabilities;
pub use v1::SessionResumeCapabilities;
pub use v1::PermissionOption;
pub use v1::PermissionOptionId;
pub use v1::PermissionOptionKind;
pub use v1::RequestPermissionOutcome;
pub use v1::RequestPermissionRequest;
pub use v1::RequestPermissionResponse;
pub use v1::SelectedPermissionOutcome;
pub use v1::SessionConfigBoolean;
pub use v1::SessionConfigGroupId;
pub use v1::SessionConfigId;
pub use v1::SessionConfigKind;
pub use v1::SessionConfigOption;
pub use v1::SessionConfigOptionCategory;
pub use v1::SessionConfigOptionValue;
pub use v1::SessionConfigSelect;
pub use v1::SessionConfigSelectGroup;
pub use v1::SessionConfigSelectOption;
pub use v1::SessionConfigSelectOptions;
pub use v1::SessionConfigValueId;
pub use v1::SessionId;
pub use v1::SessionInfo;
pub use v1::SessionMode;
pub use v1::SessionModeId;
pub use v1::SessionModeState;
pub use v1::AvailableCommandsUpdate;
pub use v1::ConfigOptionUpdate;
pub use v1::CurrentModeUpdate;
pub use v1::SessionInfoUpdate;
pub use v1::SessionUpdate;
pub use v1::Plan;
pub use v1::PlanEntry;
pub use v1::PlanEntryPriority;
pub use v1::PlanEntryStatus;
pub use v1::TerminalExitStatus;
pub use v1::TerminalId;
pub use v1::McpServer;
pub use v1::McpServerHttp;
pub use v1::McpServerSse;
pub use v1::McpServerStdio;
pub use v1::AgentAuthCapabilities;
pub use v1::AuthMethod;
pub use v1::AuthMethodAgent;
pub use v1::AuthMethodId;
pub use v1::LogoutCapabilities;
pub use v1::AgentMethodNames;
pub use v1::AvailableCommand;
pub use v1::AvailableCommandInput;
pub use v1::ClientMethodNames;
pub use v1::Diff;
pub use v1::EnvVariable;
pub use v1::GeneralMethodNames;
pub use v1::HttpHeader;
pub use v1::Implementation;
pub use v1::MessageId;
pub use v1::StopReason;
pub use v1::UnstructuredCommandInput;
pub use v1::Error;
pub use v1::ErrorCode;
pub use v1::ExtRequest;
pub use v1::ExtResponse;
pub use agent_client_protocol_schema::ProtocolVersion;
pub use v1::Response;
#[cfg(test)]
mod tests {
use super::*;
fn assert_roundtrip<
T: serde::Serialize + serde::de::DeserializeOwned + std::fmt::Debug + PartialEq,
>(
val: &T,
) {
let json = serde_json::to_string(val).expect("serialize");
let val2: T = serde_json::from_str(&json).expect("deserialize");
assert_eq!(val, &val2, "roundtrip failed for JSON: {json}");
}
fn assert_json_roundtrip<
T: serde::de::DeserializeOwned + serde::Serialize + std::fmt::Debug + PartialEq,
>(
json: &str,
) {
let val: T = serde_json::from_str(json).expect("deserialize from literal");
let serialized = serde_json::to_string(&val).expect("serialize");
let val2: T = serde_json::from_str(&serialized).expect("deserialize from serialized");
assert_eq!(
val, val2,
"json roundtrip failed\n input: {json}\n serialized: {serialized}"
);
}
#[test]
fn tool_kind_variants_roundtrip() {
for kind in [
crate::acp::ToolKind::Read,
crate::acp::ToolKind::Edit,
crate::acp::ToolKind::Write,
crate::acp::ToolKind::Execute,
crate::acp::ToolKind::Search,
crate::acp::ToolKind::Fetch,
crate::acp::ToolKind::WebSearch,
crate::acp::ToolKind::Other,
] {
assert_roundtrip(&kind);
}
}
#[test]
fn tool_call_status_variants_roundtrip() {
for status in [
ToolCallStatus::Pending,
ToolCallStatus::InProgress,
ToolCallStatus::Completed,
ToolCallStatus::Failed,
] {
assert_roundtrip(&status);
}
}
#[test]
fn stop_reason_variants_roundtrip() {
for reason in [
StopReason::EndTurn,
StopReason::Cancelled,
StopReason::MaxTokens,
StopReason::MaxTurnRequests,
StopReason::Refusal,
] {
assert_roundtrip(&reason);
}
}
#[test]
fn permission_option_kind_variants_roundtrip() {
for kind in [
PermissionOptionKind::AllowOnce,
PermissionOptionKind::AllowAlways,
PermissionOptionKind::RejectOnce,
PermissionOptionKind::RejectAlways,
] {
assert_roundtrip(&kind);
}
}
#[test]
fn plan_entry_status_variants_roundtrip() {
for status in [
PlanEntryStatus::Pending,
PlanEntryStatus::InProgress,
PlanEntryStatus::Completed,
] {
assert_roundtrip(&status);
}
}
#[test]
fn plan_entry_priority_variants_roundtrip() {
for priority in [
PlanEntryPriority::Low,
PlanEntryPriority::Medium,
PlanEntryPriority::High,
] {
assert_roundtrip(&priority);
}
}
#[test]
fn error_code_variants_roundtrip() {
for code in [
ErrorCode::ParseError,
ErrorCode::InvalidRequest,
ErrorCode::MethodNotFound,
ErrorCode::InvalidParams,
ErrorCode::InternalError,
] {
assert_roundtrip(&code);
}
}
#[test]
fn role_variants_roundtrip() {
assert_roundtrip(&Role::User);
assert_roundtrip(&Role::Assistant);
}
#[test]
fn session_config_kind_variants_roundtrip() {
assert_json_roundtrip::<SessionConfigKind>(r#"{"type":"boolean","currentValue":true}"#);
assert_json_roundtrip::<SessionConfigKind>(
r#"{"type":"select","currentValue":"a","options":[{"value":"a","name":"A"}]}"#,
);
}
#[test]
fn content_block_variants_roundtrip() {
assert_json_roundtrip::<ContentBlock>(r#"{"type":"text","text":"hello"}"#);
assert_json_roundtrip::<ContentBlock>(
r#"{"type":"image","data":"AAAA","mimeType":"image/png"}"#,
);
assert_json_roundtrip::<ContentBlock>(
r#"{"type":"audio","data":"AAAA","mimeType":"audio/wav"}"#,
);
assert_json_roundtrip::<ContentBlock>(
r#"{"type":"resource_link","uri":"file:///tmp/data.txt","name":"data.txt","mimeType":"text/plain"}"#,
);
assert_json_roundtrip::<ContentBlock>(
r#"{"type":"resource","resource":{"uri":"file:///tmp/x","mimeType":"text/plain","text":"content"}}"#,
);
}
#[test]
fn tool_call_content_variants_roundtrip() {
assert_json_roundtrip::<ToolCallContent>(
r#"{"type":"content","content":{"type":"text","text":"output"}}"#,
);
assert_json_roundtrip::<ToolCallContent>(
r#"{"type":"diff","path":"/tmp/file.txt","newText":"hello"}"#,
);
assert_json_roundtrip::<ToolCallContent>(r#"{"type":"terminal","terminalId":"t1"}"#);
}
#[test]
fn session_update_variants_roundtrip() {
assert_json_roundtrip::<SessionUpdate>(
r#"{"sessionUpdate":"user_message_chunk","content":{"type":"text","text":"hello"}}"#,
);
assert_json_roundtrip::<SessionUpdate>(
r#"{"sessionUpdate":"agent_message_chunk","content":{"type":"text","text":"hi"}}"#,
);
assert_json_roundtrip::<SessionUpdate>(
r#"{"sessionUpdate":"tool_call","toolCallId":"tc1","title":"test","kind":"bash","status":"in_progress"}"#,
);
assert_json_roundtrip::<SessionUpdate>(
r#"{"sessionUpdate":"tool_call_update","toolCallId":"tc1","status":"completed"}"#,
);
}
#[test]
fn mcp_server_variants_roundtrip() {
assert_json_roundtrip::<McpServer>(
r#"{"name":"fs","command":"node","args":["server.js"],"env":[]}"#,
);
assert_json_roundtrip::<McpServer>(
r#"{"type":"http","name":"api","url":"http://localhost:8080","headers":[]}"#,
);
assert_json_roundtrip::<McpServer>(
r#"{"type":"sse","name":"events","url":"http://localhost:8080/sse","headers":[]}"#,
);
}
#[test]
fn embedded_resource_resource_variants_roundtrip() {
assert_json_roundtrip::<EmbeddedResourceResource>(
r#"{"uri":"file:///tmp/x","mimeType":"text/plain","text":"hello"}"#,
);
assert_json_roundtrip::<EmbeddedResourceResource>(
r#"{"uri":"file:///tmp/x","mimeType":"application/octet-stream","blob":"AAAA"}"#,
);
}
#[test]
fn auth_method_variants_roundtrip() {
assert_json_roundtrip::<AuthMethod>(r#"{"id":"github","name":"GitHub"}"#);
}
#[test]
fn available_command_input_variants_roundtrip() {
assert_json_roundtrip::<AvailableCommandInput>(r#"{"hint":"query"}"#);
}
#[test]
fn initialize_request_roundtrip() {
assert_json_roundtrip::<InitializeRequest>(
r#"{"protocolVersion":1,"clientCapabilities":{"terminal":true},"clientInfo":{"name":"zed","version":"1.0"}}"#,
);
}
#[test]
fn initialize_response_roundtrip() {
assert_json_roundtrip::<InitializeResponse>(
r#"{"protocolVersion":1,"agentInfo":{"name":"recursive","version":"0.7.0"},"agentCapabilities":{"promptCapabilities":{"text":true}}}"#,
);
}
#[test]
fn new_session_request_roundtrip() {
assert_json_roundtrip::<NewSessionRequest>(r#"{"cwd":"/tmp","mcpServers":[]}"#);
}
#[test]
fn new_session_response_roundtrip() {
assert_json_roundtrip::<NewSessionResponse>(r#"{"sessionId":"s1","capabilities":{}}"#);
}
#[test]
fn prompt_request_roundtrip() {
assert_json_roundtrip::<PromptRequest>(
r#"{"sessionId":"s1","prompt":[{"type":"text","text":"hello"}]}"#,
);
}
#[test]
fn prompt_response_roundtrip() {
assert_json_roundtrip::<PromptResponse>(r#"{"stopReason":"end_turn"}"#);
}
#[test]
fn cancel_notification_roundtrip() {
assert_json_roundtrip::<CancelNotification>(
r#"{"sessionId":"s1","reason":"user request"}"#,
);
}
#[test]
fn session_notification_roundtrip() {
assert_json_roundtrip::<SessionNotification>(
r#"{"sessionId":"s1","update":{"sessionUpdate":"agent_message_chunk","content":{"type":"text","text":"hi"}}}"#,
);
}
#[test]
fn tool_call_roundtrip() {
assert_json_roundtrip::<ToolCall>(
r#"{"toolCallId":"tc1","title":"test","kind":"bash","status":"in_progress"}"#,
);
}
#[test]
fn tool_call_update_roundtrip() {
assert_json_roundtrip::<ToolCallUpdate>(r#"{"toolCallId":"tc1","status":"completed"}"#);
}
#[test]
fn tool_call_location_roundtrip() {
assert_json_roundtrip::<ToolCallLocation>(r#"{"path":"/tmp/file.txt","line":42}"#);
}
#[test]
fn diff_roundtrip() {
assert_json_roundtrip::<Diff>(r#"{"path":"/tmp/file.txt","newText":"hello"}"#);
}
#[test]
fn annotations_roundtrip() {
assert_json_roundtrip::<Annotations>(r#"{"audience":["user"],"priority":0.5}"#);
}
#[test]
fn cost_roundtrip() {
assert_json_roundtrip::<Cost>(r#"{"amount":0.05,"currency":"USD"}"#);
}
#[test]
fn content_chunk_roundtrip() {
assert_json_roundtrip::<ContentChunk>(
r#"{"type":"text","content":{"type":"text","text":"hello"}}"#,
);
}
#[test]
fn agent_capabilities_roundtrip() {
assert_json_roundtrip::<AgentCapabilities>(
r#"{"promptCapabilities":{"text":true},"mcpCapabilities":{"http":true}}"#,
);
}
#[test]
fn client_capabilities_roundtrip() {
assert_json_roundtrip::<ClientCapabilities>(r#"{"terminal":true}"#);
}
#[test]
fn session_capabilities_roundtrip() {
assert_json_roundtrip::<SessionCapabilities>(r#"{}"#);
}
#[test]
fn request_permission_request_roundtrip() {
assert_json_roundtrip::<RequestPermissionRequest>(
r#"{"sessionId":"s1","toolCall":{"toolCallId":"tc1"},"options":[{"kind":"allow_once","optionId":"opt1","name":"Allow"}]}"#,
);
}
#[test]
fn request_permission_response_roundtrip() {
assert_json_roundtrip::<RequestPermissionResponse>(
r#"{"outcome":{"outcome":"selected","optionId":"opt1"}}"#,
);
}
#[test]
fn implementation_roundtrip() {
assert_json_roundtrip::<Implementation>(r#"{"name":"recursive","version":"0.7.0"}"#);
}
#[test]
fn load_session_request_roundtrip() {
assert_json_roundtrip::<LoadSessionRequest>(
r#"{"sessionId":"s1","cwd":"/tmp","mcpServers":[]}"#,
);
}
#[test]
fn load_session_response_roundtrip() {
assert_json_roundtrip::<LoadSessionResponse>(r#"{"sessionId":"s1","messages":[]}"#);
}
#[test]
fn close_session_request_roundtrip() {
assert_json_roundtrip::<CloseSessionRequest>(r#"{"sessionId":"s1"}"#);
}
#[test]
fn close_session_response_roundtrip() {
assert_json_roundtrip::<CloseSessionResponse>(r#"{}"#);
}
#[test]
fn session_id_roundtrip() {
assert_json_roundtrip::<SessionId>(r#""session-abc-123""#);
}
#[test]
fn tool_call_id_roundtrip() {
assert_json_roundtrip::<ToolCallId>(r#""tc-xyz""#);
}
#[test]
fn message_id_roundtrip() {
assert_json_roundtrip::<MessageId>(r#""msg-456""#);
}
#[test]
fn terminal_id_roundtrip() {
assert_json_roundtrip::<TerminalId>(r#""term-1""#);
}
#[test]
fn text_content_roundtrip() {
assert_json_roundtrip::<TextContent>(r#"{"type":"text","text":"hello"}"#);
}
#[test]
fn image_content_roundtrip() {
assert_json_roundtrip::<ImageContent>(
r#"{"type":"image","data":"AAAA","mimeType":"image/png"}"#,
);
}
#[test]
fn plan_roundtrip() {
assert_json_roundtrip::<Plan>(r#"{"entries":[]}"#);
}
#[test]
fn plan_entry_roundtrip() {
assert_json_roundtrip::<PlanEntry>(
r#"{"id":"p1","content":"Do X","status":"pending","priority":"medium"}"#,
);
}
#[test]
fn session_mode_roundtrip() {
assert_json_roundtrip::<SessionMode>(r#"{"id":"default","name":"Default"}"#);
}
#[test]
fn mcp_capabilities_roundtrip() {
assert_json_roundtrip::<McpCapabilities>(r#"{"http":true,"sse":false}"#);
}
#[test]
fn file_system_capabilities_roundtrip() {
assert_json_roundtrip::<FileSystemCapabilities>(
r#"{"readTextFile":true,"writeTextFile":false}"#,
);
}
#[test]
fn error_roundtrip() {
assert_json_roundtrip::<Error>(r#"{"code":-32600,"message":"Invalid Request"}"#);
}
#[test]
fn usage_update_roundtrip() {
assert_json_roundtrip::<UsageUpdate>(r#"{"used":1500,"size":200000}"#);
}
#[test]
fn auth_method_agent_roundtrip() {
assert_json_roundtrip::<AuthMethodAgent>(r#"{"id":"github","name":"GitHub"}"#);
}
#[test]
fn env_variable_roundtrip() {
assert_json_roundtrip::<EnvVariable>(r#"{"name":"API_KEY","value":"secret123"}"#);
}
#[test]
fn http_header_roundtrip() {
assert_json_roundtrip::<HttpHeader>(r#"{"name":"Authorization","value":"Bearer token"}"#);
}
#[test]
fn option_field_none() {
assert_json_roundtrip::<Implementation>(r#"{"name":"test","version":"1.0"}"#);
assert_json_roundtrip::<Implementation>(
r#"{"name":"test","version":"1.0","title":"Test App"}"#,
);
assert_json_roundtrip::<Annotations>(r#"{}"#);
assert_json_roundtrip::<ToolCallLocation>(r#"{"path":"/tmp/f"}"#);
assert_json_roundtrip::<Diff>(r#"{"path":"/tmp/f","newText":"new"}"#);
}
#[test]
fn vec_field_empty() {
assert_json_roundtrip::<Plan>(r#"{"entries":[]}"#);
assert_json_roundtrip::<PromptRequest>(r#"{"sessionId":"s1","prompt":[]}"#);
assert_json_roundtrip::<LoadSessionResponse>(r#"{"sessionId":"s1","messages":[]}"#);
assert_json_roundtrip::<ToolCall>(
r#"{"toolCallId":"tc1","title":"t","content":[],"locations":[]}"#,
);
}
#[test]
fn nested_enum_coverage() {
assert_json_roundtrip::<ContentChunk>(
r#"{"type":"text","content":{"type":"text","text":"hello"}}"#,
);
assert_json_roundtrip::<ContentChunk>(
r#"{"type":"image","content":{"type":"image","data":"AAAA","mimeType":"image/png"}}"#,
);
assert_json_roundtrip::<ContentChunk>(
r#"{"type":"resource_link","content":{"type":"resource_link","uri":"file:///x","name":"x","mimeType":"text/plain"}}"#,
);
assert_json_roundtrip::<SessionNotification>(
r#"{"sessionId":"s1","update":{"sessionUpdate":"tool_call","toolCallId":"tc1","title":"Run","kind":"execute","status":"in_progress"}}"#,
);
}
#[test]
fn enum_non_default_variant_roundtrip() {
assert_roundtrip(&crate::acp::ToolKind::Read);
assert_roundtrip(&crate::acp::ToolKind::Edit);
assert_roundtrip(&ToolCallStatus::Completed);
assert_roundtrip(&ToolCallStatus::Failed);
assert_roundtrip(&StopReason::Cancelled);
assert_roundtrip(&StopReason::Refusal);
}
#[test]
fn session_update_plan_variant_roundtrip() {
assert_json_roundtrip::<SessionUpdate>(r#"{"sessionUpdate":"plan","entries":[]}"#);
}
#[test]
fn session_update_usage_update_variant_roundtrip() {
assert_json_roundtrip::<SessionUpdate>(
r#"{"sessionUpdate":"usage_update","used":1000,"size":200000}"#,
);
}
#[test]
fn permission_option_all_kinds() {
for (kind_str, kind) in [
("allow_once", PermissionOptionKind::AllowOnce),
("allow_always", PermissionOptionKind::AllowAlways),
("reject_once", PermissionOptionKind::RejectOnce),
("reject_always", PermissionOptionKind::RejectAlways),
] {
let json = format!(r#"{{"kind":"{kind_str}","optionId":"o1","name":"L"}}"#);
assert_json_roundtrip::<PermissionOption>(&json);
assert_roundtrip(&kind);
}
}
}