Here’s a comprehensive, up-to-date step-by-step tutorial for setting up and using Laravel Passport (OAuth2 API authentication) with clear explanations, working code samples, and troubleshooting tips—suitable for local XAMPP and production environments.
Laravel Passport Full Tutorial (2025)
1. What is Laravel Passport?
Laravel Passport provides a full OAuth2 server implementation for your Laravel application in minutes.
It’s used when you want to secure your API endpoints (e.g., for microservices or mobile/web clients) with OAuth2—supporting access tokens, refresh tokens, personal access, and password grants.
2. Requirements
- Laravel 10 or 11+
- PHP 8.1+
- Composer
- MySQL/SQLite (or any supported DB)
- mod_rewrite enabled on Apache (XAMPP)
3. Installation Steps
a. Install Passport
composer require laravel/passport
Code language: JavaScript (javascript)
b. Run Passport Install
This will generate encryption keys, migration files, and optional clients.
php artisan passport:install
Code language: CSS (css)
If prompted, let it run migrations.
If you skip, runphp artisan migrate
manually.
Common Issues:
- If you see “encryption keys already exist,” use
--force
. - If tables already exist, clear your DB or delete
oauth_*
tables and re-migrate.
c. Publish Config (optional)
php artisan vendor:publish --tag=passport-config
4. Configure Laravel
a. Service Provider
If using Laravel 10+, this is automatic.
If not, add in config/app.php
under providers
:
Laravel\Passport\PassportServiceProvider::class,
Code language: JavaScript (javascript)
b. Database Migrations
Run if not done already:
php artisan migrate
5. Set Up Auth in Laravel
a. In app/Models/User.php
use Laravel\Passport\HasApiTokens;
class User extends Authenticatable
{
use HasApiTokens, Notifiable;
//...
}
Code language: PHP (php)
b. In config/auth.php
Set api
driver to passport
:
'guards' => [
'api' => [
'driver' => 'passport',
'provider' => 'users',
],
],
Code language: PHP (php)
c. In app/Providers/AuthServiceProvider.php
use Laravel\Passport\Passport;
public function boot()
{
$this->registerPolicies();
Passport::routes(); // Enables Passport routes
// Optionally, set token expiration here
}
Code language: PHP (php)
6. Create OAuth Clients
a. Client Credentials Grant (machine-to-machine, microservices):
php artisan passport:client --client
Code language: CSS (css)
- Note the
Client ID
andClient Secret
—you need them for token requests.
b. Password Grant (for username/password login):
php artisan passport:client --password
Code language: CSS (css)
c. Personal Access Client (for tokens not attached to users):
php artisan passport:client --personal
Code language: CSS (css)
7. Protect Your Routes
In routes/api.php
:
Route::middleware('auth:api')->get('/user', function (Request $request) {
return $request->user();
});
Code language: PHP (php)
Or for controller routes:
Route::middleware('auth:api')->group(function () {
Route::get('/orders', [OrderController::class, 'index']);
});
Code language: CSS (css)
8. How to Get a Token (Machine-to-Machine, Client Credentials Grant)
a. cURL Command:
curl -X POST "http://localhost/yourproject/oauth/token" \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "grant_type=client_credentials&client_id=YOUR_CLIENT_ID&client_secret=YOUR_CLIENT_SECRET"
Code language: JavaScript (javascript)
If using JSON:
curl -X POST "http://localhost/yourproject/oauth/token" \
-H "Content-Type: application/json" \
-d '{"grant_type":"client_credentials","client_id":"YOUR_CLIENT_ID","client_secret":"YOUR_CLIENT_SECRET"}'
Code language: JavaScript (javascript)
b. Example Response:
{
"token_type": "Bearer",
"expires_in": 31536000,
"access_token": "eyJ0eXA..."
}
Code language: JSON / JSON with Comments (json)
9. Use the Token in API Requests
Add as a Bearer token in your header:
curl -H "Authorization: Bearer ACCESS_TOKEN_HERE" http://localhost/yourproject/api/user
Code language: JavaScript (javascript)
Or with Guzzle in Laravel:
$response = Http::withToken($accessToken)->get('http://localhost/yourproject/api/user');
Code language: PHP (php)
10. Troubleshooting
a. 404 on /oauth/token
- Make sure you’re calling the public entry (e.g.,
/yourproject/oauth/token
). - Ensure
.htaccess
is standard and mod_rewrite is enabled. - Check Alias in Apache vhost (should point
/yourproject
topublic
folder). - Run
php artisan route:list | grep oauth
to confirm the route exists.
b. 405 Method Not Allowed
- You’re likely using the wrong HTTP verb (must be POST for
/oauth/token
). - Try hitting
/yourproject/index.php/oauth/token
to bypass .htaccess (diagnostic). - If this works, .htaccess or mod_rewrite is not working.
c. 403 Forbidden
- Check
.htaccess
for PHP file restrictions. - Ensure
AllowOverride All
is set in Apache config for your Directory. - Check permissions of the
public
folder.
d. Token not working
- Confirm your API route uses
auth:api
middleware. - Confirm correct guard in
config/auth.php
.
11. Environment Variables Best Practices
Separate internal and public URLs:
Add these in your .env
:
APP_URL=https://www.myhospitalnow.com/yourproject
INTERNAL_API_URL=http://localhost/yourproject
Code language: JavaScript (javascript)
In code:
$apiBase = env('INTERNAL_API_URL', config('app.url'));
$response = Http::post("$apiBase/oauth/token", [...]);
Code language: PHP (php)
12. Testing Everything
curl -I http://localhost/yourproject/
(should return 200 OK)curl -X POST .../oauth/token
(should return access token)curl -H "Authorization: Bearer ..." .../api/user
(should return user info)php artisan route:list | grep oauth
(should show token route)- Check your logs for errors.
13. Production Tips
- Use HTTPS for public endpoints.
- Never expose your
.env
or sensitive client secrets. - Restrict token scopes to only what’s necessary.
- Rotate client secrets if leaked.
14. References
Want to see a Dockerized version, multi-service microservices setup, or real-world client integration code? Just ask!
Let me know if you want a production deployment checklist, more about securing microservices, or a walkthrough for specific grant types (password, auth code, etc.).
Laravel Passport on XAMPP: Debug Checklist
Routes Confirmed
You ran php artisan route:list
and see:
- POST oauth/token … passport.token
- (etc)
Problem
curl -I http://localhost/rajesh/
returns 200 OK.curl -X POST http://localhost/rajesh/oauth/token ...
returns 404 Not Found.
Next Steps
- Check .htaccess in
/opt/lampp/htdocs/myhospitalnow/rajesh/public
:- Should be standard Laravel version (see below).
- Check Apache Alias & Directory
- In your httpd-vhosts.conf or httpd.conf, you should have:
Alias /rajesh /opt/lampp/htdocs/myhospitalnow/rajesh/public <Directory /opt/lampp/htdocs/myhospitalnow/rajesh/public> Options Indexes FollowSymLinks AllowOverride All Require all granted </Directory>
- After editing, restart Apache.
- Test Index.php Direct Access
- Run:
curl -X POST http://localhost/rajesh/index.php/oauth/token ...
- If this works:
.htaccess
or mod_rewrite is not working.
- Check mod_rewrite is enabled
- Run:
apachectl -M | grep rewrite
- Should show
rewrite_module
.
- Check Directory Index
- Make sure your
/opt/lampp/htdocs/myhospitalnow/rajesh/public
hasindex.php
present and readable.
- Make sure your
- Check File Permissions
- Run
ls -al /opt/lampp/htdocs/myhospitalnow/rajesh/public
- Run
- If still stuck
- Post your
/opt/lampp/htdocs/myhospitalnow/rajesh/public/.htaccess
- Post your relevant Apache vhost/alias config.
- Post your
Sample .htaccess
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-f
RewriteRule ^ index.php [L]
</IfModule>
Code language: HTML, XML (xml)
Command
2099 composer create-project laravel/laravel rajesh
2100 cd rajesh/
2103 composer require laravel/passport
2104 php artisan passport:install
2107 php artisan migrate
2108 php artisan passport:client
2112 php artisan route:list | grep oauth
2113 vi /opt/lampp/etc/extra/httpd-localhost.conf
2114 /opt/lampp/lampp restart
2115 php artisan route:list | grep oauth
2119 curl -I http://localhost/rajesh/
2120 php artisan route:list
2121 ls public/.htaccess
2122 more public/.htaccess
2123 vi /opt/lampp/etc/extra/httpd-localhost.conf
2125 /opt/lampp/lampp restart
2126 curl -X POST "http://localhost/rajesh/oauth/token" -H "Content-Type: application/x-www-form-urlencoded" -d "grant_type=client_credentials&client_id=01981006-d7bd-72ad-b931-39a792643c83&client_secret=6q3yC4cCttUi28mAX6ITFocvOpkhyyWyKzX4eQVw"
2127 history
Code language: PHP (php)
I’m a DevOps/SRE/DevSecOps/Cloud Expert passionate about sharing knowledge and experiences. I have worked at Cotocus. I share tech blog at DevOps School, travel stories at Holiday Landmark, stock market tips at Stocks Mantra, health and fitness guidance at My Medic Plus, product reviews at TrueReviewNow , and SEO strategies at Wizbrand.
Do you want to learn Quantum Computing?
Please find my social handles as below;
Rajesh Kumar Personal Website
Rajesh Kumar at YOUTUBE
Rajesh Kumar at INSTAGRAM
Rajesh Kumar at X
Rajesh Kumar at FACEBOOK
Rajesh Kumar at LINKEDIN
Rajesh Kumar at WIZBRAND