如何在原生PHP中实现URL路由?替代.htaccess的解决方案
Got it, let's tackle this problem step by step. Since you're dealing with growing module folders and want to replace your rigid .htaccess rewrite rules with a flexible PHP-powered routing system, here's a practical solution that maps URLs directly to your PHP files—no separate controller/view folders required.
Step 1: Update Your .htaccess
First, we still need a minimal .htaccess to route all incoming requests to a single entry point (we'll use index.php as our router). Replace your existing rules with this:
RewriteEngine On # Skip existing files/directories (so static assets like CSS/JS load normally) RewriteCond %{REQUEST_FILENAME} !-f RewriteCond %{REQUEST_FILENAME} !-d # Forward all other requests to index.php RewriteRule ^(.*)$ index.php?request=$1 [L,QSA]
- The
QSAflag preserves any query string parameters (like?id=123) so they're passed to your PHP files. - We skip existing files/directories to avoid breaking static assets.
Step 2: Build the PHP Router (index.php)
This router will parse the incoming URL, map it to your target PHP file, and include it if it exists. We'll add error handling for missing files too:
<?php // Get the requested path (strip leading/trailing slashes) $request = trim($_GET['request'] ?? '', '/'); // If no path is requested, load a default file (e.g., home.php) if (empty($request)) { $request = 'home'; } // Map the URL path to a PHP file (add .php extension) $filePath = __DIR__ . '/' . $request . '.php'; // Check if the file exists if (file_exists($filePath)) { // Include the file (it will handle the request directly) require $filePath; } else { // Handle 404 errors http_response_code(404); echo "<h1>404 Not Found</h1>"; echo "The requested resource $request.php could not be found."; } ?>
Step 3: Example Usage
Let's say you have a module folder structure like this:
project/ ├── index.php ├── .htaccess ├── module1/ │ ├── google_api_create_update.php │ └── user_management.php └── module2/ └── payment_process.php
- Accessing
yourdomain.com/module1/google_api_create_updatewill loadmodule1/google_api_create_update.phpdirectly. - Accessing
yourdomain.com/module2/payment_process?id=456will loadmodule2/payment_process.phpwith theidparameter available via$_GET['id']. - Accessing the root (
yourdomain.com) will loadhome.php(you can adjust the default file in the router code).
Step 4: Optional Enhancements
If you want to make this more robust for future growth, consider adding these:
- Autoloading: Use
spl_autoload_register()to automatically load classes if you start using OOP in your module files. - Route Validation: Add checks to restrict access to certain files/folders (e.g., block direct access to config files).
- Cleaner URL Parameters: Parse the URL path to extract parameters without using query strings (e.g.,
/module1/user/123maps tomodule1/user.phpwith$userId = 123). - Error Logging: Log 404 errors to a file for debugging.
This setup is lightweight, scalable, and fits your requirement of directly calling filenames without strict MVC conventions. You can add new modules/folders anytime without updating any rewrite rules—just drop in the PHP files and they'll be accessible via their URL path.
内容的提问来源于stack exchange,提问作者Stack Overflow

