From df8502d83b025b672935a5b5f11d04668e01779f Mon Sep 17 00:00:00 2001 From: Bryan Helmkamp Date: Mon, 23 Feb 2026 11:14:25 -0500 Subject: [PATCH] Merge agent-cli crate into agent as cli module The agent-cli binary was a thin wrapper over the agent library with nothing else depending on it. Moving it into the agent crate as a `pub mod cli` with a `[[bin]]` entry reduces workspace complexity and follows the attractor crate pattern. Co-Authored-By: Claude Opus 4.6 --- Cargo.lock | 16 +++--------- crates/agent-cli/Cargo.toml | 25 ------------------- crates/agent/Cargo.toml | 7 ++++++ .../src/main.rs => agent/src/cli.rs} | 20 +++++---------- crates/agent/src/lib.rs | 1 + crates/agent/src/main.rs | 12 +++++++++ .../tests/cli_integration.rs} | 0 7 files changed, 29 insertions(+), 52 deletions(-) delete mode 100644 crates/agent-cli/Cargo.toml rename crates/{agent-cli/src/main.rs => agent/src/cli.rs} (97%) create mode 100644 crates/agent/src/main.rs rename crates/{agent-cli/tests/integration.rs => agent/tests/cli_integration.rs} (100%) diff --git a/Cargo.lock b/Cargo.lock index 86b6d59be..1656096a2 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -6,8 +6,11 @@ version = 4 name = "agent" version = "0.1.0" dependencies = [ + "anyhow", "async-trait", "chrono", + "clap", + "dotenvy", "futures", "glob", "jsonschema", @@ -20,19 +23,6 @@ dependencies = [ "uuid", ] -[[package]] -name = "agent-cli" -version = "0.1.0" -dependencies = [ - "agent", - "anyhow", - "async-trait", - "clap", - "llm", - "serde_json", - "tokio", -] - [[package]] name = "ahash" version = "0.8.12" diff --git a/crates/agent-cli/Cargo.toml b/crates/agent-cli/Cargo.toml deleted file mode 100644 index 7a16b337a..000000000 --- a/crates/agent-cli/Cargo.toml +++ /dev/null @@ -1,25 +0,0 @@ -[package] -name = "agent-cli" -edition.workspace = true -version.workspace = true -license.workspace = true -description = "CLI for the agent agentic loop" -repository = "https://github.com/brynary/attractor-rust" -keywords = ["llm", "ai", "agent", "cli"] -categories = ["command-line-utilities"] - -[[bin]] -name = "agent" -path = "src/main.rs" - -[dependencies] -agent = { path = "../agent" } -llm = { path = "../llm" } -clap.workspace = true -tokio.workspace = true -anyhow.workspace = true -serde_json.workspace = true -async-trait.workspace = true - -[lints] -workspace = true diff --git a/crates/agent/Cargo.toml b/crates/agent/Cargo.toml index e01fee42f..43de297f5 100644 --- a/crates/agent/Cargo.toml +++ b/crates/agent/Cargo.toml @@ -12,7 +12,14 @@ categories = ["api-bindings"] [lib] doctest = false +[[bin]] +name = "agent" +path = "src/main.rs" + [dependencies] +clap.workspace = true +anyhow.workspace = true +dotenvy.workspace = true llm = { path = "../llm" } thiserror.workspace = true serde.workspace = true diff --git a/crates/agent-cli/src/main.rs b/crates/agent/src/cli.rs similarity index 97% rename from crates/agent-cli/src/main.rs rename to crates/agent/src/cli.rs index 935fbff90..36021d475 100644 --- a/crates/agent-cli/src/main.rs +++ b/crates/agent/src/cli.rs @@ -1,4 +1,4 @@ -use agent::{ +use crate::{ AnthropicProfile, EventData, EventKind, GeminiProfile, LocalExecutionEnvironment, OpenAiProfile, ProviderProfile, Session, SessionConfig, ToolApprovalFn, Turn, }; @@ -6,7 +6,6 @@ use clap::{Parser, ValueEnum}; use llm::client::Client; use std::io::{IsTerminal, Write}; use std::path::PathBuf; -use std::process::ExitCode; use std::sync::atomic::Ordering; use std::sync::{Arc, Mutex}; @@ -36,6 +35,10 @@ struct Cli { /// Print LLM request/response debug info to stderr #[arg(long)] debug: bool, + + /// Print full LLM request/response JSON to stderr + #[arg(long)] + verbose: bool, } #[derive(Clone, Copy, Debug, ValueEnum)] @@ -201,7 +204,7 @@ impl llm::middleware::Middleware for DebugMiddleware { } } -async fn run() -> anyhow::Result<()> { +pub async fn run() -> anyhow::Result<()> { let _ = dotenvy::dotenv(); let cli = Cli::parse(); @@ -279,17 +282,6 @@ async fn run() -> anyhow::Result<()> { Ok(()) } -#[tokio::main] -async fn main() -> ExitCode { - match run().await { - Ok(()) => ExitCode::SUCCESS, - Err(e) => { - eprintln!("[error] {e}"); - ExitCode::FAILURE - } - } -} - #[cfg(test)] mod tests { use super::*; diff --git a/crates/agent/src/lib.rs b/crates/agent/src/lib.rs index 2ba691eae..e6e2c25a1 100644 --- a/crates/agent/src/lib.rs +++ b/crates/agent/src/lib.rs @@ -1,3 +1,4 @@ +pub mod cli; pub mod config; pub mod error; pub mod event; diff --git a/crates/agent/src/main.rs b/crates/agent/src/main.rs new file mode 100644 index 000000000..2369b1e46 --- /dev/null +++ b/crates/agent/src/main.rs @@ -0,0 +1,12 @@ +use std::process::ExitCode; + +#[tokio::main] +async fn main() -> ExitCode { + match agent::cli::run().await { + Ok(()) => ExitCode::SUCCESS, + Err(e) => { + eprintln!("[error] {e}"); + ExitCode::FAILURE + } + } +} diff --git a/crates/agent-cli/tests/integration.rs b/crates/agent/tests/cli_integration.rs similarity index 100% rename from crates/agent-cli/tests/integration.rs rename to crates/agent/tests/cli_integration.rs