Laravel Sanctum can be use Multiauth guard
Asked Answered
C

8

13

I'm testing with laravel sanctum but here some issues.. I'm creating Admin guard.

enter image description here

When I change the middleware to auth:sanctum_admin.. it should be only can access by admin but here I can access with normal user account with web guard. I don't know why?...I used passport with multiauth package.it's fine. but here in sanctum can't be separate User Table and Admin.

Czardom answered 12/4, 2020 at 11:24 Comment(0)
S
12

You can, also use multiple guards in sanctum. To achieve this, follow these steps -

  1. Create your own guard as required. (In config/auth.php)
'guards' => [
        'web' => [
            'driver' => 'session',
            'provider' => 'users',
        ],

        'api' => [
            'driver' => 'token',
            'provider' => 'users',
            'hash' => false,
        ],

        'admin' => [
            'driver' => 'session',
            'provider' => 'admins',
        ]
    ],
  1. Set providers. (In config/auth.php)
'providers' => [
       'users' => [
           'driver' => 'eloquent',
           'model' => App\User::class,
       ],

       'admins' => [
           'driver' => 'eloquent',
           'model' => App\Admin::class,
       ],
   ],
  1. Use this guard when you authenticate a user. (In route file)
    if(auth()->guard('admin')->attempt($request->only('email','password')))
    {
        return auth()->guard('admin')->user();
    }
    
Surat answered 9/5, 2020 at 18:45 Comment(2)
Welcome! Thanks for the contribution. Can I ask that you copy the code from the images and place them into the markdown? We try to avoid screenshots of code on Stack Overflow because they're hard for other users to copy and paste from and they don't show up in search results (e.g., if someone is searching by keywords in them).Declarative
Driver should be 'sanctum' in auth config.Regatta
I
8

@Abhishek Mitra

and for authorizatioin using Laravel Sanctum in case of Multiple Auth Guard, we can use middleware as such

Route::middleware(['auth:guard_name'])->get('/user', function(){
    return auth()->guard('guard_name')->user();
}
Ioyal answered 19/5, 2020 at 7:1 Comment(0)
B
8

config/auth.php

driver is sanctum

'guards' => [
    'users' => [
        'driver' => 'sanctum',
        'provider' => 'users',
    ],

    'partners' => [
        'driver' => 'sanctum',
        'provider' => 'partners',
    ],

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

        ],

provider:

providers' => [
    'users' => [
        'driver' => 'eloquent',
        'model' => App\Models\User::class,
    ],

    'partners' => [
        'driver' => 'eloquent',
        'model' => App\Models\Partner::class,
    ],

    'admins' => [
        'driver' => 'eloquent',
        'model' => App\Models\Admin::class,
    ],
],

model:

must be add Authenticatable

<?php

namespace App\Models;

use Illuminate\Contracts\Auth\MustVerifyEmail;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable;

class Admin extends Authenticatable
{
    use HasFactory, Notifiable;

    /**
     * The attributes that are mass assignable.
     *
     * @var array
     */
    protected $fillable = [
        'name',
        'email',
        'password',
    ];

    /**
     * The attributes that should be hidden for arrays.
     *
     * @var array
     */
    protected $hidden = [
        'password',
        'remember_token',
    ];

    /**
     * The attributes that should be cast to native types.
     *
     * @var array
     */
    protected $casts = [
        'email_verified_at' => 'datetime',
    ];
}

Middleware:

