Laravel 中间件指南
创建、注册和应用 Laravel 中间件:HTTP 过滤器、认证守卫、限流、可终止中间件和组配置。
1. 创建中间件
// php artisan make:middleware EnsureApiKey
class EnsureApiKey
{
public function handle(Request $request, Closure $next): Response
{
$key = $request->header('X-API-Key') ?? $request->query('api_key');
if (! $key || ! ApiKey::where('key', $key)->where('is_active', true)->exists()) {
return response()->json(['error' => 'API 密钥无效'], 403);
}
return $next($request);
}
}
// 带参数的中间件
class RequireRole
{
public function handle(Request $request, Closure $next, string ...$roles): Response
{
if (! in_array($request->user()->role, $roles)) {
abort(403, '权限不足');
}
return $next($request);
}
}
2. 注册中间件 (Laravel 11+)
// bootstrap/app.php
return Application::configure(basePath: dirname(__DIR__))
->withMiddleware(function (Middleware $middleware) {
$middleware->alias([
'role' => RequireRole::class,
'api.key' => EnsureApiKey::class,
]);
$middleware->appendToGroup('api', [EnsureApiKey::class]);
})->create();
3. 路由中间件应用
Route::get('/admin', AdminController::class)->middleware('auth', 'role:admin');
Route::middleware(['auth', 'verified'])->group(function () {
Route::resource('articles', ArticleController::class);
});
4. 可终止中间件
class LogResponseTime implements TerminableMiddleware
{
private float $startTime;
public function handle(Request $request, Closure $next): Response
{
$this->startTime = microtime(true);
return $next($request);
}
// 响应发送给客户端后调用
public function terminate(Request $request, Response $response): void
{
$duration = (microtime(true) - $this->startTime) * 1000;
RequestLog::create([
'path' => $request->path(),
'status' => $response->getStatusCode(),
'duration' => round($duration),
]);
}
}