Laravel 11 中间件必须在 bootstrap/app.php 中显式注册:全局中间件通过 withMiddleware()->web()、->api() 等声明,路由中间件须先 alias 再使用;移除 Kernel.php 和 $routeMiddleware 自动映射,web/api 不再支持参数,未声明即报错或静默失效。

Laravel 11 对中间件的注册和使用方式做了结构性调整,核心是统一收口、显式声明、移除自动映射。如果你从 Laravel 10 升级到 11,中间件相关改动不是“微调”,而是必须重写配置逻辑,否则会直接报错或静默失效。
全局中间件不再写在 Kernel.php,全部移到 bootstrap/app.php
Laravel 11 彻底删除了 app/Http/Kernel.php 文件。所有全局中间件(包括原 $middleware、$middlewareGroups['web']、$middlewareGroups['api'])必须在 bootstrap/app.php 的 withMiddleware() 闭包中定义:
-
$middleware->use([...]):添加每次请求都执行的中间件(如日志、CSP 头) -
$middleware->web([...]):替代旧版web中间件组,需显式传入数组(可为空) -
$middleware->api([...]):同理,用于 API 路由链,不包含认证逻辑
⚠️ 注意:
$middlewareGroups已被框架内置且不可覆盖;不能再自定义中间件组名(如'admin' => [...]),也不能在web()或api()里塞带参数的中间件(如throttle:60,1)。
路由中间件必须先 alias,再使用
Laravel 10 中通过 $routeMiddleware 数组声明别名后,路由里直接写 ->middleware('auth') 就能用。Laravel 11 废除了该机制:
- 必须在
bootstrap/app.php的withMiddleware()中显式 alias:$middleware->alias([ 'auth' => \App\Http\Middleware\Authenticate::class, 'throttle' => \Illuminate\Routing\Middleware\ThrottleRequests::class, ]); - 然后才能在路由或控制器中使用字符串别名:
Route::get('/profile', [ProfileController::class, 'show'])->middleware('auth'); - ❌ 不再支持直接传类名(如
->middleware(\App\Http\Middleware\Authenticate::class)),会提示 “Undefined middleware”。
web/api 不再是“魔法字符串”,而是执行链入口
->middleware('web') 在 Laravel 11 中不再是靠配置驱动的别名,而是等价于展开你写在 $middleware->web([...]) 里的全部中间件。它的作用只是触发那一整条预设链,不能混用参数或动态组合。
- ✅ 正确:
->middleware(['auth', 'throttle:api']) - ❌ 错误:
->middleware('web')->middleware('throttle:api')(重复执行 web 链,且 throttle 会被忽略) - ❌ 错误:
->middleware('web:throttle')(不支持参数)
常见错误与修复建议
- 还在
config/app.php的'providers'里手动加RouteServiceProvider→ 报 “Provider already registered” → 删掉 - 路由写了
->middleware('web')却没在bootstrap/app.php中调用$middleware->web([])→ 中间件完全不执行,且php artisan route:list不报错,极难排查 → 补全 web() 和 api() 调用 - 沿用
Route::group(['middleware' => 'web'], ...)写法 → Laravel 11 不再识别这种数组语法 → 改用Route::middleware('web')->group(...) - 自定义中间件类里还用
$next($request)返回响应 → Laravel 11 推荐返回$next($request)->withHeaders(...)等链式调用,更安全
不复杂但容易忽略











