Metadata-Version: 2.4
Name: cavecode
Version: 1.0.0
Summary: CaveCode: AST-Aware High-Density Source-Code Compressor for AI Coding Agents
Author: CaveCode
License: GNU Affero General Public License v3
Keywords: ai,context,ast,token-optimizer,prompt-compression,developer-tools
Classifier: Development Status :: 5 - Production/Stable
Classifier: Environment :: Console
Classifier: Intended Audience :: Developers
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Programming Language :: Python :: 3.14
Classifier: Topic :: Software Development :: Code Generators
Classifier: Topic :: Utilities
Requires-Python: >=3.10
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: typer>=0.12.0
Requires-Dist: rich>=13.7.0
Requires-Dist: pydantic>=2.5.0
Requires-Dist: pyyaml>=6.0
Requires-Dist: tiktoken>=0.7.0; extra != "minimal"
Requires-Dist: tree-sitter>=0.23.0
Provides-Extra: dev
Requires-Dist: pytest>=8.0.0; extra == "dev"
Requires-Dist: pytest-cov>=4.0.0; extra == "dev"
Dynamic: license-file

# 🪨 CaveCode ⚡

> ***why input many code when few code do trick***

LLMs and AI coding agents consume massive amounts of context tokens reading boilerplate, repetitive syntax, and verbose formatting. CaveCode compresses source code before passing it to AI agents, stripping unnecessary token overhead while preserving critical information. It reduces input token usage by up to **80%+** with three configurable compression tiers.

