Pebellslearn by building
0%
RoadmapsMatrixCoursesSandboxSign in
Controllers  ›  Lesson

Route Model Binding

Route model binding 12 minWhen a route parameter's name matches a type-hinted model argument, Laravel fetches that model automatically and sends a 404 if it does not exist.

Route Model Binding

Look at almost any show, edit or update method and its first line is the same: take the id, look up the record, 404 if it is missing. Lendly would repeat Book::findOrFail($id) in dozens of places. Route model binding makes Laravel do that line for you.

The rule

Same name, model type: Laravel fetches it or sends 404.

Before:

Route::get('/books/{id}', [BookController::class, 'show']);

public function show(string $id)
{
    $book = Book::findOrFail($id);
    return view('books.show', ['book' => $book]);
}

After:

Route::get('/books/{book}', [BookController::class, 'show']);

public function show(Book $book)
{
    return view('books.show', ['book' => $book]);
}

Two things must line up:

  1. The URI segment is {book}, and the argument is $book. The names match.
  2. The argument is type-hinted with the model, Book.

Then, for /books/12, Laravel runs the lookup by primary key and passes in the finished Book. For /books/9999 with no such row, it sends a 404 and your method never runs.

Looking up by another column. Put the column after a colon in the URI:

Route::get('/books/{book:slug}', [BookController::class, 'show']);

Now /books/dune fetches the book whose slug is dune. To make a column the default for every route, override getRouteKeyName() on the model to return 'slug'.

It works in closures too: Route::get('/books/{book}', fn (Book $book) => $book->title);.

The shortcut

Scan the route and the signature side by side and ask "does the brace name match a type-hinted model variable?" If yes, the lookup and the 404 are handled. If the names differ, you get no binding.

Why is $book empty?Step 1 of 4
  1. The route

    Route::get('/books/{id}', [BookController::class, 'show']).

That empty-model result is the trap. There is no error, just a blank page with no title, so compare names first.

Drills

Answer fast — trust the rule.

quick drill

Which pairing binds a Member model automatically?

quick drill

With binding in place, what does /books/9999 return when no such book exists?

quick drill

Which route fetches a book by its isbn column?

quick drill

How do you make every Book route look up by slug by default?

Remember

  • Same name, model type: Laravel fetches it or sends 404.
  • Compare brace name and variable name first.
  • Trap: mismatched names give an empty model, not an error.

Practice — level up

0/1 solved

Write your answer, then compare it with a rubric and a model answer.

ExplainLet Laravel fetch the book

Rewrite Lendly's show route and method so Laravel fetches the Book for you. Explain the naming rule that makes it work, what happens for a missing id, and how to look books up by slug instead.