1use crate::core::{Message, ToolCall};
2use serde::{Deserialize, Serialize};
3
4fn default_subagent_status_running() -> SubAgentLifecycleStatus {
5 SubAgentLifecycleStatus::Running
6}
7
8#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
9#[serde(rename_all = "snake_case")]
10pub enum SubAgentLifecycleStatus {
11 Pending,
12 Running,
13 Completed,
14 Failed,
15 Cancelled,
16}
17
18#[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq)]
19#[serde(rename_all = "snake_case")]
20pub enum SubAgentFailureReason {
21 ToolError,
22 ApprovalDenied,
23 RuntimeError,
24 InterruptedByRestart,
25 Unknown,
26}
27
28#[derive(Debug, Clone, Serialize, Deserialize)]
29#[serde(tag = "event", rename_all = "snake_case")]
30pub enum SessionEvent {
31 Message {
32 id: String,
33 #[serde(flatten)]
34 message: Message,
35 },
36 ToolCall {
37 #[serde(flatten)]
38 call: ToolCall,
39 },
40 ToolResult {
41 id: String,
42 is_error: bool,
43 output: String,
44 #[serde(default, skip_serializing_if = "Option::is_none")]
45 result: Option<crate::tool::ToolResult>,
46 },
47 Approval {
48 id: String,
49 tool_name: String,
50 approved: bool,
51 },
52 Thinking {
53 id: String,
54 content: String,
55 },
56 Compact {
57 id: String,
58 summary: String,
59 },
60 SubAgentStart {
61 id: String,
62 #[serde(default, skip_serializing_if = "Option::is_none")]
63 task_id: Option<String>,
64 #[serde(default, skip_serializing_if = "Option::is_none")]
65 name: Option<String>,
66 #[serde(default, skip_serializing_if = "Option::is_none")]
67 parent_id: Option<String>,
68 #[serde(default, skip_serializing_if = "Option::is_none")]
69 parent_session_id: Option<String>,
70 #[serde(default, skip_serializing_if = "Option::is_none")]
71 agent_name: Option<String>,
72 #[serde(default, skip_serializing_if = "Option::is_none")]
73 session_id: Option<String>,
74 #[serde(default = "default_subagent_status_running")]
75 status: SubAgentLifecycleStatus,
76 #[serde(default)]
77 created_at: u64,
78 #[serde(default)]
79 updated_at: u64,
80 prompt: String,
81 depth: usize,
82 },
83 SubAgentProgress {
84 id: String,
85 #[serde(default, skip_serializing_if = "Option::is_none")]
86 task_id: Option<String>,
87 #[serde(default)]
88 seq: u64,
89 content: String,
90 },
91 SubAgentResult {
92 id: String,
93 #[serde(default, skip_serializing_if = "Option::is_none")]
94 task_id: Option<String>,
95 #[serde(default = "default_subagent_status_running")]
96 status: SubAgentLifecycleStatus,
97 #[serde(default, skip_serializing_if = "Option::is_none")]
98 summary: Option<String>,
99 #[serde(default, skip_serializing_if = "Option::is_none")]
100 failure_reason: Option<SubAgentFailureReason>,
101 is_error: bool,
102 output: String,
103 },
104}
105
106#[derive(Debug, Clone, Serialize, Deserialize)]
107pub struct SessionMetadata {
108 pub id: String,
109 pub title: String,
110 pub created_at: u64, pub last_updated_at: u64, #[serde(default, skip_serializing_if = "Option::is_none")]
113 pub parent_session_id: Option<String>,
114}