Dependency injection in controllers — automatic resolution
Concept
Resource controllers provide a standardized approach to CRUD operations following RESTful conventions. Route::resource() generates 7 routes that map to 7 controller methods.
The 7 resource routes:
| Verb | URI | Action | Route Name |
|---|---|---|---|
| GET | /photos | index | photos.index |
| GET | /photos/create | create | photos.create |
| POST | /photos | store | photos.store |
| GET | /photos/ | show | photos.show |
| GET | /photos//edit | edit | photos.edit |
| PUT/PATCH | /photos/ | update | photos.update |
| DELETE | /photos/ | destroy | photos.destroy |
API resource controllers: Route::apiResource() generates the same routes minus create and edit (no HTML forms in APIs). Use this for API-only controllers.
Partial resource routes: ->only(['index', 'show']) or ->except(['create', 'edit']) restrict which routes are generated.
Nested resources: Route::resource('posts.comments', PostCommentController::class) generates routes like /posts/{post}/comments/{comment}. The controller receives both parent and child model IDs.
Shallow nesting: ->shallow() avoids deeply nested URLs — only index/store use the parent; show/update/destroy use the child directly.
php artisan make:controller UserController --resource: Generates a controller stub with all 7 method signatures.
php artisan make:controller UserController --api: Generates an API resource stub (5 methods, no create/edit).
php artisan make:controller UserController --model=User: Generates with type-hinted User parameters.
Code Example
<?php
// routes/api.php
use App\Http\Controllers\Api;
Route::apiResource('users', Api\UserController::class);
Route::apiResource('posts', Api\PostController::class);
// Nested resource — post comments
Route::apiResource('posts.comments', Api\PostCommentController::class)->shallow();
// Partial resource — only list and show
Route::apiResource('categories', Api\CategoryController::class)->only(['index', 'show']);
// API Resource Controller
namespace App\Http\Controllers\Api;
use App\Http\Controllers\Controller;
use App\Http\Resources\UserResource;
use App\Http\Resources\UserCollection;
use App\Models\User;
use Illuminate\Http\Request;
use Illuminate\Http\Resources\Json\JsonResource;
class UserController extends Controller
{
public function index(Request $request): UserCollection
{
$users = User::with('profile')
->when($request->search, fn($q, $s) => $q->where('name', 'like', "%$s%"))
->paginate(15);
return new UserCollection($users);
}
public function show(User $user): UserResource
{
return new UserResource($user->load('profile', 'orders'));
}
public function store(Request $request): UserResource
{
$validated = $request->validate([
'name' => 'required|string|max:255',
'email' => 'required|email|unique:users',
'password' => 'required|string|min:8',
]);
$user = User::create([...$validated, 'password' => bcrypt($validated['password'])]);
return new UserResource($user);
}
public function update(Request $request, User $user): UserResource
{
$user->update($request->validated());
return new UserResource($user);
}
public function destroy(User $user): \Illuminate\Http\Response
{
$user->delete();
return response()->noContent(); // 204 No Content
}
}