49 lines
2.0 KiB
Rust
49 lines
2.0 KiB
Rust
//! Manual probe: `probe "<agent command>" <vault> <cli-path> "<prompt>"` runs one
|
|
//! prompt against a real ACP agent and prints every event.
|
|
|
|
use std::time::{Duration, Instant};
|
|
|
|
use notescraft_acp::{AgentCommand, AgentProcess, Event, McpServerConfig, PromptBlock};
|
|
|
|
const STEP: Duration = Duration::from_secs(30);
|
|
const TURN: Duration = Duration::from_secs(180);
|
|
|
|
fn main() -> Result<(), Box<dyn std::error::Error>> {
|
|
let args: Vec<String> = std::env::args().collect();
|
|
let [_, agent, vault, cli, prompt] = args.as_slice() else {
|
|
return Err("usage: probe <agent> <vault> <cli> <prompt>".into());
|
|
};
|
|
let vault = std::path::PathBuf::from(vault);
|
|
let mut proc = AgentProcess::spawn(AgentCommand::new(agent, vault.clone(), notescraft_acp::lean_opencode_env(agent, vec![]))?)?;
|
|
println!("init: {}", proc.initialize_blocking(STEP)?);
|
|
let mcp = McpServerConfig {
|
|
name: "notescraft".into(),
|
|
command: cli.clone(),
|
|
args: vec!["--vault".into(), vault.display().to_string(), "mcp".into()],
|
|
env: vec![],
|
|
};
|
|
let sid = proc.new_session_blocking(&vault, &[mcp], STEP)?;
|
|
println!("session: {sid}");
|
|
if let Ok(secs) = std::env::var("PROBE_WAIT") {
|
|
std::thread::sleep(Duration::from_secs(secs.parse().unwrap_or(0)));
|
|
}
|
|
proc.prompt(&sid, &[PromptBlock::Text(prompt.clone())])?;
|
|
let start = Instant::now();
|
|
while start.elapsed() < TURN {
|
|
let Ok(ev) = proc.events().recv_timeout(Duration::from_secs(1)) else { continue };
|
|
println!("{ev:?}");
|
|
match ev {
|
|
Event::PermissionRequest { request_id, options, .. } => {
|
|
let pick = options.iter().find(|o| o.kind.starts_with("reject")).map(|o| o.id.as_str());
|
|
println!("-> rejecting {pick:?}");
|
|
proc.answer_permission(&request_id, pick)?;
|
|
}
|
|
Event::PromptDone { .. } | Event::Exited { .. } => break,
|
|
_ => {}
|
|
}
|
|
}
|
|
println!("stderr: {}", proc.stderr_tail());
|
|
proc.close()?;
|
|
Ok(())
|
|
}
|