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

Laravel7如何限制URL访问 仅允许用户访问自身数据

Laravel 7 全局修复水平越权的轻量方案

250余条路由不需要逐条修改,利用Laravel 7自带的授权能力,不到20行代码就能实现全站点数据归属校验,核心步骤如下:

  • 第一步:统一路由登录拦截
    先把所有需要登录访问的路由收拢到auth中间件分组下,拦截未登录的访客请求,不需要调整单条路由的业务逻辑:

    // routes/web.php
    Route::middleware(['auth'])->group(function () {
        // 所有需要登录后访问的路由全部放到这个分组内,包括你提到的records编辑、删除路由
        Route::get('/records/edit/{record}', 'RecordController@edit');
        // 其余200余条路由保持原有定义即可
    });
    
  • 第二步:用策略类(Policy)自动校验数据归属
    这是解决越权最核心的步骤,不需要在每个控制器方法里重复写权限判断,策略类会自动拦截对应模型的访问请求,校验当前登录用户是否为数据创建者。

    1. 执行Artisan命令生成对应业务模型的策略类,以你提到的records数据对应Record模型为例:
      php artisan make:policy RecordPolicy --model=Record
      
    2. 打开生成的app/Policies/RecordPolicy.php,写入对应操作的校验规则,所有需要控制权限的操作(查看、编辑、删除)都判断数据归属的user_id是否和当前登录用户ID一致:
      <?php
      namespace App\Policies;
      
      use App\Record;
      use App\User;
      use Illuminate\Auth\Access\HandlesAuthorization;
      
      class RecordPolicy
      {
          use HandlesAuthorization;
      
          public function view(User $user, Record $record)
          {
              return $user->id === $record->user_id;
          }
      
          public function update(User $user, Record $record)
          {
              return $user->id === $record->user_id;
          }
      
          public function delete(User $user, Record $record)
          {
              return $user->id === $record->user_id;
          }
      }
      
    3. 在app/Providers/AuthServiceProvider.php中完成模型和策略的绑定:
      protected $policies = [
          Record::class => RecordPolicy::class,
      ];
      
    4. 在对应控制器的构造方法中加一行代码,开启控制器方法的自动授权,不需要在每个方法单独写校验逻辑:
      // app/Http/Controllers/RecordController.php
      public function __construct()
      {
          $this->authorizeResource(Record::class, 'record');
      }
      
    5. 列表页查询直接加归属过滤,从源头避免用户看到他人数据:
      // 列表查询时不要用全量查询,只查当前用户自己创建的数据
      $records = Record::where('user_id', auth()->id())->paginate(10);
      
  • 第三步:全局兜底校验(可选,适配零散路由)
    如果存在部分路由没有做路由模型绑定、零散分布不好收拢,可以写一个全局中间件做兜底:

    1. 执行命令生成中间件:
      php artisan make:middleware CheckDataOwner
      
    2. 在中间件逻辑中统一拦截带模型参数的请求,校验归属:
      public function handle($request, Closure $next)
      {
          // 适配所有带模型绑定参数的路由,只要数据存在user_id字段就自动校验
          foreach ($request->route()->parameters() as $param) {
              if (is_object($param) && isset($param->user_id) && $param->user_id != auth()->id()) {
                  abort(403, '无权访问该内容');
              }
          }
          return $next($request);
      }
      
    3. 把这个中间件注册到app/Http/Kernel.php的web中间件组中,所有web请求会自动走校验,不需要修改路由定义。

注意:不要通过前端隐藏编辑、删除按钮的方式做权限控制,前端展示控制仅做体验优化,所有权限校验必须在后端完成,否则用户直接输入URL就能绕过限制。

如果站点还有其他业务模型(比如文章、评论、附件等),只需要给每个模型生成对应的策略类,复用同样的user_id校验逻辑即可,整体工作量极低,完全不需要重构现有业务代码。

内容的提问来源于stack exchange,提问作者Shan Md Shazarul Haque 171-15-

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.28 16:18:21