Route names and groups
Addresses change as a project grows: /posts/5 may become /articles/5. To avoid fixing every link, a route is given a name and the address is built from that name. Routes that share the start of the address are put into a group so the prefix is not repeated.
A route name
The name is set with setName(), called right after the route is declared:
// public/index.php
$app->get('/posts/{id:[0-9]+}', function (Request $request, Response $response, array $args) {
$response->getBody()->write('Post #' . $args['id']);
return $response;
})->setName('posts.show');The route works as before, but now it can be referred to by the name posts.show. A name is any string; the "section.action" form is convenient.
A link by name
The RouteParser object builds an address from a name. Inside a handler it is taken from the request:
// public/index.php
use Slim\Routing\RouteContext;
$app->get('/', function (Request $request, Response $response) {
$parser = RouteContext::fromRequest($request)->getRouteParser();
$url = $parser->urlFor('posts.show', ['id' => 5]);
$response->getBody()->write('<a href="' . $url . '">Post five</a>');
return $response;
});The home page shows a link to /posts/5. The use line goes at the top of the file with the others.
| Call | Result |
|---|---|
urlFor('posts.show', ['id' => 5]) | /posts/5 |
urlFor('posts.show', ['id' => 5], ['ref' => 'home']) | /posts/5?ref=home |
fullUrlFor($request->getUri(), 'posts.show', ['id' => 5]) | http://localhost:8080/posts/5 |
The second argument holds the placeholder values, the third the parameters after the question mark.
A group
A group declares the shared prefix once. Inside the group, routes are added to the $group object:
// public/index.php
use Slim\Routing\RouteCollectorProxy;
$app->group('/admin', function (RouteCollectorProxy $group) {
$group->get('/posts', function (Request $request, Response $response) {
$response->getBody()->write('Manage posts');
return $response;
});
$group->get('/users', function (Request $request, Response $response) {
$response->getBody()->write('Users');
return $response;
});
});This gives the addresses /admin/posts and /admin/users. If the prefix changes to /panel, only one line needs editing.
Names inside a group
Routes in a group are named the same way:
$group->get('/posts', $handler)->setName('admin.posts');Here $handler is any handler function. The call urlFor('admin.posts') returns /admin/posts: the group prefix is added automatically.
What else groups are for
Groups can be nested, and most importantly a middleware can be attached to a group: code that runs before all of its routes, for example a login check for the whole /admin section. Middleware has its own lesson.
Common mistake
If urlFor() is called with a name that does not exist, or a required placeholder is not passed, Slim throws an exception and the page fails with a 500 error. The usual cause is a typo in the name or a forgotten setName() call. Names must be unique: two routes with one name cannot be told apart.