(&mut self)
| 1202 | } |
| 1203 | |
| 1204 | fn show_session_selector(&mut self) { |
| 1205 | self.push_current_popup_to_stack(); |
| 1206 | let coordinator = self.coordinator.clone(); |
| 1207 | let sessions = tokio::task::block_in_place(|| { |
| 1208 | let workspace_path = self.workspace_path_buf(); |
| 1209 | tokio::runtime::Handle::current().block_on(async { |
| 1210 | coordinator |
| 1211 | .list_sessions(&workspace_path) |
| 1212 | .await |
| 1213 | .unwrap_or_default() |
| 1214 | }) |
| 1215 | }); |
| 1216 | |
| 1217 | if sessions.is_empty() { |
| 1218 | self.status = Some("No sessions found.".to_string()); |
| 1219 | return; |
| 1220 | } |
| 1221 | |
| 1222 | let session_items: Vec<SessionItem> = sessions |
| 1223 | .into_iter() |
| 1224 | .map(|s| { |
| 1225 | let last_activity = { |
| 1226 | let elapsed = s.last_activity_at.elapsed().unwrap_or_default(); |
| 1227 | if elapsed.as_secs() < 60 { |
| 1228 | "just now".to_string() |
| 1229 | } else if elapsed.as_secs() < 3600 { |
| 1230 | format!("{}m ago", elapsed.as_secs() / 60) |
| 1231 | } else if elapsed.as_secs() < 86400 { |
| 1232 | format!("{}h ago", elapsed.as_secs() / 3600) |
| 1233 | } else { |
| 1234 | format!("{}d ago", elapsed.as_secs() / 86400) |
| 1235 | } |
| 1236 | }; |
| 1237 | SessionItem { |
| 1238 | session_id: s.session_id, |
| 1239 | session_name: s.session_name, |
| 1240 | last_activity, |
| 1241 | workspace: Some(self.workspace_display.clone()), |
| 1242 | } |
| 1243 | }) |
| 1244 | .collect(); |
| 1245 | |
| 1246 | self.session_selector.show(session_items, None); |
| 1247 | } |
| 1248 | |
| 1249 | fn handle_session_delete(&mut self, item: &SessionItem) { |
| 1250 | let coordinator = self.coordinator.clone(); |
no test coverage detected