diff --git a/src-tauri/src/services/session_usage.rs b/src-tauri/src/services/session_usage.rs index 254371c02..27f71700a 100644 --- a/src-tauri/src/services/session_usage.rs +++ b/src-tauri/src/services/session_usage.rs @@ -107,7 +107,11 @@ pub fn sync_claude_session_logs(db: &Database) -> Result Vec { let mut files = Vec::new(); @@ -126,7 +130,22 @@ fn collect_jsonl_files(projects_dir: &Path) -> Vec { for sub_entry in sub_entries.flatten() { let sub_path = sub_entry.path(); if sub_path.extension().and_then(|e| e.to_str()) == Some("jsonl") { + // 主会话 JSONL 文件 files.push(sub_path); + } else if sub_path.is_dir() { + // 扫描子 agent 目录: 项目/SESSION_ID/subagents/*.jsonl + let subagents_dir = sub_path.join("subagents"); + if subagents_dir.is_dir() { + if let Ok(agent_entries) = fs::read_dir(&subagents_dir) { + for agent_entry in agent_entries.flatten() { + let agent_path = agent_entry.path(); + if agent_path.extension().and_then(|e| e.to_str()) == Some("jsonl") + { + files.push(agent_path); + } + } + } + } } } } @@ -637,4 +656,27 @@ mod tests { Ok(()) } + + #[test] + fn test_collect_jsonl_files_includes_subagents() { + let tmp = std::env::temp_dir().join(format!("cc-switch-test-{}", uuid::Uuid::new_v4())); + let project = tmp.join("project"); + let session_dir = project.join("test-session"); + let subagents_dir = session_dir.join("subagents"); + fs::create_dir_all(&subagents_dir).unwrap(); + + fs::write(project.join("main.jsonl"), "{}").unwrap(); + fs::write(subagents_dir.join("agent-abc.jsonl"), "{}").unwrap(); + + let files = collect_jsonl_files(&tmp); + assert_eq!(files.len(), 2); + let paths: Vec = files + .iter() + .map(|p| p.to_string_lossy().to_string()) + .collect(); + assert!(paths.iter().any(|p| p.contains("main.jsonl"))); + assert!(paths.iter().any(|p| p.contains("agent-abc.jsonl"))); + + fs::remove_dir_all(&tmp).ok(); + } }