Challenge 3: Replace Manual Routes With Route::resource() — Possible Solution ==================================================================== // BEFORE — five hand-written routes use Illuminate\Support\Facades\Route; use App\Http\Controllers\ProductController; Route::get('/products', [ProductController::class, 'index'])->name('products.index'); Route::get('/products/create', [ProductController::class, 'create'])->name('products.create'); Route::post('/products', [ProductController::class, 'store'])->name('products.store'); Route::get('/products/{product}', [ProductController::class, 'show'])->name('products.show'); Route::get('/products/{product}/edit', [ProductController::class, 'edit'])->name('products.edit'); Route::put('/products/{product}', [ProductController::class, 'update'])->name('products.update'); Route::delete('/products/{product}', [ProductController::class, 'destroy'])->name('products.destroy'); // AFTER — one line Route::resource('products', ProductController::class); ROUTE NAMES GENERATED BY Route::resource('products', ProductController::class) -------------------------------------------------------------------------------- products.index GET /products products.create GET /products/create products.store POST /products products.show GET /products/{product} products.edit GET /products/{product}/edit products.update PUT /products/{product} products.destroy DELETE /products/{product} (Confirmable directly by running `php artisan route:list` after adding the Route::resource() line, per Chapter 1's Artisan challenge.) WHY THIS WORKS -------------- - Route::resource('products', ProductController::class) is Laravel's version of the exact same "generate a full RESTful route set from one line" pattern seen twice already in this project — Rails' resources :books and Django REST Framework's router.register("products", ...) from django2-2 — all three frameworks converge on essentially the same idea because REST resource routing follows a highly predictable, repeatable shape. - The generated route NAMES follow a consistent convention (products.index, products.show, etc.) automatically — matching exactly what a careful developer would have named the hand-written versions by convention anyway, just without needing to type each one out. - If only SOME of the seven actions are actually needed, Route::resource() accepts an ->only([...]) or ->except([...]) modifier to generate a subset — e.g. Route::resource('products', ProductController::class) ->only(['index', 'show']) for a read-only resource — rather than forcing all seven or none.