Hello everyone, welcome back to justlaravel.com.
I am back with another tutorial, here I will show you how to integrate
Passport(a Laravel’s API authentication package) into your Laravel
applications.
Here I will create 2 Laravel projects, one is an API and other is the API consumer app. It basically means I will create an API with Passport package integrated. A normal Laravel app where I call the API and show its data.
Let’s get started!
Now, register the Passport service provider in the providers array of your
Now, run the following commands to setup passport, but before that setup database details in
The migrate command creates some default Laravel tables and some new tables for authentication which comes from passport.
Now run,
it creates some client id’s and secrets, which can be later used by consumer app to access the API.
Now, in the User model(
Next, we need to add some routes which passport uses, so in the
And finally, in
Now I will generate some random fake data so we can fill up the API with some data. We can use an inbuilt Laravel package
I will now create a copy of users table and fill that table with dummy users. Create a new
Let’s create a seeder for
In the Seeder file(
Now, in the Database seeder file(
Now, we can run the migrate command which fills us the database.
Its time to create a new controller named
In the controller(
Now if we run the application(
So when the registration form is submitted, a new user is created and also an OAuth client id and secret are generated for that user.
The route(
In the register function, I first save the user and then get its
Assume a case where the user is created and got an error in creating a record in oauth_clients table, in this case, there is a problem, so to avoid such situations there is a concept called Transactions and Atomicity property of the transaction is what we use here.
So the basic flow of operation looks like,
In the registration form, I check for some basic validations and then proceed to insert the user.
Now, in the else part, I will create a new user, enclosing with try catch block for rollback scenario.
After the user is created, I will get the inserted id to use it the oauth_clients table.
Now, there is some data to be inserted in oauth_clients table.
Secret – A random 40 character string
Name – Any name
Password Client – As it is password access client the value should be ‘1’
Personal Access Client – It should be 0 as it is a password client and not personal
Redirect – A redirect URL
Revoked – whether the client revoked the access or not, it should be ‘0’ as we need access to the API
So the insert query for oauth_clients will look as follows,
After successful insertion of both queries, I can use DB commit and give the user the required client id and secret.
The final register function looks as below.
Assuming the API we created is running at
I will call the url
As you see there are some
With the above call, we get an
Now, the obtained data is stored in some variable, so we can loop it and display the data accordingly.
So now when we open
So that’s it, guys! We have successfully created an API with passport authentication and also consumed that API in another application.
Here I will create 2 Laravel projects, one is an API and other is the API consumer app. It basically means I will create an API with Passport package integrated. A normal Laravel app where I call the API and show its data.
Let’s get started!
Laravel API
Passport Install
Passport Configure
Generate data – Faker | DB Seeding
Routing | Getting info from DB
Protect the routes with Passport
Registration and Generating OAuth client_id and client_secret
Consumer APP
Create a new App
Install GuzzleHttp
Authenticate the API and get the data
Display the data
Run the app
laravel new sampleAPI
Passport Install
Now, install the Passport package using composer,composer require laravel/passport
Now, register the Passport service provider in the providers array of your
config/app.php
file.Now, run the following commands to setup passport, but before that setup database details in
.env
file ordatabase.php
(app\config\database.php
) file.The migrate command creates some default Laravel tables and some new tables for authentication which comes from passport.
Now run,
it creates some client id’s and secrets, which can be later used by consumer app to access the API.
Passport Configure
Here we need to make some configuration changes to our Laravel app so Passport can be used in the API authentication.Now, in the User model(
app\User.php
) we need to add HasApiTokens
trait from Passport package,Next, we need to add some routes which passport uses, so in the
AuthServiceProvider<code>(</code>app/Providers/AuthServiceProvider.php
) add the below extra lines,And finally, in
auth.php
file(config/auth.php
), I will set the API driver to passport.Generate data – Faker | DB Seeding
As this is not a real API and just for tutorial purpose, I can stuff with some dummy data.Now I will generate some random fake data so we can fill up the API with some data. We can use an inbuilt Laravel package
Faker
to get us some data.I will now create a copy of users table and fill that table with dummy users. Create a new
details
table by running the following SQL query.Let’s create a seeder for
details
table, run the following command,In the Seeder file(
database\seeds\DetailsTableSeeder.php
), loop and create 250 random users, paste the following in the run()
function of the seeder.Now, in the Database seeder file(
database\seeds\DatabaseSeeder.php
), call this DetailsTableSeeder
Now, we can run the migrate command which fills us the database.
1
|
php artisan migrate --seed
|
Routing | Getting info from DB
Now, lets create a route to the controller which gets all the user data, so in the api routes(\routes\api.php
) place the following route.Its time to create a new controller named
DetailController
as used in the above route.In the controller(
app\Http\Controllers\DetailController.php
), lets create a function and fetch all the data from user table.Now if we run the application(
php artisan serve
) and go to route(http://127.0.0.1:8000/api/users
),
it will display us all the users, but the thing here is everyone can
see the details of the API, it just a normal app. An API needs
authentication, so now let us use the passport package we have installed
earlier.Protect the routes with Passport
Let’s protect the route which we created earlier for displaying the users. Open api.php file(routes\api.php
) and add middleware authentication to the route.
1
Route::get('users', 'UserController@index')->middleware('auth:api');
Now if we check the link(
Now, if any user wants to access our API, we need them to register to the API and then generate those client_id and client_secret for them so they can access the API.
For registration view, I used the basic files generated that comes from Laravel’s auth scaffolding. So I ran,
So make a new route in (
http://127.0.0.1:8000/api/users
), we are now unable to access the data as it is protected with the passport and it needs some authentication.Registration and Generating OAuth client_id and client_secret
So to access we need some client_id and client_secret, we have got some of these when I ranphp artisan passport:install
earlier and these are stored in a table called oauth_clients
.Now, if any user wants to access our API, we need them to register to the API and then generate those client_id and client_secret for them so they can access the API.
For registration view, I used the basic files generated that comes from Laravel’s auth scaffolding. So I ran,
php artisan make:auth
and removed all unnecessary files and kept only view files also removed its controllers and routes.So make a new route in (
routes\web.php
) calling the registration view.
1
2
3
|
Route::get('/register', function(){
return view('auth.register');
});
|
So when the registration form is submitted, a new user is created and also an OAuth client id and secret are generated for that user.
The route(
routes/web.php
),In the register function, I first save the user and then get its
id
and use it in oauth_clients
table. So as am dealing with one or more insertions for an operation, I
use a concept called DB Transactions, what this does is, it either
inserts in both of the tables or none of them. As I don’t need any sort
of incomplete operations here.Assume a case where the user is created and got an error in creating a record in oauth_clients table, in this case, there is a problem, so to avoid such situations there is a concept called Transactions and Atomicity property of the transaction is what we use here.
So the basic flow of operation looks like,
In the registration form, I check for some basic validations and then proceed to insert the user.
Now, in the else part, I will create a new user, enclosing with try catch block for rollback scenario.
After the user is created, I will get the inserted id to use it the oauth_clients table.
Now, there is some data to be inserted in oauth_clients table.
Secret – A random 40 character string
Name – Any name
Password Client – As it is password access client the value should be ‘1’
Personal Access Client – It should be 0 as it is a password client and not personal
Redirect – A redirect URL
Revoked – whether the client revoked the access or not, it should be ‘0’ as we need access to the API
So the insert query for oauth_clients will look as follows,
After successful insertion of both queries, I can use DB commit and give the user the required client id and secret.
The final register function looks as below.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
|
<?php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use DB;
use App\User;
use App\OAuthClient;
use Str;
use Validator;
use Redirect;
class PassportController extends Controller
{
public function register(Request $request)
{
DB::beginTransaction();
try {
$validator = Validator::make($request->all(),[
'name' => 'required|string',
'email' => 'required|string|email|unique:users',
'password' => 'required|string|confirmed'
]);
if ($validator->fails()) {
return Redirect::back()
->withErrors($validator)
->withInput();
}
else{
try {
$user_save = User::create([
'name' => $request->name,
'email' => $request->email,
'password' => bcrypt($request->password)
]);
}
catch(\Exception $e){
DB::rollback();
$message = $e->getMessage();
return response()->json(['error' => 1, 'message' => $message]);
}
}
$insertedId = $user_save->id;
$secret = Str::random(40);
try {
$oauth_clients = OAuthClient::create([
"user_id" => $insertedId,
"secret" => $secret,
"name" => "Password Grant",
"revoked" => 0,
"password_client" => 1,
"personal_access_client" => 0,
"redirect" => "http://localhost",
]);
}
catch(\Exception $e){
DB::rollback();
$message = $e->getMessage();
return response()->json(['error' => 1, 'message' => $message]);
}
DB::commit();
return response()->json([
'message' => 'Successfully created user!',
'client_secret' => $secret,
'client_id' => $oauth_clients->id
], 201);
} catch (\Exception $e) {
DB::rollback();
// something went wrong
$message = $e->getMessage();
return response()->json(['error' => 1, 'message' => $message]);
}
}
}
|
Consumer App
Now, let us create a consumer app, where this API data is fetched and displayed.Create a new App
Let us create a new Laravel app,Install GuzzleHttp
Here I useGuzzleHttp
package to call the API just created. So let us install it. In the consumerApp root, run the following command to install it,Authenticate the API and get the data
Now, let us authenticate the API and get data from the API. Here it is only one function so I will manage everything in a single function in the routes file(routes\web.php
)Assuming the API we created is running at
http://localhost:8000
I will call the url
http://localhost:8000/oauth/token
with post method, this URL is one of the route created by the passport package.As you see there are some
form_params
to be passed to it, client_id
and client_secret
are the one which obtained when registered to the API and the grant_type
is password, and also we need to provide the username
and password
used for registering to the API, also scope
should be passed as *With the above call, we get an
access_token
and pass this access_token as a Header to the actual API call to get all the details.Now, the obtained data is stored in some variable, so we can loop it and display the data accordingly.
1
|
$details = json_decode( (string) $response->getBody() );
|
Display the data
Here I will use a basic HTML table to display the data.Run the app
So now lets run the application and see. As the API is running on default port 8000. Let us change the port and run it.So now when we open
http://localhost:8594/
we can see the data, which looks like the below image.So that’s it, guys! We have successfully created an API with passport authentication and also consumed that API in another application.
0 comments