1use serde::de::{self, MapAccess, SeqAccess, Visitor};
2use serde::{Deserialize, Deserializer, Serialize};
3
4use crate::{ProcessCommand, SessionName, TerminalSize};
5
6use super::compat::{compat_next_element, required_next};
7
8#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
10pub struct NewSessionRequest {
11 pub session_name: SessionName,
13 pub detached: bool,
15 pub size: Option<TerminalSize>,
17 #[serde(default)]
19 pub environment: Option<Vec<String>>,
20}
21
22#[derive(Debug, Clone, PartialEq, Eq, Serialize)]
24pub struct NewSessionExtRequest {
25 pub session_name: Option<SessionName>,
27 #[serde(default)]
29 pub working_directory: Option<String>,
30 pub detached: bool,
32 pub size: Option<TerminalSize>,
34 #[serde(default)]
36 pub environment: Option<Vec<String>>,
37 #[serde(default)]
39 pub group_target: Option<SessionName>,
40 #[serde(default)]
42 pub attach_if_exists: bool,
43 #[serde(default)]
45 pub detach_other_clients: bool,
46 #[serde(default)]
48 pub kill_other_clients: bool,
49 #[serde(default)]
51 pub flags: Option<Vec<String>>,
52 #[serde(default)]
54 pub window_name: Option<String>,
55 #[serde(default)]
57 pub print_session_info: bool,
58 #[serde(default)]
60 pub print_format: Option<String>,
61 #[serde(default)]
64 pub command: Option<Vec<String>>,
65 #[serde(default)]
67 pub process_command: Option<ProcessCommand>,
68 #[serde(default)]
70 pub client_environment: Option<Vec<String>>,
71}
72
73impl<'de> Deserialize<'de> for NewSessionExtRequest {
74 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
75 where
76 D: Deserializer<'de>,
77 {
78 deserializer.deserialize_struct(
79 "NewSessionExtRequest",
80 &[
81 "session_name",
82 "working_directory",
83 "detached",
84 "size",
85 "environment",
86 "group_target",
87 "attach_if_exists",
88 "detach_other_clients",
89 "kill_other_clients",
90 "flags",
91 "window_name",
92 "print_session_info",
93 "print_format",
94 "command",
95 "process_command",
96 "client_environment",
97 ],
98 NewSessionExtRequestVisitor,
99 )
100 }
101}
102
103struct NewSessionExtRequestVisitor;
104
105impl<'de> Visitor<'de> for NewSessionExtRequestVisitor {
106 type Value = NewSessionExtRequest;
107
108 fn expecting(&self, formatter: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
109 formatter.write_str("a new-session extended request")
110 }
111
112 fn visit_seq<A>(self, mut seq: A) -> Result<Self::Value, A::Error>
113 where
114 A: SeqAccess<'de>,
115 {
116 let session_name = required_next(&mut seq, 0, &self)?;
117 let working_directory = required_next(&mut seq, 1, &self)?;
118 let detached = required_next(&mut seq, 2, &self)?;
119 let size = required_next(&mut seq, 3, &self)?;
120 let environment = required_next(&mut seq, 4, &self)?;
121 let group_target = required_next(&mut seq, 5, &self)?;
122 let attach_if_exists = required_next(&mut seq, 6, &self)?;
123 let detach_other_clients = required_next(&mut seq, 7, &self)?;
124 let kill_other_clients = required_next(&mut seq, 8, &self)?;
125 let flags = required_next(&mut seq, 9, &self)?;
126 let window_name = required_next(&mut seq, 10, &self)?;
127 let print_session_info = required_next(&mut seq, 11, &self)?;
128 let print_format = required_next(&mut seq, 12, &self)?;
129 let command = required_next(&mut seq, 13, &self)?;
130 let process_command = compat_next_element(&mut seq)?;
131 let client_environment = compat_next_element(&mut seq)?;
132
133 Ok(NewSessionExtRequest {
134 session_name,
135 working_directory,
136 detached,
137 size,
138 environment,
139 group_target,
140 attach_if_exists,
141 detach_other_clients,
142 kill_other_clients,
143 flags,
144 window_name,
145 print_session_info,
146 print_format,
147 command,
148 process_command,
149 client_environment,
150 })
151 }
152
153 fn visit_map<A>(self, mut map: A) -> Result<Self::Value, A::Error>
154 where
155 A: MapAccess<'de>,
156 {
157 let mut session_name = None;
158 let mut working_directory = None;
159 let mut detached = None;
160 let mut size = None;
161 let mut environment = None;
162 let mut group_target = None;
163 let mut attach_if_exists = None;
164 let mut detach_other_clients = None;
165 let mut kill_other_clients = None;
166 let mut flags = None;
167 let mut window_name = None;
168 let mut print_session_info = None;
169 let mut print_format = None;
170 let mut command = None;
171 let mut process_command = None;
172 let mut client_environment = None;
173
174 while let Some(key) = map.next_key::<String>()? {
175 match key.as_str() {
176 "session_name" => session_name = Some(map.next_value()?),
177 "working_directory" => working_directory = Some(map.next_value()?),
178 "detached" => detached = Some(map.next_value()?),
179 "size" => size = Some(map.next_value()?),
180 "environment" => environment = Some(map.next_value()?),
181 "group_target" => group_target = Some(map.next_value()?),
182 "attach_if_exists" => attach_if_exists = Some(map.next_value()?),
183 "detach_other_clients" => detach_other_clients = Some(map.next_value()?),
184 "kill_other_clients" => kill_other_clients = Some(map.next_value()?),
185 "flags" => flags = Some(map.next_value()?),
186 "window_name" => window_name = Some(map.next_value()?),
187 "print_session_info" => print_session_info = Some(map.next_value()?),
188 "print_format" => print_format = Some(map.next_value()?),
189 "command" => command = Some(map.next_value()?),
190 "process_command" => process_command = Some(map.next_value()?),
191 "client_environment" => client_environment = Some(map.next_value()?),
192 _ => {
193 let _: de::IgnoredAny = map.next_value()?;
194 }
195 }
196 }
197
198 Ok(NewSessionExtRequest {
199 session_name: session_name.ok_or_else(|| de::Error::missing_field("session_name"))?,
200 working_directory: working_directory
201 .ok_or_else(|| de::Error::missing_field("working_directory"))?,
202 detached: detached.ok_or_else(|| de::Error::missing_field("detached"))?,
203 size: size.ok_or_else(|| de::Error::missing_field("size"))?,
204 environment: environment.ok_or_else(|| de::Error::missing_field("environment"))?,
205 group_target: group_target.ok_or_else(|| de::Error::missing_field("group_target"))?,
206 attach_if_exists: attach_if_exists
207 .ok_or_else(|| de::Error::missing_field("attach_if_exists"))?,
208 detach_other_clients: detach_other_clients
209 .ok_or_else(|| de::Error::missing_field("detach_other_clients"))?,
210 kill_other_clients: kill_other_clients
211 .ok_or_else(|| de::Error::missing_field("kill_other_clients"))?,
212 flags: flags.ok_or_else(|| de::Error::missing_field("flags"))?,
213 window_name: window_name.ok_or_else(|| de::Error::missing_field("window_name"))?,
214 print_session_info: print_session_info
215 .ok_or_else(|| de::Error::missing_field("print_session_info"))?,
216 print_format: print_format.ok_or_else(|| de::Error::missing_field("print_format"))?,
217 command: command.ok_or_else(|| de::Error::missing_field("command"))?,
218 process_command: process_command.unwrap_or_default(),
219 client_environment: client_environment.unwrap_or_default(),
220 })
221 }
222}
223
224#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
226pub struct HasSessionRequest {
227 pub target: SessionName,
229}
230
231#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
233pub struct KillSessionRequest {
234 pub target: SessionName,
236 #[serde(default)]
238 pub kill_all_except_target: bool,
239 #[serde(default)]
241 pub clear_alerts: bool,
242}
243
244#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
246pub struct CreateSessionLeaseRequest {
247 pub session_name: SessionName,
249 pub ttl_millis: u64,
251}
252
253#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
255pub struct RenewSessionLeaseRequest {
256 pub session_name: SessionName,
258 pub token: u64,
260 pub ttl_millis: u64,
262}
263
264#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
266pub struct ReleaseSessionLeaseRequest {
267 pub session_name: SessionName,
269 pub token: u64,
271}
272
273#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
275pub struct RenameSessionRequest {
276 pub target: SessionName,
278 pub new_name: SessionName,
280}
281
282#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
284pub struct ListSessionsRequest {
285 pub format: Option<String>,
287 #[serde(default)]
289 pub filter: Option<String>,
290 #[serde(default)]
292 pub sort_order: Option<String>,
293 #[serde(default)]
295 pub reversed: bool,
296}