mirror of
https://github.com/affaan-m/everything-claude-code.git
synced 2026-04-16 23:23:29 +08:00
feat: detect custom ecc2 harness markers
This commit is contained in:
@@ -158,7 +158,7 @@ pub fn list_sessions(db: &StateStore) -> Result<Vec<Session>> {
|
||||
db.list_sessions()
|
||||
}
|
||||
|
||||
pub fn get_status(db: &StateStore, id: &str) -> Result<SessionStatus> {
|
||||
pub fn get_status(db: &StateStore, cfg: &Config, id: &str) -> Result<SessionStatus> {
|
||||
let session = resolve_session(db, id)?;
|
||||
let session_id = session.id.clone();
|
||||
Ok(SessionStatus {
|
||||
@@ -166,7 +166,8 @@ pub fn get_status(db: &StateStore, id: &str) -> Result<SessionStatus> {
|
||||
.get_session_harness_info(&session_id)?
|
||||
.unwrap_or_else(|| {
|
||||
SessionHarnessInfo::detect(&session.agent_type, &session.working_dir)
|
||||
}),
|
||||
})
|
||||
.with_config_detection(cfg, &session.working_dir),
|
||||
profile: db.get_session_profile(&session_id)?,
|
||||
session,
|
||||
parent_session: db.latest_task_handoff_source(&session_id)?,
|
||||
@@ -5500,12 +5501,38 @@ mod tests {
|
||||
db.insert_session(&build_session("older", SessionState::Running, older))?;
|
||||
db.insert_session(&build_session("newer", SessionState::Idle, newer))?;
|
||||
|
||||
let status = get_status(&db, "latest")?;
|
||||
let status = get_status(&db, &cfg, "latest")?;
|
||||
assert_eq!(status.session.id, "newer");
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn get_status_uses_configured_custom_harness_markers() -> Result<()> {
|
||||
let tempdir = TestDir::new("manager-custom-harness-status")?;
|
||||
fs::create_dir_all(tempdir.path().join(".acme"))?;
|
||||
let mut cfg = build_config(tempdir.path());
|
||||
cfg.harness_runners.insert(
|
||||
"acme-runner".to_string(),
|
||||
crate::config::HarnessRunnerConfig {
|
||||
project_markers: vec![PathBuf::from(".acme")],
|
||||
..Default::default()
|
||||
},
|
||||
);
|
||||
let db = StateStore::open(&cfg.db_path)?;
|
||||
let mut session = build_session("custom", SessionState::Pending, Utc::now());
|
||||
session.agent_type = "".to_string();
|
||||
session.working_dir = tempdir.path().to_path_buf();
|
||||
db.insert_session(&session)?;
|
||||
|
||||
let status = get_status(&db, &cfg, "custom")?;
|
||||
assert_eq!(status.harness.primary, HarnessKind::Unknown);
|
||||
assert_eq!(status.harness.primary_label, "acme-runner");
|
||||
assert_eq!(status.harness.detected_summary(), "acme-runner");
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn get_status_surfaces_handoff_lineage() -> Result<()> {
|
||||
let tempdir = TestDir::new("manager-status-lineage")?;
|
||||
@@ -5538,14 +5565,14 @@ mod tests {
|
||||
"task_handoff",
|
||||
)?;
|
||||
|
||||
let status = get_status(&db, "parent")?;
|
||||
let status = get_status(&db, &cfg, "parent")?;
|
||||
let rendered = status.to_string();
|
||||
|
||||
assert!(rendered.contains("Children:"));
|
||||
assert!(rendered.contains("child"));
|
||||
assert!(rendered.contains("sibling"));
|
||||
|
||||
let child_status = get_status(&db, "child")?;
|
||||
let child_status = get_status(&db, &cfg, "child")?;
|
||||
assert_eq!(child_status.parent_session.as_deref(), Some("parent"));
|
||||
|
||||
Ok(())
|
||||
|
||||
@@ -111,9 +111,34 @@ pub struct SessionHarnessInfo {
|
||||
pub primary: HarnessKind,
|
||||
pub primary_label: String,
|
||||
pub detected: Vec<HarnessKind>,
|
||||
pub detected_labels: Vec<String>,
|
||||
}
|
||||
|
||||
impl SessionHarnessInfo {
|
||||
fn detected_labels_for(detected: &[HarnessKind]) -> Vec<String> {
|
||||
detected.iter().map(|harness| harness.to_string()).collect()
|
||||
}
|
||||
|
||||
fn configured_detected_labels(cfg: &crate::config::Config, working_dir: &Path) -> Vec<String> {
|
||||
let mut labels = Vec::new();
|
||||
for (name, runner) in &cfg.harness_runners {
|
||||
if runner.project_markers.is_empty() {
|
||||
continue;
|
||||
}
|
||||
if runner
|
||||
.project_markers
|
||||
.iter()
|
||||
.any(|marker| working_dir.join(marker).exists())
|
||||
{
|
||||
let label = Self::runner_key(name);
|
||||
if !label.is_empty() && !labels.contains(&label) {
|
||||
labels.push(label);
|
||||
}
|
||||
}
|
||||
}
|
||||
labels
|
||||
}
|
||||
|
||||
pub fn runner_key(agent_type: &str) -> String {
|
||||
let canonical = HarnessKind::canonical_agent_type(agent_type);
|
||||
match HarnessKind::from_agent_type(&canonical) {
|
||||
@@ -167,10 +192,12 @@ impl SessionHarnessInfo {
|
||||
harness => harness,
|
||||
};
|
||||
|
||||
let detected_labels = Self::detected_labels_for(&detected);
|
||||
Self {
|
||||
primary,
|
||||
primary_label: Self::primary_label_for(agent_type, primary),
|
||||
detected,
|
||||
detected_labels,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -187,6 +214,7 @@ impl SessionHarnessInfo {
|
||||
}
|
||||
|
||||
let normalized_label = harness_label.trim().to_ascii_lowercase();
|
||||
let detected_labels = Self::detected_labels_for(&detected);
|
||||
Self {
|
||||
primary,
|
||||
primary_label: if normalized_label.is_empty() {
|
||||
@@ -195,18 +223,36 @@ impl SessionHarnessInfo {
|
||||
normalized_label
|
||||
},
|
||||
detected,
|
||||
detected_labels,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn with_config_detection(
|
||||
mut self,
|
||||
cfg: &crate::config::Config,
|
||||
working_dir: &Path,
|
||||
) -> Self {
|
||||
for label in Self::configured_detected_labels(cfg, working_dir) {
|
||||
if !self.detected_labels.contains(&label) {
|
||||
self.detected_labels.push(label);
|
||||
}
|
||||
}
|
||||
|
||||
if self.primary == HarnessKind::Unknown
|
||||
&& self.primary_label == HarnessKind::Unknown.as_str()
|
||||
&& !self.detected_labels.is_empty()
|
||||
{
|
||||
self.primary_label = self.detected_labels[0].clone();
|
||||
}
|
||||
|
||||
self
|
||||
}
|
||||
|
||||
pub fn detected_summary(&self) -> String {
|
||||
if self.detected.is_empty() {
|
||||
if self.detected_labels.is_empty() {
|
||||
"none detected".to_string()
|
||||
} else {
|
||||
self.detected
|
||||
.iter()
|
||||
.map(|harness| harness.to_string())
|
||||
.collect::<Vec<_>>()
|
||||
.join(", ")
|
||||
self.detected_labels.join(", ")
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -573,6 +619,7 @@ mod tests {
|
||||
harness.detected,
|
||||
vec![HarnessKind::Claude, HarnessKind::Codex]
|
||||
);
|
||||
assert_eq!(harness.detected_labels, vec!["claude", "codex"]);
|
||||
assert_eq!(harness.detected_summary(), "claude, codex");
|
||||
Ok(())
|
||||
}
|
||||
@@ -587,6 +634,7 @@ mod tests {
|
||||
assert_eq!(harness.primary, HarnessKind::Gemini);
|
||||
assert_eq!(harness.primary_label, "gemini");
|
||||
assert_eq!(harness.detected, vec![HarnessKind::Gemini]);
|
||||
assert_eq!(harness.detected_labels, vec!["gemini"]);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
@@ -610,6 +658,7 @@ mod tests {
|
||||
assert_eq!(harness.primary, HarnessKind::Unknown);
|
||||
assert_eq!(harness.primary_label, "custom-runner");
|
||||
assert!(harness.detected.is_empty());
|
||||
assert!(harness.detected_labels.is_empty());
|
||||
}
|
||||
|
||||
#[test]
|
||||
@@ -626,6 +675,54 @@ mod tests {
|
||||
harness.detected,
|
||||
vec![HarnessKind::Claude, HarnessKind::Codex]
|
||||
);
|
||||
assert_eq!(harness.detected_labels, vec!["claude", "codex"]);
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn config_detection_adds_custom_markers_to_detected_summary(
|
||||
) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let repo = TestDir::new("session-harness-custom-config")?;
|
||||
fs::create_dir_all(repo.path().join(".acme"))?;
|
||||
let mut cfg = crate::config::Config::default();
|
||||
cfg.harness_runners.insert(
|
||||
"acme-runner".to_string(),
|
||||
crate::config::HarnessRunnerConfig {
|
||||
project_markers: vec![PathBuf::from(".acme")],
|
||||
..Default::default()
|
||||
},
|
||||
);
|
||||
|
||||
let harness =
|
||||
SessionHarnessInfo::detect("", repo.path()).with_config_detection(&cfg, repo.path());
|
||||
assert_eq!(harness.primary, HarnessKind::Unknown);
|
||||
assert_eq!(harness.primary_label, "acme-runner");
|
||||
assert_eq!(harness.detected_labels, vec!["acme-runner"]);
|
||||
assert_eq!(harness.detected_summary(), "acme-runner");
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn config_detection_preserves_custom_primary_label_and_appends_marker_matches(
|
||||
) -> Result<(), Box<dyn std::error::Error>> {
|
||||
let repo = TestDir::new("session-harness-config-append")?;
|
||||
fs::create_dir_all(repo.path().join(".acme"))?;
|
||||
fs::create_dir_all(repo.path().join(".codex"))?;
|
||||
let mut cfg = crate::config::Config::default();
|
||||
cfg.harness_runners.insert(
|
||||
"acme-runner".to_string(),
|
||||
crate::config::HarnessRunnerConfig {
|
||||
project_markers: vec![PathBuf::from(".acme")],
|
||||
..Default::default()
|
||||
},
|
||||
);
|
||||
|
||||
let harness = SessionHarnessInfo::detect("acme-runner", repo.path())
|
||||
.with_config_detection(&cfg, repo.path());
|
||||
assert_eq!(harness.primary, HarnessKind::Unknown);
|
||||
assert_eq!(harness.primary_label, "acme-runner");
|
||||
assert_eq!(harness.detected_labels, vec!["codex", "acme-runner"]);
|
||||
assert_eq!(harness.detected_summary(), "codex, acme-runner");
|
||||
Ok(())
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user