# How to Build Custom Compression Rules for Specific Output Formats in OmniRoute

> Learn to build custom compression rules in OmniRoute. Create JSON rule packs, validate with ruleLoader.ts, and load at runtime for specific output format transformations.

- Repository: [Diego Rodrigues de Sa e Souza/OmniRoute](https://github.com/diegosouzapw/OmniRoute)
- Tags: how-to-guide
- Published: 2026-07-27

---

**To build custom compression rules in OmniRoute, create a JSON rule pack in `open-sse/services/compression/rules/<language>/<category>.json`, validate it through the `validateRulePack` function in [`ruleLoader.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/ruleLoader.ts), and load it at runtime via `loadRulePack` to apply regex-based transformations targeted at specific output formats.**

OmniRoute uses a **Caveman rule system** to power its prompt-compression engine, allowing developers to define regex-based transformations through simple JSON configuration files. When you build custom compression rules for specific output formats in OmniRoute, you create modular rule packs that the compression pipeline loads and applies based on language and category selectors. This architecture enables precise control over how prompts are compressed before being sent upstream, ensuring optimal token usage for different output formats.

## Understanding the Caveman Rule System

The Caveman rule system processes **rule packs**—JSON files containing arrays of `FileRule` objects that define regular-expression-based transformations. Each rule specifies a pattern, replacement strategy, and contextual metadata that determines when and how the transformation applies. According to the OmniRoute source code in [`open-sse/services/compression/ruleLoader.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/open-sse/services/compression/ruleLoader.ts), these rules are compiled into `CavemanRule` objects and cached in memory to avoid recompilation on subsequent requests.

## Creating a Custom Rule Pack

To add custom compression logic, you define rules in a structured JSON file following the `FileRule` interface defined in [`open-sse/services/compression/types.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/open-sse/services/compression/types.ts).

### Rule Schema and Required Fields

Each rule requires specific fields to ensure the compression pipeline can parse and execute the transformation correctly:

- **name**: Unique identifier for the rule
- **pattern**: Regular expression string to match content
- **replacement** or **replacementMap**: Static string or mapping object for substitutions
- **flags**: Regex flags (e.g., `"gm"` for global multiline)
- **context**: Execution scope (e.g., `"all"`, `"assistant"`)
- **category**: Classification such as `filler`, `dedup`, or `ultra`
- **minIntensity**: Minimum compression level (e.g., `lite`)
- **description**: Human-readable explanation of the rule's function

### File Location Conventions

Store rule packs in the directory structure `open-sse/services/compression/rules/<language>/<category>.json`, where `<language>` represents the language code (e.g., `en`, `ja`) and `<category>` matches the compression intensity or type.

```json
[
  {
    "name": "strip-debug-logs",
    "pattern": "^debug:\\s.*$",
    "replacement": "",
    "flags": "gm",
    "context": "assistant",
    "category": "filler",
    "minIntensity": "lite",
    "description": "Remove any debug statements generated by the assistant."
  }
]

```

## Validating and Loading Rules

The [`ruleLoader.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/ruleLoader.ts) module handles rule ingestion through two primary functions: `validateRulePack` for schema validation and `loadRulePack` for runtime compilation.

When you invoke `loadRulePack(language, category)`, the loader checks a `Map<string, CavemanRule[]>` cache keyed by `${rulesDir}:${language}:${category}` to return existing compiled rules or process new ones. The `validateRulePack` function enforces constraints against allowed enums including `VALID_CONTEXTS`, `VALID_CATEGORIES`, and `VALID_INTENSITIES`, ensuring only compliant rules enter the pipeline.

```typescript
import { loadRulePack } from "@omniroute/open-sse/services/compression/ruleLoader";

// Load English filler rules for custom processing
const customRules = loadRulePack("en", "filler");

```

## Integrating with Output Formats

To target specific output formats, configure **compression combos** in [`strategySelector.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/strategySelector.ts) that reference your custom rule packs. The strategy selector resolves which packs to apply based on the request's compression mode, combo overrides, and the presence of a `refresh` flag.

When constructing a combo, you can merge custom rules with existing category packs:

```typescript
const combo = {
  name: "my-ultra-combo",
  compression: {
    language: "en",
    category: "ultra",
    extraRules: customRules // Merges with the ultra pack
  }
};

```

## Exposing Rule Metadata via API

The API endpoint in [`src/app/api/compression/rules/route.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/src/app/api/compression/rules/route.ts) exposes rule metadata through the `getCavemanRuleMetadata()` function, enabling UI tools to discover available custom rules programmatically.

Query the endpoint to retrieve rule descriptors including `name`, `category`, and `description`:

```bash
curl -X GET https://my-omniroute.example.com/api/compression/rules \
     -H "Authorization: Bearer <management-api-key>"

```

## Summary

- **Create JSON rule packs** in `open-sse/services/compression/rules/<language>/<category>.json` following the `FileRule` schema with pattern, replacement, and metadata fields.
- **Validate rules** using the `validateRulePack` function in [`ruleLoader.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/ruleLoader.ts), which checks against `VALID_CONTEXTS`, `VALID_CATEGORIES`, and `VALID_INTENSITIES` enums.
- **Load compiled rules** at runtime via `loadRulePack(language, category)`, which caches `CavemanRule` objects in a Map keyed by directory, language, and category.
- **Target output formats** by configuring compression combos in [`strategySelector.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/strategySelector.ts) that specify language, category, and optional `extraRules` arrays.
- **Expose metadata** through the `getCavemanRuleMetadata` API endpoint defined in [`src/app/api/compression/rules/route.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/src/app/api/compression/rules/route.ts) for management interfaces.

## Frequently Asked Questions

### What is the Caveman rule system in OmniRoute?

The Caveman rule system is OmniRoute's prompt-compression engine that processes JSON-based rule packs containing regular-expression transformations. It compiles these configurations into executable `CavemanRule` objects and applies them to prompts before upstream transmission, reducing token usage through pattern-based replacement.

### Where should I store custom compression rule files?

Store custom rule files in the directory `open-sse/services/compression/rules/<language>/<category>.json`, replacing `<language>` with the appropriate language code (such as `en` or `ja`) and `<category>` with the compression type (such as `filler` or `ultra`). The [`ruleLoader.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/ruleLoader.ts) module automatically discovers and loads rules from this structured path.

### How does OmniRoute validate custom compression rules?

OmniRoute validates rules through the `validateRulePack` function in [`ruleLoader.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/ruleLoader.ts), which verifies required fields, regex validity, and enum compliance against `VALID_CONTEXTS`, `VALID_CATEGORIES`, and `VALID_INTENSITIES`. This validation occurs at load time, preventing malformed rules from entering the compression pipeline.

### Can I apply different rules based on the output format?

Yes. The [`strategySelector.ts`](https://github.com/diegosouzapw/OmniRoute/blob/main/strategySelector.ts) module enables format-specific rule application by resolving compression combos that map to particular output formats. You can configure combos to load specific language and category packs, or supply `extraRules` arrays to override default behavior for targeted output formats.