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

Laravel调用hasPermissionTo()报空对象错误求助

排查Laravel中Call to a member function hasPermissionTo() on null错误

我在配置Spatie Laravel Permission实现角色与权限管理时,遇到了如下致命错误:

(1/1) FatalErrorException Call to a member function hasPermissionTo() on null in ClearanceMiddleware.php line 17

我的数据库权限相关表结构如下:
数据库权限表截图

当前使用的ClearanceMiddleware代码如下:

<?php
namespace App\Http\Middleware;
use Closure;
use Illuminate\Support\Facades\Auth;
class ClearanceMiddleware {
    /**
     * Handle an incoming request.
     *
     * @param \Illuminate\Http\Request $request
     * @param \Closure $next
     * @return mixed
     */
    public function handle($request, Closure $next) {
        if (Auth::user()->hasPermissionTo('Administer roles & permissions')) //If user has this permission
        {
            return $next($request);
        }
        if ($request->is('posts/create'))//If user is creating a post
        {
            if (!Auth::user()->hasPermissionTo('Create Post')) {
                abort('401');
            } else {
                return $next($request);
            }
        }
        if ($request->is('posts/*/edit')) //If user is editing a post
        {
            if (!Auth::user()->hasPermissionTo('Edit Post')) {
                abort('401');
            } else {
                return $next($request);
            }
        }
        if ($request->isMethod('Delete')) //If user is deleting a post
        {
            if (!Auth::user()->hasPermissionTo('Delete Post')) {
                abort('401');
            } else {
                return $next($request);
            }
        }
        return $next($request);
    }
}

问题原因分析

这个错误的核心是**Auth::user()返回了null**——也就是说,当这个中间件执行时,当前请求并没有已登录的用户,直接调用hasPermissionTo()自然会触发报错。

解决步骤

  • 调整中间件执行顺序
    Laravel的中间件是按注册顺序执行的,你的ClearanceMiddleware必须放在Authenticate(登录验证)中间件之后。打开app/Http/Kernel.php,检查$middlewareGroups里的web组,确保Authenticate中间件先于ClearanceMiddleware执行;如果是路由单独绑定中间件,也要确保路由同时绑定了auth中间件和你的权限中间件,比如:

    Route::resource('posts', PostController::class)->middleware(['auth', 'clearance']);
    
  • 在中间件内先校验用户登录状态
    在ClearanceMiddleware的handle方法最开头,先判断用户是否已登录,未登录则引导到登录页或者返回未授权响应:

    public function handle($request, Closure $next) {
        // 先检查用户是否登录
        if (!Auth::check()) {
            // 普通web应用跳转到登录页
            return redirect()->route('login');
            // 如果是API接口,返回JSON格式的未授权响应
            // return response()->json(['message' => 'Unauthorized'], 401);
        }
    
        // 原有的权限检查逻辑...
    }
    
  • 检查路由配置
    确认所有应用了ClearanceMiddleware的路由,都是需要用户登录才能访问的页面/接口。如果有公开路由错误绑定了这个中间件,就会触发这个错误。

  • 可选:使用空安全运算符(PHP 8+)
    如果你使用的是PHP 8及以上版本,可以用空安全运算符来避免直接调用null的方法,但这只是临时规避错误,还是建议先确保用户已登录再做权限检查:

    if (Auth::user()?->hasPermissionTo('Administer roles & permissions'))
    

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.28 04:24:03