Route::middleware(['auth:admin'])->get('/user', function(){
   
}

Guard:

auth()->guard('admin')->user();

Unauthenticated user message:

In app/Exceptions/Handler.php

use Illuminate\Auth\AuthenticationException;

function:

protected function unauthenticated($request, AuthenticationException $exception)
    {
       return response()->json(['message' => 'Unauthenticated.'], 401);

}

or

custom guard and custom redirect

public function render($request, Exception $exception)
{
    $class = get_class($exception);

    switch($class) {
        case 'Illuminate\Auth\AuthenticationException':
            $guard = array_get($exception->guards(), 0);
            switch ($guard) {
                case 'admin':
                    $login = 'admin.login';
                    break;
                default:
                    $login = 'login';
                    break;
            }

            return redirect()->route($login);
    }

    return parent::render($request, $exception);
}
Brittain answered 27/2, 2021 at 5:4 Comment(1)
'driver' => 'sanctum' Guard Works for me. Thanks @ßãlãjîVincevincelette
A
1
  1. you must add your custom guard in config/auth.php.

'guards' => [

    'web' => [
        'driver' => 'session',
        'provider' => 'users',
    ],

    'custom-guard' => [
        'driver' => 'session',
        'provider' => 'custom-provider',
    ]
],

be careful, the driver in custom guard must be session. and set provider as:

'providers' => [
   'users' => [
       'driver' => 'eloquent',
       'model' => App\User::class,
   ],

   'custom-provider' => [
       'driver' => 'eloquent',
       'model' => App\CustomProvider::class,
   ],

], the App\CustomProvider::class must be the model. after that can easily use the guard in auth.

auth('custom-guard')->user()
Any answered 31/8, 2021 at 4:50 Comment(0)
H
1

In config/auth.php:

'guards' => [
    ...

    'api' => [
        'driver' => 'sanctum',
        'provider' => 'users',
    ],
],

(Tested in Laravel 9.x)

Hackberry answered 31/3, 2022 at 8:9 Comment(0)
G
1

Defining API sanctum guards using the sanctum driver

'guards' => [
        // Web Guards
        'web' => [
            'driver' => 'session',
            'provider' => 'users',
        ],

        //API Sanctum Guards
        'admin-api' => [
            'driver' => 'sanctum',
            'provider' => 'admins',
        ],
        'vendor-api' => [
            'driver' => 'sanctum',
            'provider' => 'vendors',
        ],
    ],

Defining Providers

'providers' => [
    'users' => [
        'driver' => 'eloquent',
        'model' => App\Models\User::class,
    ],
    'admins' => [
        'driver' => 'eloquent',
        'model' => App\Models\Admin::class,
    ],
    'vendors' => [
        'driver' => 'eloquent',
        'model' => App\Models\Vendor::class,
    ],
],

Generating Token

$user = Admin::where('email', $request->email)->first();
$token = $user->createToken(uniqid());
return ['token' => $token->plainTextToken];


$user = Vendor::where('email', $request->email)->first();
$token = $user->createToken(uniqid());
return ['token' => $token->plainTextToken];

Protecting Routes using sanctum guard

Route::middleware('auth:admin-api')->get('/admin', function (Request $request) {
    return $request->user();
});

Route::middleware('auth:vendor-api')->get('/vendor', function (Request $request) {
    return $request->user();
});
Grandeur answered 4/1, 2023 at 14:7 Comment(1)
member' => [ 'driver' => 'sanctum', 'provider' => 'members' ], it throw error { "message": "Xdebug has detected a possible infinite loop, and aborted your script with a stack depth of '256' frames", } Route::middleware('auth:member')->get('/manage-profile', function (Request $request) { return $request->user(); });Africanist
V
0

I also face the same issue and solved it by following -

  1. In auth.php add an extra Guard - front
    'guards' => [
        'web' => [
            'driver' => 'session',
            'provider' => 'users',
        ],
        'front' => [
            'driver' => 'session',
            'provider' => 'members',
        ],
    ],
    'providers' => [
        'users' => [
            'driver' => 'eloquent',
            'model' => Vanguard\User::class,
        ],

        'members' => [
             'driver' => 'eloquent',
             'model' => Vanguard\Member::class,
        ],
    ],
  1. Log in as a Default User or Member
/** Default Guard**/
if (Auth::attempt(['username' => $credentials['username'], 'password' => $credentials['password']], $request->get('remember'))) {
}
/** Front Guard **/
if (Auth::guard('front')->attempt(['username' => $credentials['username'], 'password' => $credentials['password']], $request->get('remember'))) {
}

  1. Finally add the Guard in sanctum.php
'guard' => ['front','web']
Vincevincelette answered 11/4, 2022 at 6:37 Comment(0)
P
-1

I think the default guard should be like this:

'defaults'{
    'guard' : "sanctum_admin",
    'passwords': 'admins',
}

Or

'defaults'{
    'guard' : 'web',
    'passwords' : 'users',
}
Photoelectric answered 18/4, 2020 at 5:40 Comment(0)

© 2022 - 2025 — McMap. All rights reserved.