Search code examples
laravel-8laravel-sanctumlaravel-api

Creating auth tokens for a custom model that is not the default User model


How do I create access/api/auth tokens for a different model? From most questions, docs, or tutorials, most are using the default User model.

I read the default doc but it doesn't really say where to substitute the default Model class or how to verify against non-Model classes.

Any suggestions?


Solution

  • To use a different model than User for Laravel Sanctum API authentication.

    This is for Laravel 8.

    1. Create new model, php artisan make:model ModelName -m

      1. the flag m is used to instantiate a migration file for this model.
    2. Go to the Model class file and extend it with Illuminate\Foundation\Auth\User, ensure it uses HasApiTokens, and list out your fillable fields for record creation.

      ...
      use Illuminate\Foundation\Auth\User as Authenticatable;
      
      class ModelName extends Authenticatable{
          use ..., HasApiTokens;
          protected $fillable = [...]
      }
      
    3. Go to config/auth.php and add new provider and new guard.

    'guards' => [
            ...
                    ,
            'api' => [
                'driver' => 'sanctum',
                'provider' => 'model-name',
                'hash' => false,
            ]
            ],
    
    'providers' => [
            ...
                    ,
            'model-name' => [
                'driver' => 'eloquent',
                'model' => App\Models\ModelName::class,
                    ]
            ]
    
    1. Go to your api routes and wrap your routes as below.
    Route::middleware(['auth:sanctum'])->group(function(){
        Route::get('/whatever-route-name',function(){
           return 'Authenticated';
        });
    });
    
    1. Download Postman or your favored API testing tool, send a GET request to [http://localhost:8000/api/whatever-route-name](http://localhost:8000/api/whatever-route-name) , in Headers, ensure Accept has a value of applcation/json, send the request, and it should return an {”message”: “Unauthenticated.”}
    2. Go to your public routes, create a dummy route to create a record for ModelName
    3. After creation ensure that you call $model_name→createToken($model_name→whatever_field)→plaintTextToken; to get the plain text api key.
    4. Go to back to your API test tool, under Authorization, choose Bearer Token and supply the api key returned from above.
    5. The route wrapped in auth:sanctum is now accessible.