.ht.router.php 2.4 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071
  1. <?php
  2. /**
  3. * @file
  4. * Router script for the built-in PHP web server.
  5. *
  6. * The built-in web server should only be used for development and testing as it
  7. * has a number of limitations that makes running Drupal on it highly insecure
  8. * and somewhat limited.
  9. *
  10. * Note that:
  11. * - The server is single-threaded, any requests made during the execution of
  12. * the main request will hang until the main request has been completed.
  13. * - The web server does not enforce any of the settings in .htaccess in
  14. * particular a remote user will be able to download files that normally would
  15. * be protected from direct access such as .module files.
  16. *
  17. * The router script is needed to work around a bug in PHP, see
  18. * https://bugs.php.net/bug.php?id=61286.
  19. *
  20. * Usage:
  21. * php -S localhost:8888 .ht.router.php
  22. *
  23. * @see http://php.net/manual/en/features.commandline.webserver.php
  24. */
  25. if (PHP_SAPI !== 'cli-server') {
  26. // Bail out if this is not PHP's Development Server.
  27. header($_SERVER['SERVER_PROTOCOL'] . ' 403 Forbidden');
  28. exit;
  29. }
  30. $url = parse_url($_SERVER['REQUEST_URI']);
  31. if (file_exists(__DIR__ . $url['path'])) {
  32. // Serve the requested resource as-is.
  33. return FALSE;
  34. }
  35. // Work around the PHP bug.
  36. $path = $url['path'];
  37. $script = 'index.php';
  38. if (str_contains($path, '.php')) {
  39. // Work backwards through the path to check if a script exists. Otherwise
  40. // fallback to index.php.
  41. do {
  42. $path = dirname($path);
  43. if (preg_match('/\.php$/', $path) && is_file(__DIR__ . $path)) {
  44. // Discovered that the path contains an existing PHP file. Use that as the
  45. // script to include.
  46. $script = ltrim($path, '/');
  47. break;
  48. }
  49. } while ($path !== '/' && $path !== '.');
  50. }
  51. // Update $_SERVER variables to point to the correct index-file.
  52. $index_file_absolute = $_SERVER['DOCUMENT_ROOT'] . DIRECTORY_SEPARATOR . $script;
  53. $index_file_relative = DIRECTORY_SEPARATOR . $script;
  54. // SCRIPT_FILENAME will point to the router script itself, it should point to
  55. // the full path of index.php.
  56. $_SERVER['SCRIPT_FILENAME'] = $index_file_absolute;
  57. // SCRIPT_NAME and PHP_SELF will either point to index.php or contain the full
  58. // virtual path being requested depending on the URL being requested. They
  59. // should always point to index.php relative to document root.
  60. $_SERVER['SCRIPT_NAME'] = $index_file_relative;
  61. $_SERVER['PHP_SELF'] = $index_file_relative;
  62. // Require the script and let core take over.
  63. require $_SERVER['SCRIPT_FILENAME'];