Converted all external tool calling to async

This commit is contained in:
Timmy
2026-06-29 16:59:54 +01:00
parent 75f41088b1
commit feb35ddd10
49 changed files with 482 additions and 496 deletions
@@ -28,7 +28,7 @@ impl AgentPool {
// Verify agent exists, is Running, and grab its worktree path.
let worktree_path = {
let agents = self.agents.lock().map_err(|e| e.to_string())?;
let agents = self.agents.lock().await;
let agent = agents
.get(&key)
.ok_or_else(|| format!("No agent '{agent_name}' for story '{story_id}'"))?;
@@ -82,7 +82,7 @@ impl AgentPool {
merge_failure_reported_for_advance,
session_id_for_advance,
) = {
let mut agents = self.agents.lock().map_err(|e| e.to_string())?;
let mut agents = self.agents.lock().await;
let agent = agents.get_mut(&key).ok_or_else(|| {
format!("Agent '{agent_name}' for story '{story_id}' disappeared during gate check")
})?;
@@ -2,7 +2,8 @@
use crate::io::watcher::WatcherEvent;
use crate::slog;
use std::collections::HashMap;
use std::sync::{Arc, Mutex};
use std::sync::Arc;
use tokio::sync::Mutex;
use tokio::sync::broadcast;
use super::super::super::super::{AgentEvent, CompletionReport, PipelineStage, pipeline_stage};
@@ -45,10 +46,7 @@ pub(in crate::agents::pool) async fn run_server_owned_completion(
// Guard: skip if completion was already recorded (legacy path).
{
let lock = match agents.lock() {
Ok(a) => a,
Err(_) => return,
};
let lock = agents.lock().await;
match lock.get(&key) {
Some(agent) if agent.completion.is_some() => {
slog!(
@@ -64,10 +62,7 @@ pub(in crate::agents::pool) async fn run_server_owned_completion(
// Get worktree path for running gates.
let worktree_path = {
let lock = match agents.lock() {
Ok(a) => a,
Err(_) => return,
};
let lock = agents.lock().await;
lock.get(&key)
.and_then(|a| a.worktree_info.as_ref().map(|wt| wt.path.clone()))
};
@@ -192,10 +187,7 @@ pub(in crate::agents::pool) async fn run_server_owned_completion(
// Store completion report, extract data for pipeline advance, then
// remove the entry so completed agents never appear in list_agents.
let (tx, project_root_for_advance, wt_path_for_advance, merge_failure_reported_for_advance) = {
let mut lock = match agents.lock() {
Ok(a) => a,
Err(_) => return,
};
let mut lock = agents.lock().await;
let agent = match lock.get_mut(&key) {
Some(a) => a,
None => return,
@@ -108,7 +108,7 @@ async fn server_owned_completion_skips_when_already_completed() {
);
// Subscribe before calling so we can check if Done event was emitted.
let mut rx = pool.subscribe("s10", "coder-1").unwrap();
let mut rx = pool.subscribe("s10", "coder-1").await.unwrap();
run_server_owned_completion(
&pool.agents,
@@ -121,7 +121,7 @@ async fn server_owned_completion_skips_when_already_completed() {
.await;
// Status should remain Completed (unchanged) — no gate re-run.
let agents = pool.agents.lock().unwrap();
let agents = pool.agents.try_lock().unwrap();
let key = super::super::super::composite_key("s10", "coder-1");
let agent = agents.get(&key).unwrap();
assert_eq!(agent.status, AgentStatus::Completed);
@@ -147,7 +147,7 @@ async fn server_owned_completion_runs_gates_on_clean_worktree() {
let pool = AgentPool::new_test(3001);
pool.inject_test_agent_with_path("s11", "coder-1", AgentStatus::Running, repo.to_path_buf());
let mut rx = pool.subscribe("s11", "coder-1").unwrap();
let mut rx = pool.subscribe("s11", "coder-1").await.unwrap();
run_server_owned_completion(
&pool.agents,
@@ -160,7 +160,7 @@ async fn server_owned_completion_runs_gates_on_clean_worktree() {
.await;
// Agent entry should be removed from the map after completion.
let agents = pool.agents.lock().unwrap();
let agents = pool.agents.try_lock().unwrap();
let key = super::super::super::composite_key("s11", "coder-1");
assert!(
agents.get(&key).is_none(),
@@ -192,7 +192,7 @@ async fn server_owned_completion_fails_on_dirty_worktree() {
let pool = AgentPool::new_test(3001);
pool.inject_test_agent_with_path("s12", "coder-1", AgentStatus::Running, repo.to_path_buf());
let mut rx = pool.subscribe("s12", "coder-1").unwrap();
let mut rx = pool.subscribe("s12", "coder-1").await.unwrap();
run_server_owned_completion(
&pool.agents,
@@ -205,7 +205,7 @@ async fn server_owned_completion_fails_on_dirty_worktree() {
.await;
// Agent entry should be removed from the map after completion (even on failure).
let agents = pool.agents.lock().unwrap();
let agents = pool.agents.try_lock().unwrap();
let key = super::super::super::composite_key("s12", "coder-1");
assert!(
agents.get(&key).is_none(),
@@ -307,7 +307,7 @@ async fn server_owned_completion_is_noop_for_mergemaster() {
// The agent entry should remain in the pool (lifecycle cleanup is the
// caller's responsibility, not run_server_owned_completion's).
let agents = pool.agents.lock().unwrap();
let agents = pool.agents.try_lock().unwrap();
let key = super::super::super::composite_key("99_story_merge445", "mergemaster");
assert!(
agents.get(&key).is_some(),
@@ -361,7 +361,7 @@ async fn server_owned_completion_preserves_dirty_worktree_with_committed_work()
let pool = AgentPool::new_test(3001);
pool.inject_test_agent_with_path("645_test", "coder-1", AgentStatus::Running, wt_path.clone());
let mut rx = pool.subscribe("645_test", "coder-1").unwrap();
let mut rx = pool.subscribe("645_test", "coder-1").await.unwrap();
run_server_owned_completion(
&pool.agents,