Laravel Sanctum provides a featherweight authentication system for SPAs (single page applications), mobile applications, and simple, token based APIs. Sanctum allows each user of your application to generate multiple API tokens for their account. These tokens may be granted abilities / scopes which specify which actions the tokens are allowed to perform.
— Laravel Docs
I always seem to need a refresher when I need token auth with Sanctum so I’m writing this here for easy reference.
Installation & Setup
Refer to the laravel docs for initial setup
Controller Structure
php artisan make:controller AuthController
class AuthController extends Controller
{
public function register(Request $request) {
$fields = $request->validate([
// Validation
]);
$fields = $request->all();
$fields['password'] = bcrypt($fields['password']);
$user = User::create($fields);
$token = $user->createToken('whateverYouWant')->plainTextToken;
$response = [
// Instead of sending the complete user
// you should send specific properties
'user' => $user,
'token' => $token
];
return response($response, 201);
}
public function login(Request $request) {
$fields = $request->validate([
'email' => 'required|string',
'password' => 'required|string'
]);
// Check email
$user = User::where('email', $fields['email'])->first();
// Check password
if(!$user || !Hash::check($fields['password'], $user->password)) {
return response([
'message' => 'Bad credentials.'
], 401);
}
// Delete all other tokens if you want
// $user->tokens()->delete();
$token = $user->createToken('whateverYouWant')->plainTextToken;
$response = [
// Again, instead of sending the complete user
// you should send specific properties
'user' => $user,
'user' => $user,
'token' => $token
];
return response($response, 200);
}
public function logout(Request $request) {
// Revoke the token that was used to authenticate the current request...
$request->user()->currentAccessToken()->delete();
return [
'message' => 'Logged out',
];
}
public function logoutAllDevices(Request $request) {
// Revoke all tokens...
$request->user()->tokens()->delete();
return [
'message' => 'Logged out all devices',
];
}
}
Auth Routes
Route::post('/register', [AuthController::class, 'register']);
Route::post('/login', [AuthController::class, 'login']);
Route::group(['middleware' => ['auth:sanctum']], function () {
Route::post('/logout', [AuthController::class, 'logout']);
});
Gotchas
Server side CORS might be an issue. So remember to add this to app/config/cors.php
'supports_credentials' => true,
On the client-side (using axios for example)
axios.defaults.withCredentials = true;