You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Laravel 5.5 利用中间件基于角色权限实现路由保护

Laravel 5.5 多级会员路由保护方案

嘿,我来帮你搞定这个Laravel 5.5的路由权限保护问题~你之前用if语句的思路虽然能跑,但确实不够优雅也不好维护,Laravel本身提供了更标准的解决方案——中间件,这也是处理路由权限的最佳实践,我给你详细拆解几个可行的方案:

方案一:针对管理员的专属中间件(最简单直接)

如果只是需要保护管理员(role_id=2)的路由,专门写一个管理员验证中间件就够了:

1. 创建中间件

在终端执行命令生成中间件文件:

php artisan make:middleware CheckAdmin

打开生成的 app/Http/Middleware/CheckAdmin.php,写入权限验证逻辑:

<?php

namespace App\Http\Middleware;

use Closure;
use Illuminate\Support\Facades\Auth;

class CheckAdmin
{
    public function handle($request, Closure $next)
    {
        // 先判断用户是否已登录
        if (!Auth::check()) {
            return redirect('/login'); // 未登录直接跳转到登录页
        }

        $currentUser = Auth::user();

        // 验证用户是否是管理员(role_id=2)
        if ($currentUser->role_id !== 2) {
            // 非管理员跳回首页,还可以加个错误提示
            return redirect()->route('home')->with('error', '抱歉,你没有访问该页面的权限');
        }

        // 验证通过,继续请求
        return $next($request);
    }
}

2. 注册中间件

打开 app/Http/Kernel.php,在 $routeMiddleware 数组里添加这个中间件的别名:

protected $routeMiddleware = [
    // 保留原来的其他中间件...
    'admin' => \App\Http\Middleware\CheckAdmin::class,
];

3. 给路由添加保护

现在你可以在 web.php 里给管理员路由分组,直接用这个中间件:

// 所有管理员专属路由都放在这个组里
Route::middleware('admin')->group(function () {
    Route::get('/admin','AdminController@index')->name('admin');
    // 后续新增的管理员路由都可以加在这里,不用重复写判断
});

方案二:通用角色验证中间件(支持多角色)

如果需要给不同角色(比如所有者1、版主3)都做路由保护,写一个通用的中间件更灵活:

1. 创建通用角色中间件

执行命令生成中间件:

php artisan make:middleware CheckRole

编辑 app/Http/Middleware/CheckRole.php,实现支持多角色参数的逻辑:

<?php

namespace App\Http\Middleware;

use Closure;
use Illuminate\Support\Facades\Auth;

class CheckRole
{
    public function handle($request, Closure $next, ...$allowedRoles)
    {
        if (!Auth::check()) {
            return redirect('/login');
        }

        $userRole = Auth::user()->role_id;

        // 检查用户角色是否在允许的列表里
        if (!in_array($userRole, $allowedRoles)) {
            return redirect()->route('home')->with('error', '权限不足,无法访问');
        }

        return $next($request);
    }
}

2. 注册中间件

同样在 Kernel.php 的 $routeMiddleware 里添加:

protected $routeMiddleware = [
    // ...其他中间件
    'role' => \App\Http\Middleware\CheckRole::class,
];

3. 灵活使用路由保护

现在你可以给不同路由指定允许的角色:

// 所有者(1)和管理员(2)都能访问的路由组
Route::middleware('role:1,2')->group(function () {
    Route::get('/admin','AdminController@index')->name('admin');
    Route::get('/owner-dashboard','OwnerController@index')->name('owner.dashboard');
});

// 只有版主(3)能访问的路由
Route::get('/mod-panel','ModController@index')->name('mod.panel')->middleware('role:3');

额外处理:封禁用户(role_id=4)的拦截

针对封禁用户,最好做一个全局中间件,确保他们无法访问任何内容:

1. 创建封禁检查中间件

php artisan make:middleware CheckBanned

编辑 app/Http/Middleware/CheckBanned.php:

<?php

namespace App\Http\Middleware;

use Closure;
use Illuminate\Support\Facades\Auth;

class CheckBanned
{
    public function handle($request, Closure $next)
    {
        if (Auth::check() && Auth::user()->role_id === 4) {
            Auth::logout(); // 强制退出封禁用户
            return redirect('/login')->with('error', '你的账号已被封禁,无法登录');
        }

        return $next($request);
    }
}

2. 注册为全局中间件

打开 Kernel.php,把这个中间件加到 $middleware 数组里(全局中间件会拦截所有请求):

protected $middleware = [
    // ...原来的全局中间件
    \App\Http\Middleware\CheckBanned::class,
];

为什么不推荐你原来的if写法?

直接在路由文件里写if判断虽然能临时解决问题,但当路由越来越多的时候,代码会变得杂乱不堪,而且权限逻辑分散在路由文件里,后续修改或扩展会非常麻烦。用中间件的话,权限逻辑集中在一个地方,维护和扩展都更方便,也符合Laravel的设计规范。

如果后续需要更细粒度的权限控制(比如某个控制器方法的权限),还可以结合Laravel的Gate和Policy来实现,但路由级别的保护用中间件就足够简单高效了。

内容的提问来源于stack exchange,提问作者daugaard47

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.25 04:23:10