-
Notifications
You must be signed in to change notification settings - Fork 0
Feature/rust cli implementation #2
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
e35b579
9582b43
6341a53
859f71b
5694367
05b6fc5
18d4700
9f540bc
0f06d80
53bce83
c388a13
2c523a4
e2c1906
0e0e3e6
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,32 @@ | ||
| # Cargo aliases (simpler alternative to cargo-make) | ||
| # Usage: cargo <alias-name> | ||
| # Examples: cargo b (build), cargo r (run), cargo t (test), cargo cl (clippy) | ||
|
|
||
| [alias] | ||
| # Build aliases | ||
| b = "build" | ||
| br = "build --release" | ||
| c = "check" | ||
|
|
||
| # Run aliases | ||
| r = "run" | ||
| rr = "run --release" | ||
|
|
||
| # Test aliases | ||
| t = "test" | ||
| tt = "test -- --nocapture" | ||
|
|
||
| # Linting/formatting | ||
| cl = "clippy -- -D warnings" | ||
| f = "fmt" | ||
| fc = "fmt -- --check" | ||
|
|
||
| # Clean | ||
| clean-all = "clean" | ||
|
|
||
| # Combined tasks (use scripts/pre-commit.sh for combined workflow) | ||
| # Note: Cargo aliases don't support shell operators like && | ||
| # Run these commands separately: | ||
| # cargo fmt | ||
| # cargo clippy -- -D warnings | ||
| # cargo test |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,39 @@ | ||
| # Logs | ||
| logs | ||
| *.log | ||
| npm-debug.log* | ||
| yarn-debug.log* | ||
| yarn-error.log* | ||
| dev-debug.log | ||
|
|
||
| # Dependency directories | ||
| node_modules/ | ||
|
|
||
| # Environment variables | ||
| .env | ||
|
|
||
| # Editor directories and files | ||
| .idea | ||
| .vscode | ||
| *.suo | ||
| *.ntvs* | ||
| *.njsproj | ||
| *.sln | ||
| *.sw? | ||
|
|
||
| # OS specific | ||
| .DS_Store | ||
|
|
||
|
|
||
| # Added by cargo | ||
|
|
||
| /target | ||
|
|
||
| # Local config files | ||
| .clai.toml | ||
|
|
||
| # TaskMaster (local to developer, not tracked in Git) | ||
| .taskmaster/ | ||
|
|
||
| # Cursor IDE (local to developer, not tracked in Git) | ||
| .cursor/ |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,72 @@ | ||
| # CLAUDE.md | ||
|
|
||
| This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository. | ||
|
|
||
| ## Project Overview | ||
|
|
||
| clai is a CLI tool that converts natural language into shell commands using AI. It follows Unix philosophy: simple, composable, and privacy-respecting. Users provide instructions like `clai "find all rust files modified today"` and get executable shell commands back. | ||
|
|
||
| ## Build and Development Commands | ||
|
|
||
| ```bash | ||
| cargo build # Debug build | ||
| cargo build --release # Release build | ||
| cargo test # Run all tests | ||
| cargo test <test_name> # Run a single test | ||
| cargo clippy -- -D warnings # Lint (warnings are errors) | ||
| cargo fmt # Format code | ||
| cargo bench --features bench # Run benchmarks | ||
| cargo run -- "instruction" # Run with an instruction | ||
| ``` | ||
|
|
||
| Pre-commit checks (run before committing): | ||
| ```bash | ||
| ./scripts/pre-commit.sh # Runs fmt, clippy, and tests | ||
| ``` | ||
|
|
||
| ## Architecture | ||
|
|
||
| ### Core Flow | ||
|
|
||
| `main.rs` orchestrates the pipeline: | ||
| 1. Parse CLI args → `cli/mod.rs` (clap-based) | ||
| 2. Load config → `config/` (layered: .clai.toml > ~/.config/clai/config.toml > /etc/clai/config.toml) | ||
| 3. Gather context → `context/` (system info, cwd, files, shell history, stdin) | ||
| 4. Build prompt → `ai/prompt.rs` | ||
| 5. Call AI provider → `ai/providers/` (OpenRouter via provider chain) | ||
| 6. Safety check → `safety/` (dangerous command detection with regex patterns) | ||
| 7. Output or execute → `output/`, `safety/interactive.rs` | ||
|
|
||
| ### Key Modules | ||
|
|
||
| - **ai/**: AI provider abstraction with async traits. `handler.rs` orchestrates generation, `chain.rs` manages provider fallback, `providers/openrouter.rs` is the primary implementation. | ||
| - **config/**: Layered config system. `paths.rs` discovers config files, `loader.rs` loads/validates TOML, `merger.rs` combines configs, `cache.rs` provides lazy caching. | ||
| - **context/**: Gathers system context for prompts. `gatherer.rs` orchestrates, individual modules handle system info, directory scanning, shell history, and stdin. | ||
| - **safety/**: Dangerous command detection. `patterns.rs` defines regex patterns, `detector.rs` matches commands, `confirmation.rs` and `interactive.rs` handle user prompts. | ||
| - **error/**: Typed errors with exit codes (1=general, 2=usage, 3=config, 4=API, 5=safety, 130=interrupted). | ||
|
|
||
| ### Design Patterns | ||
|
|
||
| - **Pure functions preferred**: Most functions are pure transformations. I/O is isolated to main.rs and handler functions. | ||
| - **Immutable Config**: Config struct is immutable after creation from CLI args. | ||
| - **Strict stdout/stderr**: stdout = commands only (for piping), stderr = logs/warnings. | ||
| - **Async with tokio**: AI calls use async/await with reqwest. | ||
|
|
||
| ## Configuration | ||
|
|
||
| Environment variables: | ||
| - `OPENROUTER_API_KEY` - Required for AI provider | ||
| - `NO_COLOR` - Disable colored output | ||
|
|
||
| Config file locations (highest to lowest priority): | ||
| 1. `./.clai.toml` (project-local) | ||
| 2. `~/.config/clai/config.toml` (user) | ||
| 3. `/etc/clai/config.toml` (system) | ||
|
|
||
| ## Testing | ||
|
|
||
| Tests are co-located in the same files as implementation (`#[cfg(test)]` modules). Run specific test file with: | ||
| ```bash | ||
| cargo test --lib config::tests | ||
| cargo test --lib safety::tests | ||
| ``` |
| Original file line number | Diff line number | Diff line change | ||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,138 @@ | ||||||||||||||||||
| # Contributing to clai | ||||||||||||||||||
|
|
||||||||||||||||||
| ## Development Setup | ||||||||||||||||||
|
|
||||||||||||||||||
| ### Prerequisites | ||||||||||||||||||
|
|
||||||||||||||||||
| - Rust 1.70+ | ||||||||||||||||||
| - OpenRouter API key (for testing AI features) | ||||||||||||||||||
|
|
||||||||||||||||||
| ```bash | ||||||||||||||||||
| git clone https://github.com/Vedaant-Rajoo/clAI.git | ||||||||||||||||||
| cd clAI | ||||||||||||||||||
| cargo build | ||||||||||||||||||
|
|
||||||||||||||||||
| # Install Git hooks (recommended) | ||||||||||||||||||
| ./scripts/install-hooks.sh | ||||||||||||||||||
| ``` | ||||||||||||||||||
|
|
||||||||||||||||||
| ### Running | ||||||||||||||||||
|
|
||||||||||||||||||
| ```bash | ||||||||||||||||||
| cargo run -- "your instruction" | ||||||||||||||||||
| ``` | ||||||||||||||||||
|
|
||||||||||||||||||
| ## Project Structure | ||||||||||||||||||
|
|
||||||||||||||||||
| ``` | ||||||||||||||||||
| src/ | ||||||||||||||||||
| ├── main.rs # Entry point | ||||||||||||||||||
| ├── lib.rs # Library exports | ||||||||||||||||||
| ├── cli/ # Argument parsing | ||||||||||||||||||
| ├── config/ # Configuration loading | ||||||||||||||||||
| ├── context/ # System/directory context gathering | ||||||||||||||||||
| ├── ai/ # AI provider abstraction | ||||||||||||||||||
| │ └── providers/ # OpenRouter, etc. | ||||||||||||||||||
| ├── safety/ # Dangerous command detection | ||||||||||||||||||
| └── error/ # Error types and exit codes | ||||||||||||||||||
| ``` | ||||||||||||||||||
|
|
||||||||||||||||||
| ## Commands | ||||||||||||||||||
|
|
||||||||||||||||||
| ```bash | ||||||||||||||||||
| cargo build # Debug build | ||||||||||||||||||
| cargo build --release # Release build | ||||||||||||||||||
| cargo test # Run tests | ||||||||||||||||||
| cargo clippy # Lint | ||||||||||||||||||
| cargo fmt # Format | ||||||||||||||||||
| cargo bench --features bench # Run benchmarks | ||||||||||||||||||
| ``` | ||||||||||||||||||
|
|
||||||||||||||||||
| ## Configuration | ||||||||||||||||||
|
|
||||||||||||||||||
| ### Environment Variables | ||||||||||||||||||
|
|
||||||||||||||||||
| | Variable | Description | | ||||||||||||||||||
| | -------------------- | ---------------------- | | ||||||||||||||||||
| | `OPENROUTER_API_KEY` | API key for OpenRouter | | ||||||||||||||||||
| | `NO_COLOR` | Disable colored output | | ||||||||||||||||||
|
|
||||||||||||||||||
| ### Config File Locations | ||||||||||||||||||
|
|
||||||||||||||||||
| 1. `./.clai.toml` (project-local, highest priority) | ||||||||||||||||||
| 2. `~/.config/clai/config.toml` (user) | ||||||||||||||||||
| 3. `/etc/clai/config.toml` (system) | ||||||||||||||||||
|
|
||||||||||||||||||
|
Comment on lines
+62
to
+65
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Document XDG_CONFIG_HOME support in config file precedence. The implementation in 🔎 Proposed fixUpdate the list to include all four locations: 1. `./.clai.toml` (project-local, highest priority)
-2. `~/.config/clai/config.toml` (user)
-3. `/etc/clai/config.toml` (system)
+2. `$XDG_CONFIG_HOME/clai/config.toml` (if XDG_CONFIG_HOME is set)
+3. `~/.config/clai/config.toml` (fallback if XDG_CONFIG_HOME not set)
+4. `/etc/clai/config.toml` (system, lowest priority)📝 Committable suggestion
Suggested change
🤖 Prompt for AI Agents |
||||||||||||||||||
| ### Full Config Example | ||||||||||||||||||
|
|
||||||||||||||||||
| ```toml | ||||||||||||||||||
| [provider] | ||||||||||||||||||
| default = "openrouter" | ||||||||||||||||||
| api-key = "${OPENROUTER_API_KEY}" | ||||||||||||||||||
|
|
||||||||||||||||||
| [provider.openrouter] | ||||||||||||||||||
| model = "qwen/qwen3-coder" | ||||||||||||||||||
|
|
||||||||||||||||||
| [context] | ||||||||||||||||||
| max-history = 3 | ||||||||||||||||||
| max-files = 10 | ||||||||||||||||||
|
|
||||||||||||||||||
| [safety] | ||||||||||||||||||
| confirm-dangerous = true | ||||||||||||||||||
| dangerous-patterns = [ | ||||||||||||||||||
| "rm -rf", | ||||||||||||||||||
| "sudo.*rm", | ||||||||||||||||||
| ".*> /dev/sd[a-z]", | ||||||||||||||||||
| ] | ||||||||||||||||||
|
|
||||||||||||||||||
| [ui] | ||||||||||||||||||
| interactive = true | ||||||||||||||||||
| color = "auto" | ||||||||||||||||||
| ``` | ||||||||||||||||||
|
|
||||||||||||||||||
| ## Exit Codes | ||||||||||||||||||
|
|
||||||||||||||||||
| | Code | Meaning | | ||||||||||||||||||
| | ---- | ----------------------------------------- | | ||||||||||||||||||
| | 0 | Success | | ||||||||||||||||||
| | 1 | General error | | ||||||||||||||||||
| | 2 | Usage error | | ||||||||||||||||||
| | 3 | Configuration error | | ||||||||||||||||||
| | 4 | API error | | ||||||||||||||||||
| | 5 | Safety error (dangerous command rejected) | | ||||||||||||||||||
| | 130 | Interrupted (Ctrl+C) | | ||||||||||||||||||
|
|
||||||||||||||||||
| ## Pull Request Process | ||||||||||||||||||
|
|
||||||||||||||||||
| 1. Fork and create a feature branch | ||||||||||||||||||
| 2. Install Git hooks: `./scripts/install-hooks.sh` (if not already done) | ||||||||||||||||||
| 3. Make changes | ||||||||||||||||||
| 4. The pre-commit hook will automatically run checks before each commit: | ||||||||||||||||||
| - Format code with `cargo fmt` | ||||||||||||||||||
| - Run `cargo clippy -- -D warnings` | ||||||||||||||||||
| - Run `cargo test` | ||||||||||||||||||
| 5. If you need to bypass the hook temporarily: `git commit --no-verify` | ||||||||||||||||||
| 6. Submit PR | ||||||||||||||||||
|
|
||||||||||||||||||
| ### Manual Checks | ||||||||||||||||||
|
|
||||||||||||||||||
| If you haven't installed the Git hooks, run these commands before committing: | ||||||||||||||||||
|
|
||||||||||||||||||
| ```bash | ||||||||||||||||||
| ./scripts/pre-commit.sh # Run all checks | ||||||||||||||||||
| ``` | ||||||||||||||||||
|
|
||||||||||||||||||
| Or individually: | ||||||||||||||||||
|
|
||||||||||||||||||
| ```bash | ||||||||||||||||||
| cargo fmt # Format code | ||||||||||||||||||
| cargo clippy -- -D warnings # Check lints | ||||||||||||||||||
| cargo test # Run tests | ||||||||||||||||||
| ``` | ||||||||||||||||||
|
|
||||||||||||||||||
| ## Code Style | ||||||||||||||||||
|
|
||||||||||||||||||
| - Follow `cargo fmt` formatting | ||||||||||||||||||
| - Use `cargo clippy` for lints | ||||||||||||||||||
| - Write tests for new features | ||||||||||||||||||
| - Document public APIs | ||||||||||||||||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Add language identifier to fenced code block.
The code block at line 27 lacks a language identifier, causing markdown linting failures.
🔎 Proposed fix
📝 Committable suggestion
🧰 Tools
🪛 markdownlint-cli2 (0.18.1)
27-27: Fenced code blocks should have a language specified
(MD040, fenced-code-language)
🤖 Prompt for AI Agents