# Validatrix
A multi-language source code validation framework written in Nim. Validatrix uses tokenizer-based validation to check syntax correctness across 10 languages and config formats, with auto-detection, comprehensive diagnostics, and a never-crash guarantee.
## Features
- **10 languages supported**: Nim, Bash, Python, JavaScript, PHP, HTML, Jinja, JSON, YAML, TOML
- **Tokenizer-based validation** — real tokenizers that track bracket depth, string context, comments, and nesting
- **Auto-detection** — detect language from file extension or content analysis
- **Comprehensive diagnostics** — structured error reports with position, severity, hints, and debug output
- **Never-crash guarantee** — every validation path is wrapped in try/except; invalid input returns errors gracefully, never panics
- **JSON output** — machine-readable diagnostics via `toJson()` on any validation result
- **Inspection API** — extract module structure (imports, definitions, functions/classes) as JSON
- **Debug mode** — compile with `-d:validatrixDebug` for detailed tokenization logging
- **No external dependencies** — pure Nim standard library
## Quick Start
```nim
import validatrix
# Validate source code from a string
let r = validateSource("proc hello() = echo 'hi'", lfNim)
echo r.errors # seq[ValidationError]
# Auto-detect language
let r2 = validateSource("print('hello')", lfUnknown) # detects Python
# Validate a file
let r3 = validateFile("path/to/file.nim", lfNim)
# Get JSON diagnostics
echo r.toJson().pretty()
# Inspect source structure
let info = inspectSource("class Foo: ...", lfPython)
echo $info # JSON with class/function info
```
## CLI Usage
When compiled as a standalone binary:
```
validatrix validate --file=source.nim
validatrix validate --source="print('hi')" --flavor=python
validatrix inspect --file=source.py
validatrix detect --file=unknown.txt
```
## API Reference
### Core Functions
| Function | Description |
|---|---|
| `validateSource(source, flavor, options, sourcePath)` | Validate source code string |
| `validateFile(filePath, flavor, options)` | Validate a file |
| `inspectSource(source, flavor, options, sourcePath)` | Return structural diagnostics as JSON |
| `inspectFile(filePath, flavor, options)` | Return structural diagnostics for a file as JSON |
| `detectFlavor(source, filePath)` | Auto-detect language flavor |
| `supportedFlavors()` | List all registered language flavors |
### Types
- **`ValidationResult`** — contains `errors: seq[ValidationError]`, `valid: bool`, `moduleInfo`, `debugOutput`, `detectionInfo`
- **`ValidationError`** — contains `code`, `message`, `severity`, `position`, `hint`, `context`
- **`ValidationOptions`** — contains `flavor`, `debugMode`, `maxErrors`, `validateAll`
- **`LanguageFlavor`** — enum: `lfUnknown`, `lfNim`, `lfBash`, `lfPython`, `lfJavaScript`, `lfPHP`, `lfHTML`, `lfJinja`, `lfJSON`, `lfYAML`, `lfTOML`
## Error Codes
| Code | Meaning |
|---|---|
| `E1000` | Unexpected/unmatched bracket |
| `E1001` | Unclosed bracket |
| `E1002` | Unmatched closing bracket |
| `E2000` | Unclosed string literal |
| `E2001` | Invalid string escape |
| `E2002` | Unclosed multi-line string |
| `E3000` | Unclosed comment |
| `E3001` | Invalid comment syntax |
| `E4000` | Invalid syntax |
| `E4001` | Reserved word misuse |
| `E5000` | Unclosed block/control structure |
| `E9999` | Internal error (never-crash fallback) |
## Supported Languages
| Language | File Extensions | Tokenizer Features |
|---|---|---|
| Nim | `.nim`, `.nims`, `.nimble` | Block comments `#[ ]#` with nesting, triple-quoted strings, raw strings, doc comments |
| Bash | `.sh`, `.bash` | Shebang detection, heredocs, command substitution, variable expansion, fi/done/esac matching |
| Python | `.py` | F-strings with nesting, triple-quoted strings, decorators, async/await, match statements |
| JavaScript | `.js`, `.jsx`, `.mjs`, `.cjs` | Template literals with nesting, regex literals, arrow functions, ESM imports |
| PHP | `.php` | `<?php` tags, heredocs/nowdocs, variable variables |
| HTML | `.html`, `.htm` | Tag balancing, self-closing tags, attributes |
| Jinja | `.j2`, `.jinja`, `.html.j2` | `{% %}`, `{{ }}`, `{# #}` block detection, nested blocks |
| JSON | `.json` | Bracket balance, string validation, comma checking |
| YAML | `.yaml`, `.yml` | Indentation tracking, key-value checking |
| TOML | `.toml` | Table headers, bracket balance, string validation |
## Building
```bash
# Build the library
nim c src/validatrix.nim
# Build with debug mode
nim c -d:validatrixDebug src/validatrix.nim
# Run all tests
nim c -r tests/test_all.nim
# Build standalone binary
nim c -d:release src/validatrix.nim
```
## Testing
The test suite covers **256 test cases** across all supported languages:
- **25-30 tests per language** including edge cases
- **Fuzz tests** — null bytes, binary data, deep nesting (100 levels), unicode bombs, empty sources
- **Mixed-file validators** — HTML+Jinja combined files
- **Config formats** — JSON, YAML, TOML validation
- **Concurrent validation** — thread safety under parallel calls
- **Never-crash guarantee** — every test verifies invalid input returns graceful errors, not crashes
## Architecture
```
src/validatrix/
validatrix.nim # Public API entry point
core/
types.nim # Core types: ValidationResult, ValidationError, LanguageFlavor
tokenizerbase.nim # Abstract tokenizer base class
validatorbase.nim # Abstract validator base class
detector.nim # Language auto-detection
debug.nim # Debug logging infrastructure
tokenizers/
nim_tokenizer.nim
bash_tokenizer.nim
python_tokenizer.nim
javascript_tokenizer.nim
php_tokenizer.nim
html_tokenizer.nim
jinja_tokenizer.nim
languages/
nim_validator.nim
bash_validator.nim
python_validator.nim
javascript_validator.nim
php_validator.nim
html_validator.nim
jinja_validator.nim
config_validators.nim # JSON, YAML, TOML validators
reporting/
errors.nim # Error formatting and JSON output
```
## License
MIT
## Author
molodetz — DevPlace Code