PSR-4 Rules and Directory Mapping
PSR-4 Specification
PSR-4 defines how to map a namespace prefix to a filesystem directory.
The Mapping Process
Step 1: Start with the fully qualified class name
Vendor\Module\Model\Product
Step 2: Match against registered namespace prefixes
Prefix: Vendor\Module\
Remaining: Model\Product
Step 3: Replace namespace separators with directory separators
Model\Product -> Model/Product.php
Step 4: Prepend the base directory from the prefix mapping
app/code/Vendor/Module/ + Model/Product.php
= app/code/Vendor/Module/Model/Product.php
Complete Example
composer.json:
{
"autoload": {
"psr-4": {
"Vendor\\Module\\": "app/code/Vendor/Module/"
}
}
}
File structure:
app/code/Vendor/Module/
├── Model/
│ ├── Product.php # Vendor\Module\Model\Product
│ ├── ProductRepository.php # Vendor\Module\Model\ProductRepository
│ └── ResourceModel/
│ ├── Product.php # Vendor\Module\Model\ResourceModel\Product
│ └── Product/
│ └── Collection.php # Vendor\Module\Model\ResourceModel\Product\Collection
├── Helper/
│ └── Data.php # Vendor\Module\Helper\Data
├── Controller/
│ └── Index/
│ └── Index.php # Vendor\Module\Controller\Index\Index
└── Block/
└── Product/
└── View.php # Vendor\Module\Block\Product\View
PSR-4 Rules
1. The namespace prefix maps to a base directory
2. Each namespace segment maps to a subdirectory
3. The class name maps to the filename
4. The filename MUST end with .php
5. The class name MUST match the filename exactly (case-sensitive)
6. One class per file
7. The file MUST contain only PHP code
Multiple Prefixes
{
"autoload": {
"psr-4": {
"Vendor\\Module\\": "app/code/Vendor/Module/",
"Vendor\\Library\\": "lib/Vendor/Library/",
"": "app/code/"
}
}
}
The empty string prefix is a fallback for any class not matched by other prefixes.
Key Takeaway
PSR-4 strips the namespace prefix and converts the remainder to a file path. The prefix maps to a base directory, and namespace segments become subdirectories.
PSR-4 vs Classmap vs Files
Autoloading Methods Comparison
| Method | Use Case | Pros | Cons |
|---|---|---|---|
| PSR-4 | Standard namespaces | Flexible, lazy loading | Slightly slower path resolution |
| Classmap | Non-standard classes | Fastest loading | Must regenerate after adding classes |
| Files | Helper functions, constants | Always loaded | Slows initial bootstrap |
PSR-4 Configuration
{
"autoload": {
"psr-4": {
"Vendor\\Module\\": "src/"
}
}
}
Classmap Configuration
{
"autoload": {
"classmap": [
"src/",
"lib/"
]
}
}
Classmap scans directories and creates a map of class names to file paths.
Files Configuration
{
"autoload": {
"files": [
"src/helpers.php",
"src/constants.php"
]
}
}
Files are always loaded on every request. Use for helper functions or constants.
When to Use Each
PSR-4: Standard classes with proper namespaces (preferred)
Classmap: Legacy code without namespaces, performance-critical
Files: Helper functions (array_*, string_*), global constants
Composer Optimization
# Development: PSR-4 (flexible)
composer install
# Production: optimized classmap (faster)
composer install --optimize-autoloader
composer dump-autoload --optimize
# This generates:
# - composer/classmap.php (pre-scanned class map)
# - composer/autoload_files.php (files to include)
# - composer/autoload_namespaces.php (PSR-4 mappings)
Key Takeaway
PSR-4 is the standard for modern PHP. Classmap provides faster loading for production. Files is only for helper functions. Always use --optimize-autoloader in production.
Magento's Autoload.php
Magento Bootstrap Process
pub/index.php
-> require app/bootstrap.php
-> require vendor/autoload.php (Composer)
-> Register Magento autoloader
-> Bootstrap::create()
-> Application runs
Magento's vendor/autoload.php
Composer generates this file with all configured autoloaders:
vendor/autoload.php
-> vendor/composer/autoload_real.php
-> vendor/composer/autoload_static.php (optimized)
-> vendor/composer/autoload_classmap.php
-> vendor/composer/autoload_namespaces.php
-> vendor/composer/autoload_files.php
Debugging Autoloading
<?php
// Check registered autoloaders
print_r(spl_autoload_functions());
// Find where a class is defined
$ref = new ReflectionClass('Vendor\Module\Model\Product');
echo $ref->getFileName();
// Check if class exists (triggers autoloader)
if (class_exists('Vendor\Module\Model\Product')) {
echo 'Class found';
}
// Composer's compiled classmap
// Run: composer dump-autoload -v
Magento-Specific Autoloading
1. Composer autoloader loads vendor packages
2. Magento registers additional autoloaders for:
- Generated classes (factories, proxies, interceptors)
- Theme files (templates, skins)
- View files (JS, CSS)
3. The fallback autoloader checks:
- app/code/ directory
- Generated/ directory
- Vendor/ directory
- Theme directories
Performance Tips
# Always optimize in production
composer dump-autoload --optimize
# Regenerate after code changes
bin/magento setup:di:compile
bin/magento setup:static-content:deploy
# Check for class conflicts
composer validate
bin/magento setup:di:compile 2>&1 | grep -i error
Key Takeaway
Magento uses Composer's autoloader as the foundation, supplemented by generated classes and fallback autoloaders. Always optimize the autoloader in production for better performance.
Quiz
1. How does PSR-4 map Vendor\Module\Model\Product to a file?
2. What is the empty string prefix in PSR-4?
3. When should you use classmap autoloading?
4. What does composer install --optimize-autoloader do?
5. What is the files autoloading method used for?
Flashcards
Question
How does PSR-4 map namespaces to files?
Click to reveal answer
Answer
Strip the namespace prefix, replace backslashes with forward slashes, append .php. Vendor\Module\Product with prefix Vendor\\Module\\ maps to Product.php in the base directory.
Question
What is the empty string prefix in PSR-4?
Click to reveal answer
Answer
A fallback for classes not matched by other prefixes. Any unregistered class is looked up relative to its base directory.
Question
What is the difference between PSR-4 and classmap?
Click to reveal answer
Answer
PSR-4: lazy loading, flexible, resolves paths at runtime. Classmap: pre-scanned, fastest loading, must regenerate after adding classes.
Question
When should you use files autoloading?
Click to reveal answer
Answer
For helper functions and constants that need to be globally available. Not for classes. Files are included on every request.
Question
What command optimizes the autoloader for production?
Click to reveal answer
Answer
composer dump-autoload --optimize or composer install --optimize-autoloader. Generates classmap for faster loading.
Question
How does Magento's autoloader work?
Click to reveal answer
Answer
Composer autoloader (PSR-4/classmap) + Magento's generated classes (factories, proxies) + fallback autoloader for themes and view files.
Question
What must a PSR-4 filename match?
Click to reveal answer
Answer
The class name exactly (case-sensitive). Product class must be in Product.php, not product.php or PRODUCT.php.
Question
What is the classmap.php file?
Click to reveal answer
Answer
A pre-computed map of all class names to their file paths. Generated by Composer for faster class loading without path resolution.
Revision Notes
Key Takeaways
- 1. PSR-4 maps namespace prefixes to directories
- 2. Strip prefix, replace backslashes, append .php
- 3. One class per file, filename must match class name
- 4. Classmap provides faster loading for production
- 5. Files autoloading is for helper functions only
- 6. Always optimize autoloader in production
- 7. Magento uses Composer + generated classes + fallback autoloader
Interview Tips
- • Explain the PSR-4 mapping process step by step
- • Know when to use PSR-4 vs classmap vs files
- • Describe how to optimize autoloading for production
- • Explain Magento's autoloading stack
- • Debug autoloading issues with spl_autoload_functions()
Cheat Sheet
PSR-4 Autoloading Cheat Sheet
Mapping:
Vendor\Module\Product -> Remove prefix -> Product.php -> Prepend base dir
composer.json:
"autoload": {
"psr-4": { "Vendor\\Module\\": "src/" }
}
Methods:
- PSR-4: Standard namespaces (preferred)
- Classmap: Fastest, pre-scanned
- Files: Helper functions, constants
Optimization:
composer dump-autoload --optimize
Rules:
- Prefix maps to base directory
- Namespace segments = subdirectories
- Class name = filename (case-sensitive)
- One class per file