//! Async Rust client for the [clawdforge] HTTP service. //! //! clawdforge is a small LAN-only service that wraps `claude -p` subprocess //! calls behind a bearer-token-gated REST API. This crate is a thin, //! ergonomic Rust SDK for it. //! //! # Quickstart //! //! ```no_run //! use clawdforge::{Client, RunRequest}; //! //! # async fn run() -> Result<(), Box> { //! let client = Client::builder() //! .base_url("http://localhost:8800") //! .token("cf_xxxxxxxxxxxxxxxx") //! .build()?; //! //! let h = client.healthz().await?; //! println!("claude present: {}", h.claude_present); //! //! let r = client.run(RunRequest { //! prompt: "Reply with JSON: {\"hello\":\"world\"}".into(), //! model: Some("sonnet".into()), //! ..Default::default() //! }).await?; //! //! #[derive(serde::Deserialize)] //! struct Hello { hello: String } //! let typed: Hello = r.as_json()?; //! println!("{}", typed.hello); //! # Ok(()) } //! ``` //! //! [clawdforge]: https://git.sulkta.com/Sulkta-OSS/clawdforge //! //! # Field naming //! //! The clawdforge wire format is snake_case end-to-end (Python / Pydantic //! conventions), so structs in [`crate::types`] do **not** carry //! `#[serde(rename_all = "camelCase")]`. If a future endpoint exposes //! camelCase, prefer per-field `#[serde(rename = "...")]` over a blanket //! container attribute. #![deny(rust_2018_idioms)] #![deny(missing_docs)] mod client; mod error; pub mod session; pub mod types; pub use client::{Client, ClientBuilder}; pub use error::Error; pub use session::{Session, SessionList, SessionOptions, SessionState, TurnEvent, TurnResult}; pub use types::{ AppToken, AppTokenInfo, Effort, FileToken, Healthz, RunFailure, RunRequest, RunResult, SystemMode, TokenCreateRequest, TokenList, };