本文目录导读:

在 Laravel 中,中间件的执行顺序遵循“洋葱模型”或“栈”模型,即在请求进入和响应返回时,中间件按特定顺序执行。
核心执行顺序规则
全局中间件最先执行
在 app/Http/Kernel.php 的 $middleware 属性中定义的中间件,会在所有路由中间件之前执行。
路由中间件按组和优先级执行
- StartKernel(框架核心中间件)→ 全局中间件 → 路由中间件(按注册顺序)
具体执行流程
请求进入时的执行顺序
请求 → StartKernel → 全局中间件 → 路由中间件组 → 路由特定中间件 → 控制器
响应返回时的执行顺序(反向)
控制器 → 路由特定中间件 → 路由中间件组 → 全局中间件 → StartKernel → 响应
中间件定义位置与优先级
app/Http/Kernel.php 中的三个属性
protected $middleware = [
// 1. 全局中间件(最先执行)
\App\Http\Middleware\TrustHosts::class,
\App\Http\Middleware\TrustProxies::class,
\Fruitcake\Cors\HandleCors::class,
\App\Http\Middleware\PreventRequestsDuringMaintenance::class,
\Illuminate\Foundation\Http\Middleware\ValidatePostSize::class,
\App\Http\Middleware\TrimStrings::class,
\Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull::class,
];
protected $middlewareGroups = [
'web' => [
// 2. web 组中间件
\App\Http\Middleware\EncryptCookies::class,
\Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class,
\Illuminate\Session\Middleware\StartSession::class,
// \Illuminate\Session\Middleware\AuthenticateSession::class,
\Illuminate\View\Middleware\ShareErrorsFromSession::class,
\App\Http\Middleware\VerifyCsrfToken::class,
\Illuminate\Routing\Middleware\SubstituteBindings::class,
],
'api' => [
// 3. api 组中间件
'throttle:api',
\Illuminate\Routing\Middleware\SubstituteBindings::class,
],
];
protected $routeMiddleware = [
// 4. 路由特定中间件(最后执行)
'auth' => \App\Http\Middleware\Authenticate::class,
'auth.basic' => \Illuminate\Auth\Middleware\AuthenticateWithBasicAuth::class,
'cache.headers' => \Illuminate\Http\Middleware\SetCacheHeaders::class,
'can' => \Illuminate\Auth\Middleware\Authorize::class,
'guest' => \App\Http\Middleware\RedirectIfAuthenticated::class,
'password.confirm' => \Illuminate\Auth\Middleware\RequirePassword::class,
'signed' => \Illuminate\Routing\Middleware\ValidateSignature::class,
'throttle' => \Illuminate\Routing\Middleware\ThrottleRequests::class,
'verified' => \Illuminate\Auth\Middleware\EnsureEmailIsVerified::class,
];
实际执行顺序示例
假设路由定义为:
Route::get('/admin', function () {
// 控制器逻辑
})->middleware(['web', 'auth', 'admin']);
执行顺序:
StartKernel(框架核心)
2. 全局中间件(TrustHosts, TrustProxies, HandleCors...)
3. web 组中间件(EncryptCookies, StartSession...)
4. 'auth' 中间件
5. 'admin' 中间件
6. 控制器
7. 'admin' 中间件(返回时)
8. 'auth' 中间件(返回时)
9. web 组中间件(返回时)
10. 全局中间件(返回时)
11. StartKernel(返回时)
中间件在控制器中的执行顺序
如果在控制器中指定多个中间件:
public function __construct()
{
$this->middleware('auth');
$this->middleware('log')->only('index');
$this->middleware('subscribed')->except('store');
}
执行顺序为:log → subscribed → auth(按定义顺序的倒序执行)
特殊情况
Terminable 中间件
实现 terminate() 方法的中间件,在响应发送到浏览器后执行:
public function terminate($request, $response)
{
// 在响应发送后执行
}
优先级(Priority)
可以设置中间件的优先级:
protected $middlewarePriority = [
\Illuminate\Foundation\Http\Middleware\HandlePrecognitiveRequests::class,
\Illuminate\Cookie\Middleware\EncryptCookies::class,
\Illuminate\Session\Middleware\StartSession::class,
];
实际应用建议
- 性能敏感中间件(如缓存、限流)应尽早执行
- 认证中间件(如 auth)应在路由组中间件之后
- 数据验证中间件(如 TrimStrings)应在最外层
理解这个执行顺序对于调试中间件问题、优化性能和确保安全至关重要,你可以使用 php artisan route:list 来查看每个路由的中间件执行顺序。
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播