rlm-cli 1.2.4

Recursive Language Model (RLM) REPL for Claude Code - handles long-context tasks via chunking and recursive sub-LLM calls
Documentation
# GitHub Copilot Instructions

This document provides context for GitHub Copilot when working with this Rust project.

## Project Context

This is a Rust crate using modern tooling:
- **Rust**: 1.80+ (2024 edition)
- **Build System**: Cargo
- **Linting**: clippy with pedantic and nursery lints
- **Formatting**: rustfmt
- **Testing**: Built-in test framework + proptest
- **Supply Chain Security**: cargo-deny

## Code Generation Guidelines

### Error Handling

Use `Result` types instead of panicking:

```rust
// Good - Returns Result
pub fn parse_value(input: &str) -> Result<i64, ParseError> {
    input.parse().map_err(|e| ParseError::InvalidFormat(e))
}

// Avoid - Panics on failure
pub fn parse_value(input: &str) -> i64 {
    input.parse().unwrap() // Never do this
}
```

Use `thiserror` for custom error types:

```rust
use thiserror::Error;

#[derive(Error, Debug)]
pub enum AppError {
    #[error("invalid input: {0}")]
    InvalidInput(String),

    #[error("operation failed: {operation}")]
    OperationFailed { operation: String },

    #[error(transparent)]
    Io(#[from] std::io::Error),
}
```

### Type Annotations

Provide explicit return types for public functions:

```rust
// Good - explicit return type
pub fn process_data(items: &[String]) -> Vec<ProcessedItem> {
    // implementation
}

// Avoid for public APIs
pub fn process_data(items: &[String]) -> impl Iterator<Item = ProcessedItem> {
    // implementation
}
```

### Documentation

Use doc comments with examples:

```rust
/// Processes a list of items according to the given configuration.
///
/// # Arguments
///
/// * `items` - The items to process.
/// * `config` - Configuration options for processing.
///
/// # Returns
///
/// A vector of processed items.
///
/// # Errors
///
/// Returns [`Error::InvalidInput`] if any item is invalid.
///
/// # Examples
///
/// ```rust
/// use {{crate_name}}::{process, Config};
///
/// let items = vec!["a", "b", "c"];
/// let config = Config::default();
/// let result = process(&items, &config)?;
/// # Ok::<(), {{crate_name}}::Error>(())
/// ```
pub fn process(items: &[&str], config: &Config) -> Result<Vec<Item>> {
    // implementation
}
```

### Ownership and Borrowing

Prefer borrowing over ownership when possible:

```rust
// Good - borrows the slice
pub fn sum_values(values: &[i64]) -> i64 {
    values.iter().sum()
}

// Avoid - takes ownership unnecessarily
pub fn sum_values(values: Vec<i64>) -> i64 {
    values.iter().sum()
}
```

Use `Cow` for efficient string handling:

```rust
use std::borrow::Cow;

pub fn normalize_name(name: &str) -> Cow<'_, str> {
    if name.contains(' ') {
        Cow::Owned(name.replace(' ', "_"))
    } else {
        Cow::Borrowed(name)
    }
}
```

### Structs and Enums

Use builder pattern for complex structs:

```rust
#[derive(Debug, Clone, Default)]
pub struct Config {
    pub timeout: Duration,
    pub retries: u32,
    pub verbose: bool,
}

impl Config {
    #[must_use]
    pub fn new() -> Self {
        Self::default()
    }

    #[must_use]
    pub fn with_timeout(mut self, timeout: Duration) -> Self {
        self.timeout = timeout;
        self
    }

    #[must_use]
    pub fn with_retries(mut self, retries: u32) -> Self {
        self.retries = retries;
        self
    }
}
```

### Testing

Write comprehensive unit tests:

```rust
#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn test_add_positive_numbers() {
        assert_eq!(add(2, 3), 5);
    }

    #[test]
    fn test_divide_by_zero_returns_error() {
        let result = divide(10, 0);
        assert!(matches!(result, Err(Error::DivisionByZero)));
    }
}
```

Use proptest for property-based testing:

```rust
use proptest::prelude::*;

proptest! {
    #[test]
    fn add_is_commutative(a in any::<i64>(), b in any::<i64>()) {
        prop_assert_eq!(add(a, b), add(b, a));
    }
}
```

### Async Code

Use async/await with tokio:

```rust
pub async fn fetch_data(url: &str) -> Result<Data> {
    let response = reqwest::get(url).await?;
    let data = response.json().await?;
    Ok(data)
}
```

## Common Patterns

### Iterator Chains

```rust
let result: Vec<_> = items
    .iter()
    .filter(|item| item.is_valid())
    .map(|item| item.transform())
    .collect();
```

### Option and Result Combinators

```rust
// Option chaining
let value = config
    .get_setting("key")
    .and_then(|s| s.parse().ok())
    .unwrap_or_default();

// Result chaining with ?
fn process() -> Result<Output> {
    let data = load_data()?;
    let parsed = parse_data(&data)?;
    let result = transform(parsed)?;
    Ok(result)
}
```

### Const Functions

Prefer `const fn` for compile-time evaluation:

```rust
#[must_use]
pub const fn new() -> Self {
    Self { value: 0 }
}
```

## File Locations

- Source code: `src/`
- Library entry: `src/lib.rs`
- Binary entry: `src/main.rs`
- Integration tests: `tests/`
- Benchmarks: `benches/` (with criterion)

## Commands

```bash
cargo build           # Build
cargo test            # Run tests
cargo clippy          # Lint
cargo fmt             # Format
cargo doc --open      # Generate and view docs
cargo deny check      # Check supply chain
```