typo3/class-alias-loader
Adds Composer-powered class aliasing for PHP libraries that rename classes. Reads alias maps from composer.json, rewrites vendor/autoload.php on dump-autoload, and registers a loader that calls class_alias() so old class names keep working transparently.
composer require typo3/class-alias-loader
composer.json:
Add your alias map file path under extra:
"extra": {
"typo3/class-alias-loader": {
"class-alias-maps": [
"path/to/YourAliasMap.php"
]
}
}
app/Compatibility/LaravelAliasMap.php):
return [
'Old\Deprecated\Class' => 'App\\New\\Class',
'Illuminate\Support\Facades\Input' => 'Illuminate\Http\Request',
];
composer dump-autoload
new Old\Deprecated\Class()).Laravel Facade Migration:
Replace Input::old() with request()->old() gradually by adding:
return [
'Illuminate\Support\Facades\Input' => 'Illuminate\Http\Request',
];
Now Input::old() transparently resolves to Request::old().
Phased Migration:
composer.json.Third-Party Compatibility:
vendor/symfony/alias-map.php).return [
'Symfony\Component\Debug\Debug' => 'Symfony\Component\Debug\Debugger',
];
Dynamic Aliases (Runtime):
always-add-alias-loader in composer.json:
"extra": {
"typo3/class-alias-loader": {
"always-add-alias-loader": true
}
}
use TYPO3\ClassAliasLoader\ClassAliasMap;
ClassAliasMap::addAliasMap([
'Dynamic\Class' => 'App\\Dynamic\\NewClass',
]);
API-Driven Resolution:
ClassAliasMap::getClassNameForAlias() in custom logic:
$newClass = \TYPO3\ClassAliasLoader\ClassAliasMap::getClassNameForAlias('Old\Class');
if ($newClass !== 'Old\Class') {
// Handle migration logic
}
Laravel Facades:
Avoid aliasing Facades directly (breaks DI). Use AppServiceProvider:
Facade::alias('Input', Request::class);
Reserve the loader for non-Facade classes (e.g., helpers, models).
Monorepos:
Place alias maps in a shared config/ directory (e.g., config/compatibility/laravel.php).
CI/CD:
Add composer dump-autoload to your build pipeline to ensure aliases are always up-to-date.
Testing:
Mock aliases in tests using ClassAliasMap::addAliasMap() to simulate deprecated behavior.
Facades and Dependency Injection:
Input) breaks Laravel’s container binding.Facade::alias() in AppServiceProvider instead.Namespace Collisions:
Old\Class vs. Old\Other\Class) may cause ClassNotFound errors.\App\Old\Class).Autoload Conflicts:
vendor/autoload.php if the loader fails silently.vendor/autoload.php before running composer dump-autoload.Case Sensitivity:
strtolower() or strtoupper() in alias maps if case-insensitive behavior is needed (not recommended post-v2.0.0).Performance Overhead:
composer.json for production.Composer Plugin Conflicts:
humbug/phar-updater) may interfere with autoload generation.--no-plugins to isolate the issue:
composer dump-autoload --no-plugins
Inspect Aliases: Create a custom Artisan command to list active aliases:
// app/Console/Commands/ListAliases.php
use TYPO3\ClassAliasLoader\ClassAliasMap;
public function handle() {
$aliases = ClassAliasMap::getAllAliasMaps();
dd($aliases);
}
Run with:
php artisan alias:list
Check Autoload:
Verify vendor/autoload.php includes the loader:
grep -A5 "ClassAliasLoader" vendor/autoload.php
Enable Debugging:
Set TYPO3_CLASS_ALIAS_LOADER_DEBUG=1 in your environment to log alias resolutions.
Common Errors:
composer dump-autoload --optimize.Facade::alias() instead).Custom Alias Maps:
composer.json or dynamically via ClassAliasMap::addAliasMap().Preventive Aliasing:
$oldClass = 'Old\Class';
$newClass = ClassAliasMap::getClassNameForAlias($oldClass);
if ($newClass !== $oldClass) {
Log::warning("Deprecated class used: {$oldClass}");
}
Environment-Specific Aliases:
alias-map.prod.php, alias-map.dev.php) using always-add-alias-loader.Integration with Laravel:
booted event to add runtime aliases:
use Illuminate\Foundation\Application;
Application::booted(function () {
ClassAliasMap::addAliasMap([
'Legacy\Class' => 'App\\Legacy\\NewClass',
]);
});
How can I help you explore Laravel packages today?