mrapids 0.1.31

Your OpenAPI, but executable
Documentation
# Validation Binary Packaging Strategy

## What Gets Bundled vs What Doesn't

### 📦 Included in MicroRapid Binary

```
mrapids (single binary ~15-20MB)
├── Core CLI functionality
├── Validation engine
├── Default validation rules (embedded)
│   ├── OAS 2.0 rules
│   ├── OAS 3.0.x rules
│   └── OAS 3.1 rules
└── Security rules (embedded)
```

### 📄 NOT Included (User Provides)

```
User's project/
├── specs/
│   ├── api.yaml          # User's OpenAPI spec
│   ├── petstore.json     # Another spec
│   └── internal-api.yaml # Yet another spec
├── mrapids.yaml          # Project config
└── requests/             # Generated by mrapids
```

## Embedding Validation Rules

### Build-Time Embedding (Recommended)

```rust
// src/validation/rules.rs
// Rules are compiled into the binary

pub mod embedded_rules {
    pub const OAS2_RULES: &str = include_str!("../../rules/oas2.spectral.yaml");
    pub const OAS3_RULES: &str = include_str!("../../rules/oas3.spectral.yaml");
    pub const OAS31_RULES: &str = include_str!("../../rules/oas31.spectral.yaml");
    pub const SECURITY_RULES: &str = include_str!("../../rules/security.spectral.yaml");
}

// At runtime, write to temp file for Spectral
pub fn get_ruleset_for_version(version: &SpecVersion) -> Result<PathBuf> {
    let rules_content = match version {
        SpecVersion::Swagger2_0 => embedded_rules::OAS2_RULES,
        SpecVersion::OpenAPI3_0(_) => embedded_rules::OAS3_RULES,
        SpecVersion::OpenAPI3_1(_) => embedded_rules::OAS31_RULES,
    };
    
    // Write to temp file
    let temp_dir = std::env::temp_dir();
    let rules_file = temp_dir.join(format!("mrapids-rules-{}.yaml", version));
    std::fs::write(&rules_file, rules_content)?;
    
    Ok(rules_file)
}
```

### Binary Size Impact

```
Base mrapids binary:        ~12MB
+ Embedded rules:           ~200KB
+ Validation logic:         ~1MB
+ Compressed:              ~8MB (with UPX)
---------------------------------
Total distributed size:     ~15-20MB
```

## Distribution Strategies

### Option 1: Pure Rust with Embedded Rules ✅ (Recommended)

```toml
# Cargo.toml
[dependencies]
# Use a Rust OpenAPI validator
openapi-struct = "0.5"
jsonschema = "0.17"

[build-dependencies]
include_dir = "0.7"

# Build script embeds rules at compile time
```

**Pros:**
- Single binary, no dependencies
- Works offline
- Fast startup
- Easy distribution

**Cons:**
- Can't use Spectral directly
- Need to implement rule engine

### Option 2: Bundle Spectral Binary

```bash
# Release package structure
mrapids-v1.0.0-darwin-arm64.tar.gz
├── mrapids              # Main CLI
├── bin/
│   └── spectral        # Spectral binary
└── rules/              # Rule files
```

**Distribution script:**
```bash
#!/bin/bash
# build-release.sh

# Build mrapids
cargo build --release

# Download platform-specific Spectral
wget https://github.com/stoplightio/spectral/releases/download/v6.11.0/spectral-darwin-x64

# Package together
tar -czf mrapids-darwin-x64.tar.gz \
    target/release/mrapids \
    spectral-darwin-x64 \
    rules/
```

### Option 3: Lazy Download (Not Recommended)

```rust
// Download Spectral on first use
pub async fn ensure_spectral_installed() -> Result<PathBuf> {
    let spectral_path = dirs::home_dir()
        .unwrap()
        .join(".mrapids")
        .join("bin")
        .join("spectral");
    
    if !spectral_path.exists() {
        println!("📥 Downloading Spectral validator...");
        download_spectral(&spectral_path).await?;
    }
    
    Ok(spectral_path)
}
```

## Platform-Specific Builds

### GitHub Release Structure
```
mrapids/releases/v1.0.0/
├── mrapids-darwin-x64.tar.gz     # macOS Intel
├── mrapids-darwin-arm64.tar.gz   # macOS Apple Silicon
├── mrapids-linux-x64.tar.gz      # Linux x64
├── mrapids-linux-arm64.tar.gz    # Linux ARM
└── mrapids-windows-x64.zip       # Windows
```

### Build Matrix
```yaml
# .github/workflows/release.yml
strategy:
  matrix:
    include:
      - os: macos-latest
        target: x86_64-apple-darwin
      - os: macos-latest
        target: aarch64-apple-darwin
      - os: ubuntu-latest
        target: x86_64-unknown-linux-gnu
      - os: windows-latest
        target: x86_64-pc-windows-msvc
```

## Validation at Runtime

### How It Works

```rust
pub fn validate_command(spec_path: &Path) -> Result<()> {
    // 1. Load user's spec (NOT bundled)
    let spec_content = std::fs::read_to_string(spec_path)?;
    
    // 2. Detect version from spec
    let version = detect_oas_version(&spec_content)?;
    println!("🔍 Detected: {}", version);
    
    // 3. Get appropriate rules (bundled)
    let rules = get_embedded_rules_for_version(&version);
    
    // 4. Validate
    let validator = Validator::with_rules(rules);
    let results = validator.validate(&spec_content)?;
    
    // 5. Report results
    display_validation_results(results);
    Ok(())
}
```

### Example Usage

```bash
# User provides their OpenAPI spec
$ ls
my-api.yaml  # This is the user's spec, NOT bundled

# MicroRapid validates it using bundled rules
$ mrapids validate spec my-api.yaml
🔍 Reading spec: my-api.yaml
🔍 Detected: OpenAPI 3.0.3
📋 Applying OpenAPI 3.0.x validation rules (bundled)
✅ Validation passed!

# Different spec, different rules
$ mrapids validate spec legacy-swagger.json
🔍 Reading spec: legacy-swagger.json
🔍 Detected: Swagger 2.0
📋 Applying Swagger 2.0 validation rules (bundled)
⚠️  Warning: Missing basePath (required in Swagger 2.0)
```

## Storage Locations

### Where Rules Live
```
# Development
api-runtime/
├── rules/                      # Source rules
│   ├── oas2.spectral.yaml
│   ├── oas3.spectral.yaml
│   └── oas31.spectral.yaml

# After compilation (embedded)
target/release/mrapids          # All rules inside binary

# At runtime (temporary)
/tmp/mrapids-rules-{uuid}.yaml  # Extracted for Spectral
```

### Where User Specs Live
```
# User's project (anywhere)
~/projects/my-api/
├── openapi.yaml               # User's spec
├── swagger.json               # Another spec
└── specs/
    └── internal-api.yaml      # More specs
```

## Summary

- **Validation rules**: Embedded in binary at compile time (~200KB)
- **OpenAPI specs**: Provided by users, never bundled
- **Distribution**: Single binary with everything needed
- **Version detection**: Automatic from spec content
- **Platform support**: Build for each OS/architecture

This approach keeps MicroRapid as a single, self-contained binary while supporting all OpenAPI versions!