Files
rspade_system/app/RSpade/CodeQuality/RuntimeChecks/CLAUDE.md
root f6fac6c4bc Fix bin/publish: copy docs.dist from project root
Fix bin/publish: use correct .env path for rspade_system
Fix bin/publish script: prevent grep exit code 1 from terminating script

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-10-21 02:08:33 +00:00

142 lines
5.6 KiB
Markdown
Executable File

# RuntimeChecks - Convention Enforcement System
## CRITICAL DISTINCTION: Runtime Requirements vs Convention Enforcement
This directory contains **convention enforcement checks** that throw `YoureDoingItWrongException` when developers violate framework conventions. These are NOT runtime requirements.
### What BELONGS Here (Convention Enforcement)
Convention checks are "best practice" validations that:
- **Could technically work** if not enforced (the code would still execute)
- Ensure **consistency and uniformity** across the codebase
- Prevent **bad coding patterns** before they become technical debt
- Are primarily checked **in development mode only**
- Provide **verbose remediation guidance** explaining the right way
Examples:
- Bundle doesn't include the view/controller directory (organizational convention)
- Views having inline `<style>` or `<script>` tags (asset organization convention)
- Layouts missing `rsx_body_class()` or bundle includes (scoping convention)
- Using absolute paths instead of RSX IDs for blade includes
- Hardcoding URLs instead of using route helpers
### What does NOT Belong Here (Runtime Requirements)
Runtime sanity checks are **actual execution requirements** that:
- **Would break the code** if not enforced
- Are **algorithmic requirements** for the code to function
- Document **what the algorithm expects** to operate correctly
- Must be checked **in all environments** (dev and production)
- Usually have **brief error messages** (the fix is obvious or situation unexpected)
Examples:
- File doesn't exist that needs to be loaded
- Duplicate class names (breaks autoloading)
- Manifest not initialized when required
- Required configuration missing
- Invalid data types that would cause crashes
**These MUST stay inline with their related code** because:
1. They document the algorithm's requirements
2. A developer reading the code needs to understand these constraints
3. They're part of the logic flow, not optional conventions
## Decision Framework
When deciding whether to create a RuntimeCheck or keep inline:
### Create a RuntimeCheck if:
- ✅ The code would still technically execute without the check
- ✅ You're enforcing a "preferred way" when multiple ways exist
- ✅ The check is primarily for development mode
- ✅ The error message needs extensive explanation and remediation steps
- ✅ You're preventing future problems, not current execution failures
### Keep Inline if:
- ❌ The code would fail/crash without the check
- ❌ It's a fundamental requirement of the algorithm
- ❌ The check documents what the code expects to operate
- ❌ It must run in production too
- ❌ The error is unexpected with no clear remediation
**When in doubt, keep it inline.** It's better to have too much information about an algorithm's requirements visible than to hide critical constraints in a separate file.
## The Cardinal Sin
**NEVER remove critical algorithm information** by moving runtime requirements to this directory. If a check explains what an algorithm needs to function correctly, it MUST stay with that algorithm.
## Creating New RuntimeChecks
1. **Group by feature domain** (BundleErrors, ViewErrors, RouteErrors, etc.)
2. **Use static methods** that build and throw comprehensive error messages
3. **Always throw `YoureDoingItWrongException`** to make it clear this is a convention violation
4. **Include verbose remediation** with examples and exact steps to fix
5. **Name methods descriptively** (e.g., `view_has_inline_assets`, `bundle_missing_controller`)
### Example Structure
```php
<?php
namespace App\RSpade\CodeQuality\RuntimeChecks;
class BundleErrors
{
/**
* Bundle doesn't include the view directory (convention for organization)
*/
public static function view_not_covered(
string $view_path,
string $view_dir,
string $bundle_class,
array $include_paths
): void {
$error_message = "RSX Bundle Path Coverage Error: ...\n\n";
// Detailed explanation of the problem
$error_message .= "View file: {$view_path}\n";
$error_message .= "Bundle: {$bundle_class}\n\n";
// Clear remediation steps
$error_message .= "To fix this, either:\n";
$error_message .= "1. Add '{$view_dir}' to the bundle's 'include' array\n";
$error_message .= "2. Use a different bundle that covers this module\n\n";
// Why this convention exists
$error_message .= "This ensures bundles are properly scoped to the modules they serve.";
throw new YoureDoingItWrongException($error_message);
}
}
```
## Usage Pattern
In your code where you want to enforce a convention:
```php
// In development mode only
if (!app()->environment('production')) {
// Check convention (bundle should include view directory)
if (!$bundle_includes_view) {
// Verbose error explaining the convention
BundleErrors::view_not_covered($view_path, $view_dir, $bundle_class, $include_paths);
}
}
```
## File Organization
- `YoureDoingItWrongException.php` - The base exception class
- `BundleErrors.php` - Bundle-related convention violations
- `ViewErrors.php` - View/template convention violations
- `RouteErrors.php` - Routing convention violations
- etc. (grouped by feature domain)
## Remember
These checks are about **teaching developers the right way**, not preventing crashes. They're educational guardrails that can be removed without breaking functionality - but shouldn't be, because they prevent bad patterns from taking root.
The key test: **"Would the code still run if I commented out this check?"**
- Yes → RuntimeCheck (convention)
- No → Keep inline (requirement)