A URL base path detector for Slim 4.
- Support for multiple servers
- Tested
- No dependencies
- Very fast
- Apache webserver with mod_rewrite and .htaccess
- PHP build-in webserver
- PHP 7.1+
composer require selective/basepath
The recommended directory structure:
public/
Web server files, the DocumentRoot.htaccess
Apache redirect rules for the front controllerindex.php
The front controller
.htaccess
Internal redirect to the public/ directory
The following steps are necessary for your Slim 4 application:
For Apache we have to "redirect" the web traffic to the front controller
in public/index.php
.
Create a file: public/.htaccess
with this content:
# Redirect to front controller
RewriteEngine On
# RewriteBase /
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ index.php [QSA,L]
We also need a rule to "redirect" the sub-directories to
the front-controller in public/index.php
.
Create a second .htaccess
file above the public/
directory with this content:
RewriteEngine on
RewriteRule ^$ public/ [L]
RewriteRule (.*) public/$1 [L]
Add the BasePathMiddleware
after addRoutingMiddleware()
to set the basePath before
the routing is started.
Example: public/index.php
<?php
use Psr\Http\Message\ResponseInterface as Response;
use Psr\Http\Message\ServerRequestInterface as Request;
use Selective\BasePath\BasePathMiddleware;
use Slim\Factory\AppFactory;
require_once __DIR__ . '/../vendor/autoload.php';
$app = AppFactory::create();
// Add Slim routing middleware
$app->addRoutingMiddleware();
// Set the base path to run the app in a subdirectory.
// This path is used in urlFor().
$app->add(new BasePathMiddleware($app));
$app->addErrorMiddleware(true, true, true);
// Define app routes
$app->get('/', function (Request $request, Response $response) {
$response->getBody()->write('Hello, World!');
return $response;
})->setName('root');
// Run app
$app->run();
Open your website, e.g. http://localhost
and you should see the message Hello, World!
.
The public/
directory is only the DoumentRoot
of your webserver,
but it's never part of your base path and the official url.
Good URLs:
http://www.example.com
http://www.example.com/users
http://www.example.com/my-app
http://www.example.com/my-app/users
Bad URLs:
http://www.example.com/public
http://www.example.com/public/users
http://www.example.com/my-app/public
http://www.example.com/my-app/public/users
$basePath = \Slim\Routing\RouteContext::fromRequest($request)->getBasePath(),
$routeParser = \Slim\Routing\RouteContext::fromRequest($request)->getRouteParser();
$url = $routeParser->urlFor('root');
This example requires slim/twig-view
<!DOCTYPE html>
<head>
<meta charset="utf-8">
<base href="{{ base_path() }}/"/>
</head>
<body>
{% block content %}{% endblock %}
</body>
</html>
Create issues at https://github.com/selective-php/basepath/issues