Route Scoping in Laravel

Posted

In Laravel 7, custom route keys were improved and support for route scoping was added. In this post, we will go through some examples of the changes which have been made and how to use them in your Laravel project.

Custom Route Keys

Custom route keys are particularly useful if you want to customise your routing to use a slug or custom ID field from your database. If you wanted to do this in previous versions of Laravel, you would either look up the model manually in your controller or declare the getRouteKeyName method in your model which returned the name of the field you were querying from.

In order to specify a custom route key in Laravel 7 or above, simply add it after your route parameter, separated with a colon as demonstrated below:

// routes/web.php use App\Post; Route::get('posts/{post:uuid}', fn(Post $post) => $post);

Custom Route Keys in Resource Routes

You might think that's cool, but what about an API or application with a lot of route resources? At the time of writing, this seems to be hidden from the Laravel docs. The way to specify custom route keys for resource routes is to use the third array parameter for supplying any extra information your routes need. In this case, we're going to pass a parameters key containing each route parameter and the binding to the custom key.

// routes/web.php use App\Http\Controllers\Users\PostsController; Route::resource('users.posts', PostsController::class, [ 'parameters' => [ 'users' => 'users:uuid', 'posts' => 'posts:uuid' ] ]);

Alternatively, you could call the parameters method on the route resource, which will do exactly the same thing.

// routes/web.php use App\Http\Controllers\Users\PostsController; Route::resource('users.posts', PostsController::class)->parameters([ 'users' => 'users:uuid', 'posts' => 'posts:uuid' ]);

Scoping

One of the main features of Laravel 7 is automatic scoping to related models. For example, if a post with the ID of 1 belonged to a user with the ID of 1 the following would work successfully and return the post:

http://example.test/users/1/posts/1

However, if the post with an ID of 2 belonged to a user with the ID of 2, the following would result in a 404:

http://example.test/users/1/posts/2

If you want to find out more about routing in Laravel, be sure to check out the docs.

© Nathan Dunn 2023