- 🌐 **[Web Playground](https://grimm67123.github.io/cavecode/)**: Try compression modes directly in your browser.
- 🤖 **Agent Protocol**: Includes an [AGENT.md](AGENT.md) documentation file for AI coding agents.

> **Compressed output is an information representation for AI context, not executable source code.** Agents continue to read and edit the original source files.

---

## Compression Modes

| Mode | Token Savings | What it keeps |
| :--- | :---: | :--- |
| **`lite`** | **~25% – ~30%** | Full function bodies & code logic |
| **`medium`** | **~35% – ~50%** | Function bodies with compressed syntax |
| **`ultra`** | **~80% – ~85%+** | AST structure, signatures & types |

### Code Comparison

#### Raw Source Code

```python
import os
import json
import logging
from typing import List, Optional
from pydantic import BaseModel

logger = logging.getLogger(__name__)

class UserProfile(BaseModel):
    user_id: str
    email: str
    roles: List[str] = []

class AuthService:
    """Service responsible for authenticating and authorizing user tokens."""

    def __init__(self, secret_key: str, expiration_secs: int = 3600):
        self.secret_key = secret_key
        self.expiration_secs = expiration_secs
        logger.info(f"AuthService initialized with TTL: {expiration_secs}s")

    def validate_token(self, token: str) -> Optional[UserProfile]:
        """Validate bearer token and return user profile if authentic."""
        logger.debug(f"Validating token: {token[:8]}...")
        if not token or len(token) < 16:
            logger.warning("Token rejected: invalid length")
            return None
        return UserProfile(user_id="u123", email="user@example.com")
```

**lite — ~30% saved**

Removes docstrings, legal headers, normalizes whitespace. ~100% of function bodies and code logic preserved.

```python
import os
import json
import logging
from typing import List, Optional
from pydantic import BaseModel

logger = logging.getLogger(__name__)

class UserProfile(BaseModel):
  user_id: str
  email: str
  roles: List[str] = []

class AuthService:
  def __init__(self, secret_key: str, expiration_secs: int = 3600):
    self.secret_key = secret_key
    self.expiration_secs = expiration_secs
    logger.info(f"AuthService initialized with TTL: {expiration_secs}s")

  def validate_token(self, token: str) -> Optional[UserProfile]:
    logger.debug(f"Validating token: {token[:8]}...")
    if not token or len(token) < 16:
      logger.warning("Token rejected: invalid length")
      return None
    return UserProfile(user_id="u123", email="user@example.com")
```

**medium — ~44% saved**

Compresses keywords (def → fn, return → ret), strips noisy logging/debug calls, condenses comments.

```text
from typing import List, Optional
from pydantic import BaseModel

class UserProfile(BaseModel):
  user_id: str
  email: str
  roles: List[str] = []

class AuthService:
  fn __init__(self, secret_key: str, expiration_secs: int = 3600):
    self.secret_key = secret_key
    self.expiration_secs = expiration_secs

  fn validate_token(self, token: str) -> Optional[UserProfile]:
    if not token or len(token) < 16:
      ret None
    ret UserProfile(user_id="u123", email="user@example.com")
```

**ultra — ~83% saved**

AST skeletonization. Retains all class structures, type hints, and function signatures while collapsing bodies to `pass`.

```text
from typing import List, Optional
from pydantic import BaseModel

class UserProfile(BaseModel):
  user_id: str
  email: str
  roles: List[str] = []

class AuthService:
  fn __init__(self, secret_key: str, expiration_secs: int = 3600):
    pass
  fn validate_token(self, token: str) -> Optional[UserProfile]:
    pass
```

---

## Installation

Install via pip:

```bash
pip install cavecode
```

Or install directly from Git:

```bash
pip install git+https://github.com/cavecode/cavecode.git
```

Or clone and install in editable development mode:

```bash
git clone https://github.com/cavecode/cavecode.git
cd cavecode
pip install -e .
```

Verify installation:

```bash
cavecode version
```

---

## Supported Languages

CaveCode supports 9 programming languages with dedicated AST parsers and syntax transformers:

- Python (`.py`)
- JavaScript (`.js`, `.jsx`, `.mjs`, `.cjs`)
- TypeScript (`.ts`, `.tsx`)
- Rust (`.rs`)
- Go (`.go`)
- Java (`.java`)
- C++ (`.cpp`, `.cc`, `.cxx`, `.hpp`)
- C# (`.cs`)
- C (`.c`, `.h`)

---

## Command Reference

### `cavecode read`

Reads file(s) or directories on the fly with AST compression and outputs directly to stdout. Leaves source files ~100% untouched.

```bash
# Read a single file in ultra mode (default: signatures & types)
cavecode read src/service.py

# Read in lite mode to keep function implementations
cavecode read src/service.py -m lite

# Read with line numbers and a specific line slice
cavecode read src/service.py -n -l 10:45

# Read an entire directory
cavecode read src/ -m ultra
```

### `cavecode view` / `cavecode cat`

Convenience aliases for `cavecode read`:

```bash
cavecode cat app/main.ts -m medium
cavecode view backend/service.go
```

### `cavecode compress`

Compresses code files into companion `.cave.<ext>` files on disk. Original source files remain untouched.

```bash
# Compress a single file to <file>.cave.<ext>
cavecode compress src/main.py

# Compress all supported files across a directory
cavecode compress src/ -m ultra

# Custom output destination for a single file
cavecode compress src/main.py -o /tmp/main.compressed.py
```

### `cavecode revert`

Removes generated `.cave` files across a file or directory tree:

```bash
cavecode revert .
```

### `cavecode estimate`

Calculates and displays approximate token counts and savings without modifying or creating files:

```bash
# Analyze a single file
cavecode estimate src/main.py -m ultra

# Analyze an entire codebase
cavecode estimate src/
```

### `cavecode stats`

Convenience alias for `cavecode estimate`:

```bash
cavecode stats src/ -m lite
```

### `cavecode verify`

Verifies that target source files have not been modified:

```bash
cavecode verify src/
```

### `cavecode init`

Creates a default `.cavecode.yaml` configuration file to configure custom inclusion patterns, exclusion lists, and compression modes:

```bash
cavecode init .
```

### `cavecode version`

Displays the current CaveCode version:

```bash
cavecode version
```

---

## Agent Documentation (AGENT.md)

Repositories using CaveCode include an `AGENT.md` file at their root. This file serves as documentation for AI coding agents (such as Claude Code, Cursor, Copilot, Codex, Gemini, etc.), informing the agent of how to use CaveCode safely and effectively.

### Reading External Dependencies Without Context Bloat

When an AI agent explores a repository or needs to understand how to call functions across sibling files, reading verbose raw source code quickly saturates its context window. `AGENT.md` guides the agent to use `cavecode read -m ultra` to extract clean interfaces, types, and API signatures from dependencies:

```bash
cavecode read path/to/dependency.py -m ultra    # Skeletons & signatures (~80% – ~85%+ token savings)
cavecode read src/ -m ultra                    # High-speed architecture & interface mapping
```

By reading compressed signatures from stdout, the agent consumes significantly fewer input tokens and keeps its context clean for the task at hand.

### When to Use Raw File Reads

Using `cavecode` is strictly intended for understanding interfaces and dependencies. When an agent is **actively writing, patching, or debugging code in a target file**, it continues to read the original raw source files using its native tools to ensure byte-exact diffs and accurate line numbers.

### Compression Modes for Agents

- **ultra (~80% – ~85%+ savings):** **Primary mode for agents.** Collapses function bodies to structural signatures (`pass` / `{ ... }`). Ideal for high-level repository mapping and referencing API interfaces of dependency files.
- **lite (~25% – ~30% savings):** Preserves full function bodies and algorithms with normalized whitespace and removed docstrings. Useful for skimming logic in an external file.
- **medium (~35% – ~50% savings):** Preserves function bodies with compact keyword replacements (`fn`, `ret`, `pub`, `priv`) and stripped debug logs.

### Preserving Raw Files

Agents write all edits directly to the original raw source files. The generated `.cave` files (if created on disk with `cavecode compress`) are strictly read-only references and should never be edited or committed.
