php - Laravel Sanctum 自定义守卫

标签 php laravel

我的 laravel 应用程序中有多个 guard :

代码 config/auth.php :

'defaults' => [
    'guard' => 'user',
    'passwords' => 'users',
],

'guards' => [
    'user' => [
        'driver' => 'token',
        'provider' => 'users',
        'hash' => true,
    ],
    'admin' => [
        'driver' => 'token',
        'provider' => 'admins',
        'hash' => true,
    ]
],

'providers' => [
    'users' => [
        'driver' => 'eloquent',
        'model' => User::class,
    ],
    'admins' => [
        'driver' => 'eloquent',
        'model' => Admin::class,
    ],
],

'passwords' => [
    'users' => [
        'provider' => 'users',
        'table' => 'users_password_resets',
        'expire' => 60,
        'throttle' => 60,
    ],
    'admins' => [
        'provider' => 'admins',
        'table' => 'admins_password_resets',
        'expire' => 60,
        'throttle' => 60,
    ],
],

'password_timeout' => 10800,

并且在 api.php 中有获取经过身份验证的用户的路由:
Route::get('admins/auth/user', 'AuthController@user')->middleware('auth:sanctum');

同样在我的模型(管理员,用户)中使用了特征:
Laravel\Sanctum\HasApiTokens
当我尝试通过 token 获取身份验证用户时,会出现错误消息:
InvalidArgumentException: Auth guard [web] is not defined. in file appname\vendor\laravel\framework\src\Illuminate\Auth\AuthManager.php on line 84

#0 appname\vendor\laravel\framework\src\Illuminate\Auth\AuthManager.php(68): Illuminate\Auth\AuthManager->resolve()
#1 appname\vendor\laravel\sanctum\src\Guard.php(45): Illuminate\Auth\AuthManager->guard()
#2 [internal function]: Laravel\Sanctum\Guard->__invoke()
#3 appname\vendor\laravel\framework\src\Illuminate\Auth\RequestGuard.php(58): call_user_func()
#4 appname\vendor\laravel\framework\src\Illuminate\Auth\GuardHelpers.php(60): Illuminate\Auth\RequestGuard->user()
#5 appname\vendor\laravel\framework\src\Illuminate\Auth\Middleware\Authenticate.php(63): Illuminate\Auth\RequestGuard->check()
#6 appname\vendor\laravel\framework\src\Illuminate\Auth\Middleware\Authenticate.php(42): Illuminate\Auth\Middleware\Authenticate->authenticate()

我已经运行了命令:
php artisan cache:clear
php artisan config:cache

并且还尝试将 guard 名称添加到 config/sanctum.php :
'stateful' => explode(',', env('SANCTUM_STATEFUL_DOMAINS', 'localhost,127.0.0.1')),

'expiration' => null,

'middleware' => [
    'verify_csrf_token' => App\Http\Middleware\VerifyCsrfToken::class,
    'encrypt_cookies' => App\Http\Middleware\EncryptCookies::class,
],

// This line added
'guard' => 'admin'

最佳答案

我解决了类似的问题,因为我对用户和管理员用户使用身份验证。
您可以使用 sanctum 使用中间件('auth: sanctum')通过 laravel/ui 包对自己进行身份验证,但要使其使用 ADMIN 模型而不是 USER,您必须更改 guard 。
让我解释一下:sanctum 通常是 auth 中定义的守卫,'web' 和 'api' 也是如此,默认情况下 auth.guards.sanctum 的 provider = null。所以我所做的就是定义我自己的守卫:

'providers' => [
'admin' => [
            'driver' => 'sanctum',
            'provider' => 'admins',
        ],
],

'providers' => [
'admins' => [
            'driver' => 'eloquent',
            'model' => App \ Models \ Admin :: class,
        ],
],
您可以使用中间件保护您的路线('auth: sanctum')
并且通过这种方式,您使用的是 Admin 模型而不是 User 模型。
每次在您使用 auth: sanctum 保护的组内调用路由时,此 auth.guard 将绑定(bind)到 providers.admins,这将始终验证 Admin 模型。
您将遇到的问题是,当您登录时,您必须定义登录时要使用的守卫,因为如果您使用 laravel/ui 包,默认情况下使用守卫。 web 并且这将关联 User 模型,尽管在 User 模型中有一个具有相同凭据的用户,但当他访问受 sanctum 保护的路径时,他将使用 Admin 模型验证凭据。
所以诀窍是,在登录时,强制将守卫更改为具有提供者 Admin 的守卫。
就我而言,我所做的是创建一个中间件,它所做的是更改guards.web 的提供者
创建中间件,我在routeMiddleware的kernel.php文件中注册了,这样放:
'auth.admin' => \ App \ Http \ Middleware \ AuthenticateGuardAdmin :: class,
并且中间件包含在这行代码中:
配置::set ('auth.guards.web.provider', 'admins');
我把它放在这里的中间件:
Route :: middleware ('auth.admin') -> group (function () {
    Auth :: routes (['register' => false]);
    Route :: middleware ('auth: sanctum') -> group (function () {
        Route :: get ('/ home', 'HomeController @ index') -> name ('home');
    });
});
在使用 laravel/ui 包的标准 Controller 登录时,我已经告诉配置变量将使用的提供程序将是我定义的使用 Admin 模型的提供程序。
有了这个,登录、身份验证和授权总是使用 Admin 模型完成。
之后,您甚至可以使用其他身份验证定义和其他模型或相同的默认用户模型创建其他路由组,甚至可以使用 API 路由或 Web 路由中的 sanctum。

关于php - Laravel Sanctum 自定义守卫,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62359429/

相关文章:

php - 如何获得集合中元素的所有可能组合? (电源组)

php - 如何用MySQL过滤正确的订单(一个订单包含多行)

php - Laravel:类似系统实现的错误

laravel - 更改 Nova 资源的资源 URL

php - 在 Laravel 5 迁移中更新表并添加数据

php - 无法为序列化准备路由 [api/user]。使用闭包

php - Paypal IPN 脚本/MySql 插入查询问题

php - count 和 sizeof 有什么区别?

PHP - 最高效的字典代码

php - 在 ubuntu 中安装 laravel 时出现错误