agentctl-auth 0.1.0

Unified auth pool and LLM API client for Claude Max Plan, OpenAI, and more
Documentation
# agentctl-auth

Unified auth pool and Claude API client for managing multiple AI provider credentials with automatic token rotation.

## Features

- **Auth Pool**: Manage credentials for multiple providers in a single TOML file
- **Token Rotation**: Automatic rotation on 429 rate limits (supports multiple tokens per provider)
- **Claude Client**: Messages API with OAuth stealth headers for Claude Max Plan integration
- **Credential Testing**: Validate API keys against provider endpoints
- **Import**: Import from auth-profiles.json format (OpenClaw/RustClaw compatible)
- **Usage Tracking**: Record success/failure, cooldowns, and last-used timestamps

## Quick Start

```rust
use agentctl_auth::{AuthPool, claude};

#[tokio::main]
async fn main() -> anyhow::Result<()> {
    // Load auth pool
    let pool = AuthPool::load(&std::path::PathBuf::from("~/.agentctl/auth.toml"))?;

    // Build Claude client with automatic token rotation
    let client = claude::Client::builder()
        .pool(&pool)
        .build()?;

    // Make a request
    let response = client.message(
        "claude-sonnet-4-20250514",
        &[claude::Message::user("Hello!")],
        4096,
    ).await?;

    println!("Response: {}", response.content[0].text);
    println!("Tokens: {} in + {} out", response.usage.input_tokens, response.usage.output_tokens);
    
    Ok(())
}
```

## Auth Pool Format

```toml
[pool]
"anthropic:default" = { provider = "anthropic", type = "token", token = "sk-ant-..." }
"anthropic:backup" = { provider = "anthropic", type = "oauth", token = "sk-ant-..." }

[defaults]
anthropic = "anthropic:default"

[order.anthropic]
0 = "anthropic:default"
1 = "anthropic:backup"
```

## Claude Client Features

- **Stealth Headers**: Mimics Claude Code CLI for Max Plan access
- **Auto-rotation**: On 429, switches to next credential in order
- **Cooldown Management**: Skips credentials in cooldown period
- **Usage Tracking**: Records success/failure for each credential

## Testing Credentials

```rust
use agentctl_auth::{test_credential, test_all};

let pool = AuthPool::load(&path)?;

// Test single credential
let result = test_credential("anthropic:default", pool.get("anthropic:default").unwrap()).await;
println!("Valid: {}, Latency: {}ms", result.success, result.latency_ms);

// Test all credentials
let results = test_all(&pool).await;
```

## Import from auth-profiles.json

```rust
let mut pool = AuthPool::default();
pool.import_from_auth_profiles_file(&path)?;
pool.save(&std::path::PathBuf::from("~/.agentctl/auth.toml"))?;
```

## License

Dual-licensed under MIT or Apache-2.0.