Module :: unilang
Zero-overhead command framework with compile-time command registration
Value Proposition
unilang processes command definitions at compile-time, generating Perfect Hash Function (PHF) maps that provide O(1) command lookups with zero runtime overhead. This approach delivers:
- 10-50x faster command resolution compared to runtime HashMap lookups
- Compile-time validation of all command definitions and arguments
- Smaller binary size through static analysis and dead code elimination
- SIMD acceleration for parsing with 4-25x performance improvements
- Zero memory allocations for command lookup operations
Architecture Overview
Compile-Time Processing:
YAML definitions → build.rs → PHF maps → Zero-cost lookups
Runtime Execution:
Command string → O(1) PHF lookup → Validated execution
Quick Start: Compile-Time Registration (Recommended)
Step 1: Define Commands
Create unilang.commands.yaml:
- name: "greet"
namespace: ""
description: "High-performance greeting command"
arguments:
- name: "name"
kind: "String"
attributes:
optional: true
default: "World"
Step 2: Configure Build Script
Add to build.rs:
use env;
use Path;
Step 3: Zero-Cost Execution
use *;
// Include compile-time generated PHF maps
include!;
Performance Comparison
| Approach | Lookup Time | Memory Overhead | Binary Size |
|---|---|---|---|
| Compile-Time (PHF) | 1-3 CPU cycles | Zero | Smaller |
| Runtime (HashMap) | 50-150 CPU cycles | Hash tables + allocations | Larger |
Benchmark Results:
- Static lookups: ~2ns per operation
- Dynamic lookups: ~80ns per operation
- Performance gain: 40x faster command resolution
When to Use Each Approach
Compile-Time Registration (Recommended)
Use when:
- Commands are known at build time
- Maximum performance is required
- Binary size optimization is important
- Production deployments
Benefits:
- Zero runtime lookup cost
- Compile-time validation
- Smaller memory footprint
- Better cache locality
Runtime Registration (Limited Use Cases)
Use when:
- Commands loaded from external sources at runtime
- Dynamic command generation required
- Plugin systems with runtime loading
- Rapid prototyping scenarios
Performance Cost:
- 10-50x slower lookup operations
- Runtime memory allocations
- Larger binary size
- Hash collision overhead
CLI Aggregation: Unifying Multiple Tools
unilang excels at aggregating multiple CLI tools into a single unified command interface. This is essential for organizations that want to consolidate developer tools while maintaining namespace isolation.
Real-World Aggregation Scenario
use CliBuilder;
// Aggregate multiple CLI tools into one unified command
let unified_cli = new
.static_module_with_prefix
.static_module_with_prefix
.static_module_with_prefix
.static_module_with_prefix
.detect_conflicts
.build_static;
// Usage: unified-cli db migrate, unified-cli fs copy src dest
Compile-Time Aggregation Benefits
Before Aggregation:
# Separate tools requiring individual installation and learning
After Aggregation:
# Single unified tool with consistent interface
Key Aggregation Features
Namespace Isolation
Each CLI module maintains its own command space with automatic prefix application:
// Database commands become .db.migrate, .db.backup
// File commands become .fs.copy, .fs.move
// Network commands become .net.ping, .net.trace
// No naming conflicts between modules
Conflict Detection
let registry = new
.static_module_with_prefix
.static_module_with_prefix // Conflict!
.detect_conflicts // Catches duplicate prefixes at build time
.build_static;
Help System Integration
# All aggregated commands support unified help
Advanced Aggregation Patterns
Conditional Module Loading
let registry = new
.conditional_module
.conditional_module
.build_static;
// Only includes modules when features are enabled
Multi-Source Aggregation
// Combine static commands, YAML definitions, and runtime modules
let registry = new
.static_module_with_prefix
.dynamic_module_with_prefix
.runtime_module_with_prefix
.build_hybrid;
Performance Characteristics
| Approach | Lookup Time | Memory Overhead | Conflict Detection |
|---|---|---|---|
| Compile-Time | O(1) PHF | Zero | Build-time |
| Runtime | O(log n) | Hash tables | Runtime |
Aggregation Scaling:
- 10 modules, 100 commands each: ~750ns lookup regardless of module count
- Single PHF map: All 1,000 commands accessible in constant time
- Namespace resolution: Zero runtime overhead with compile-time prefixing
Complete Example
See examples/practical_cli_aggregation.rs for a comprehensive demonstration showing:
- Individual CLI module definitions
- Runtime and compile-time aggregation approaches
- Namespace organization and conflict prevention
- Unified command execution patterns
- Performance comparison between approaches
# Run the complete aggregation demo
This example demonstrates aggregating database, file, network, and build CLIs into a single unified tool while maintaining type safety, performance, and usability.
Command Definition Format
Basic Command Structure
- name: "command_name" # Required: Command identifier
namespace: "optional.prefix" # Optional: Hierarchical organization
description: "What it does" # Required: User-facing description
arguments: # Optional: Command parameters
- name: "arg_name"
kind: "String" # String, Integer, Float, Boolean, Path, etc.
attributes:
optional: false # Required by default
default: "value" # Default value if optional
Supported Argument Types
- Basic Types: String, Integer, Float, Boolean
- Path Types: Path, File, Directory
- Complex Types: Url, DateTime, Pattern (regex)
- Collections: List, Map with custom delimiters
- Special Types: JsonString, Object, Enum
Validation Rules
arguments:
- name: "count"
kind: "Integer"
validation_rules:
- Min: 1
- Max: 100
- name: "email"
kind: "String"
validation_rules:
- Pattern: "^[^@]+@[^@]+\\.[^@]+$"
- MinLength: 5
Command Execution Patterns
Standard Execution
let result = pipeline.process_command_simple;
if result.success
Batch Processing
let commands = vec!
;
let batch_result = pipeline.process_batch;
println!;
Error Handling
match pipeline.process_command_simple
Help System
unilang provides comprehensive help with three access methods:
Traditional Help Operator
Modern Help Parameter
Auto-Generated Help Commands
Feature Configuration
Core Features
[]
= "0.10" # Default: enhanced_repl + simd + enabled
Performance Optimized
[]
= { = "0.10", = ["simd", "enhanced_repl"] }
Minimal Footprint
[]
= { = "0.10", = false, = ["enabled"] }
Available Features
enabled- Core functionality (required)simd- SIMD optimizations for 4-25x parsing performanceenhanced_repl- Advanced REPL with history, completion, secure inputrepl- Basic REPL functionalityon_unknown_suggest- Fuzzy command suggestions
Examples and Learning Path
Compile-Time Focus Examples
static_01_basic_compile_time.rs- PHF-based zero-cost lookupsstatic_02_yaml_build_integration.rs- Build script integration patternsstatic_03_performance_comparison.rs- Concrete performance measurementsstatic_04_multi_module_aggregation.rs- Modular command organization
Traditional Examples
01_basic_command_registration.rs- Runtime registration patterns02_argument_types.rs- Comprehensive argument type examples07_yaml_json_loading.rs- Dynamic command loading
Advanced Features
18_help_conventions_demo.rs- Help system demonstrationfull_cli_example.rs- Complete CLI application
REPL and Interactive
12_repl_loop.rs- Basic REPL implementation15_interactive_repl_mode.rs- Interactive arguments and secure input17_advanced_repl_features.rs- History, auto-completion, error recovery
WebAssembly Support
unilang provides full WebAssembly compatibility for browser deployment:
&&
WASM Features:
- Complete framework functionality in browsers
- SIMD acceleration where supported
- Optimized bundle size (800KB-1.2MB compressed)
- Seamless Rust-to-JavaScript integration
Migration from Runtime to Compile-Time
Step 1: Extract Command Definitions
Convert runtime CommandDefinition structures to YAML format.
Step 2: Configure Build Script
Add compile-time generation to build.rs.
Step 3: Update Code
Replace CommandRegistry::new() with compile-time command registration via build.rs.
Step 4: Measure Performance
Use provided benchmarking examples to verify improvements.
Performance Optimization Guidelines
Compile-Time Best Practices
- Use static command definitions for all known commands
- Leverage multi-module aggregation for organization
- Enable SIMD features for maximum parsing performance
- Utilize conflict detection during build process
Runtime Considerations
- Reserve runtime registration for truly dynamic scenarios
- Minimize command modifications during execution
- Use batch processing for multiple commands
- Implement proper error handling and recovery
Contributing
See CONTRIBUTING.md for development guidelines.
License
Licensed under MIT license (LICENSE or https://opensource.org/licenses/MIT)