Understand Laravel route with optional parameter

I’m trying to create a route with one optional parameter with Laravel 5.4.

Route :

Route::get('/run/{zone?}/id/{id}', '<a href="https://getridbug.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="4c1e39220f2322383e232020293e0c3f24233b">[email protected]</a>');

Controller :
class RunController extends Controller
{
    public function show()
    {
        $route = Route::current();
        $zone = $route->parameter('zone') ?: 'default';
        $id = $route->parameter('id');

        Run::setZone($zone);
        $run = Run::findOrFail($id);
        return view('run.show')->with(['run' => $run]);
    }
}

The url run/test/id/42 works like expected.

But with run/id/42 I got a nice NotFoundHttpException in RouteCollection.php when I expect the same result than run/default/id/42

What did I missed ?

Answers:

Thank you for visiting the Q&A section on Magenaut. Please note that all the answers may not help you solve the issue immediately. So please treat them as advisements. If you found the post helpful (or not), leave a comment & I’ll get back to you as soon as possible.

Method 1

Everything after the first optional parameter must be optional. If part of the route after an optional parameter is required, then that parameter becomes required.

In your case, the id/{id} part of the route is non-optional, so the “optional” parameter before that section of the route becomes required.

Laravel’s routing is actually built on top of Symfony’s routing, and this is a restriction in Symfony. According to the Symfony documentation here (emphasis mine):

Of course, you can have more than one optional placeholder (e.g. /blog/{slug}/{page}), but everything after an optional placeholder must be optional. For example, /{page}/blog is a valid path, but page will always be required (i.e. simply /blog will not match this route).

Additionally, another thing to watch out for:

Routes with optional parameters at the end will not match on requests with a trailing slash (i.e. /blog/ will not match, /blog will match).

Method 2

Optional parameters work when it is the last URL element so in your case it won’t work.


All methods was sourced from stackoverflow.com or stackexchange.com, is licensed under cc by-sa 2.5, cc by-sa 3.0 and cc by-sa 4.0

0 0 votes
Article Rating
Subscribe
Notify of
guest

0 Comments
Inline Feedbacks
View all comments
0
Would love your thoughts, please comment.x
()
x