Apis are a great choice when working with cross-platform applications. In addition to the website, your product may have Android and iOS apps. In this case, the API is just as good because you can write a different front end without changing any of the back end code. When using the API, simply click GET, POST, or some other type of request with a few parameters, and the server returns data in JSON (JavaScript Object Notation) format that is processed by the client application.

instructions

My official group click here.

Let’s start by writing down our application details and functionality. We will use JWT authentication to build a list of basic user products using restful apis in Laravel.

A User will use the following functions

  • Register and create a new account
  • Log in to their account
  • Unregister and discard tokens and leave the application
  • Get the details of the logged-in user
  • Retrieves the list of products available to the user
  • Find a specific product by ID
  • Add the new product to the user product list
  • Edit existing product details
  • Remove existing products from the user list

A User required

  • name
  • email
  • password

The Product will fill A

  • name
  • price
  • quantity

Creating a new project

We can start and create a new Laravel project by running the following command.

composer create-project –prefer-dist laravel/laravel jwt

This creates a new Laravel project in a directory named JWT.

Configure the JWT extension pack

We will use the Tymondesigns/JWT-Auth extension pack to let us use JWT in Laravel.

Install the Tymon/JwT-Auth extension pack

Let’s install the extension pack in the Laravel application. If you are using Laravel 5.5 or above, run the following command to get the JWT package for dev-develop:

composer require tymon/jwt-auth:dev-develop --prefer-sourceCopy the code

If you are using Laravel 5.4 or below, run the following command:

composer require tymon/jwt-authCopy the code

For Laravel versions lower than 5.5, you also set the service provider and alias in the config/app.php file.

'providers'=> [ .... Tymon\JWTAuth\Providers\JWTAuthServiceProvider::class, .... ] .'aliases'= > [...'JWTAuth' => Tymon\JWTAuth\Facades\JWTAuth::class,
 'JWTFactory'= >'Tymon\JWTAuth\Facades\JWTFactory'. ] .Copy the code

If your Laravel version is 5.5 or above, Laravel does “automatic package discovery.”

Publishing configuration files

For Laravel 5.5 or above, use the following command to publish the configuration file:

php artisan vendor:publish --provider="Tymon\JWTAuth\Providers\LaravelServiceProvider"Copy the code

For previous versions of Laravel, run the following command:

php artisan vendor:publish --provider="Tymon\JWTAuth\Providers\JWTAuthServiceProvider"Copy the code

The command above generates the config/jwt.php configuration file. Without the comments, the configuration file looks like this:

<? phpreturn [
 'secret' => env('JWT_SECRET'),
 'keys'= > ['public' => env('JWT_PUBLIC_KEY'),
 'private' => env('JWT_PRIVATE_KEY'),
 'passphrase' => env('JWT_PASSPHRASE')],'ttl' => env('JWT_TTL', 60).'refresh_ttl' => env('JWT_REFRESH_TTL', 20160),
 'algo' => env('JWT_ALGO'.'HS256'),
 'required_claims'= > ['iss'.'iat'.'exp'.'nbf'.'sub'.'jti',].'persistent_claims'= > [/ /'foo', / /'bar',].'lock_subject'= >true.'leeway' => env('JWT_LEEWAY', 0).'blacklist_enabled' => env('JWT_BLACKLIST_ENABLED'.true),
 'blacklist_grace_period' => env('JWT_BLACKLIST_GRACE_PERIOD', 0).'decrypt_cookies'= >false.'providers'= > ['jwt' => Tymon\JWTAuth\Providers\JWT\Lcobucci::class,
 'auth' => Tymon\JWTAuth\Providers\Auth\Illuminate::class,
 'storage' => Tymon\JWTAuth\Providers\Storage\Illuminate::class,
 ],
];Copy the code

Generate the JWT key

JWT tokens are issued using an encrypted key. For Laravel 5.5 or above, run the following command to generate the key for token issuance.

php artisan jwt:secretCopy the code

Laravel versions lower than 5.5 run:

php artisan jwt:generateCopy the code

This tutorial uses Laravel 5.6. The next steps in the tutorial have only been tested in 5.5 and 5.6. May not work with Laravel 5.4 or below. You can read the documentation for older versions of Laravel.

Registered middleware

The JWT Certification extension comes with middleware that allows us to use it. To register auth.jwt middleware in app/Http/ kernel. PHP:

protected $routeMiddleware= [...'auth.jwt' => \Tymon\JWTAuth\Http\Middleware\Authenticate::class,
];Copy the code

The middleware verifies the user’s authentication by checking the token attached to the request. If the user authentication, not the middleware will throw UnauthorizedHttpException anomalies.

Set the routing

Before we begin, we will set up routes for all the points discussed in this tutorial. Open routes/api.php and copy the following routes into your file.

Route::post('login'.'ApiController@login');
Route::post('register'.'ApiController@register');
Route::group(['middleware'= >'auth.jwt'].function () {
 Route::get('logout'.'ApiController@logout');
 Route::get('user'.'ApiController@getAuthUser');
 Route::get('products'.'ProductController@index');
 Route::get('products/{id}'.'ProductController@show');
 Route::post('products'.'ProductController@store');
 Route::put('products/{id}'.'ProductController@update');
 Route::delete('products/{id}'.'ProductController@destroy');
});Copy the code

Updating the User model

JWT needs to implement the Tymon\JWTAuth\Contracts\JWTSubject interface in the User model. This interface needs to implement two methods, getJWTIdentifier and getJWTCustomClaims. Update app/ user.php with the following.

<? php namespace App; use Illuminate\Foundation\Auth\User as Authenticatable; use Illuminate\Notifications\Notifiable; use Tymon\JWTAuth\Contracts\JWTSubject; class User extends Authenticatable implements JWTSubject { use Notifiable; /** * The attributes that are mass assignable. * * @var array */ protected$fillable = [
 'name'.'email'.'password',]; /** * The attributes that should be hiddenfor arrays.
 *
 * @var array
 */
 protected $hidden = [
 'password'.'remember_token',]; /** * Get the identifier that will be storedin the subject claim of the JWT.
 *
 * @return mixed
 */
 public function getJWTIdentifier()
 {
 return $this->getKey();
 }
 /**
 * Return a key value array, containing any custom claims to be added to the JWT.
 *
 * @return array
 */
 public function getJWTCustomClaims()
 {
 return[]; }}Copy the code

JWT authentication logic

Let’s write the Restful API logic in Laravel using JWT authentication.

Users need a name, email address and password to register. So, let’s create a form request to validate the data. Create a form request named RegisterAuthRequest by running the following command: RegisterAuthRequest

php artisan make:request RegisterAuthRequest

It will create the registerAuthRequest.php file in the app/Http/Requests directory. Paste the following code into the file.

<? php namespace App\Http\Requests; use Illuminate\Foundation\Http\FormRequest; Class RegisterAuthRequest extends FormRequest {/** * Determines whether the user is authorized to make this request ** @return bool
 */
 public function authorize()
 {
 return true; } /** * gets the validation rule ** @ applied to the requestreturn array
 */
 public function rules()
 {
 return [
 'name'= >'required|string'.'email'= >'required|email|unique:users'.'password'= >'required|string|min:6|max:10']; }}Copy the code

Run the following command to create a new ApiController:

php artisan make:controller ApiController

This will create the apicontroller.php file in the app/Http/Controllers directory. Paste the following code into the file.

<? php namespace App\Http\Controllers; use App\Http\Requests\RegisterAuthRequest; use App\User; use Illuminate\Http\Request; use JWTAuth; use Tymon\JWTAuth\Exceptions\JWTException; class ApiController extends Controller { public$loginAfterSignUp = true;
 public function register(RegisterAuthRequest $request)
 {
 $user = new User();
 $user->name = $request->name;
 $user->email = $request->email;
 $user->password = bcrypt($request->password);
 $user->save();
 if ($this->loginAfterSignUp) {
 return $this->login($request);
 }
 return response()->json([
 'success'= >true.'data'= >$user
 ], 200);
 }
 public function login(Request $request)
 {
 $input = $request->only('email'.'password');
 $jwt_token = null;
 if (!$jwt_token = JWTAuth::attempt($input)) {
 return response()->json([
 'success'= >false.'message'= >'Invalid Email or Password',], 401); }return response()->json([
 'success'= >true.'token'= >$jwt_token,]); } publicfunction logout(Request $request)
 {
 $this->validate($request['token'= >'required'
 ]);
 try {
 JWTAuth::invalidate($request->token);
 return response()->json([
 'success'= >true.'message'= >'User logged out successfully'
 ]);
 } catch (JWTException $exception) {
 return response()->json([
 'success'= >false.'message'= >'Sorry, the user cannot be logged out'
 ], 500);
 }
 }
 public function getAuthUser(Request $request)
 {
 $this->validate($request['token'= >'required'
 ]);
 $user = JWTAuth::authenticate($request->token);
 return response()->json(['user'= >$user]); }}Copy the code

Let me explain what happened to the code above.

In the Register method, we receive the RegisterAuthRequest. Create a user using the data in the request. If the loginAfterSignUp attribute is true, the user is logged in by calling the login method after registration. Otherwise, a successful response is returned with user data.

In the Login method, we get a subset of the request, which contains only the E-mail and password. JWTAuth:: Attempt () is called with the input value as an argument, and the response is stored in a variable. If false is returned from the Attempt method, a failed response is returned. Otherwise, a successful response is returned.

In the logout method, verify that the request contains token validation. Invalidate the token by calling the invalidate method and return a successful response. If a JWTException exception is caught, a failed response is returned.

In the getAuthUser method, verify that the request contains a token field. The Authenticate method is then called, which returns the authenticated user. Finally, the response is returned with the user.

The authentication section is now complete.

Building the product part

To create the Product section, we need the Product model, controller, and migration file. Run the following commands to create the Product model, controller, and migrate files.

php artisan make:model Product -mcCopy the code

It creates a new database migration file create_products_table.php in the database/migrations directory, changing the up method.

public function up()
{
 Schema::create('products'.function (Blueprint $table) {
 $table->increments('id');
 $table->integer('user_id');
 $table->string('name');
 $table->integer('price');
 $table->integer('quantity');
 $table->timestamps();
 $table->foreign('user_id')
 ->references('id')
 ->on('users')
 ->onDelete('cascade');
 });
}Copy the code

Add the Fillable attribute to the Product model. Open the product.php file in the app directory and add attributes.

protected $fillable = [
 'name'.'price'.'quantity'
];Copy the code

Now set up the database credentials in the.env file and migrate the database by running the following command.

php artisan migrateCopy the code

Now we must add a relationship to the User model to retrieve the related products. Add the following methods in app/ user.php.

public function products()
{
 return $this->hasMany(Product::class);
} Copy the code

Open the productController.php file in app/Http/Controllers. Overwrite the previous one by adding the use directive at the beginning of the file.

use App\Product;
use Illuminate\Http\Request;
use JWTAuth;Copy the code

Now we will implement five methods.

Index, to get a list of all products for authenticated users

Show to get a specific product by ID

Store to store new products in the product list

Update, updates product details by ID

Destroy, remove products from the list by ID

Add a constructor to get the authenticated user and store it in the User attribute.

protected $user;
public function __construct()
{
 $this->user = JWTAuth::parseToken()->authenticate();
}Copy the code

ParseToken parses the token from the request and authenticate the user with the token.

Let’s add the index method.

public function index()
{
 return $this->user
 ->products()
 ->get(['name'.'price'.'quantity'])
 ->toArray();
}Copy the code

The code above is very simple. We just grab all the products using our Eloquent method and assemble the results into an array. Finally, we return this array. Laravel will automatically convert this to JSON and create a 200 success response code.

Continue to implement the show method.

public function show($id)
{
 $product = $this->user->products()->find($id);
 if (!$product) {
 return response()->json([
 'success'= >false.'message'= >'Sorry, product with id ' . $id . ' cannot be found'
 ], 400);
 }
 return $product;
}Copy the code

This is also very easy to understand. We just need to find the product by ID. If the product does not exist, a 400 fault response is returned. Otherwise, an array of products is returned.

Next up is the Store method

public function store(Request $request)
{
 $this->validate($request['name'= >'required'.'price'= >'required|integer'.'quantity'= >'required|integer'
 ]);
 $product = new Product();
 $product->name = $request->name;
 $product->price = $request->price;
 $product->quantity = $request->quantity;
 if ($this->user->products()->save($product))
 return response()->json([
 'success'= >true.'product'= >$product
 ]);
 else
 return response()->json([
 'success'= >false.'message'= >'Sorry, product could not be added'
 ], 500);
}Copy the code

In the Store method, verify that the request contains a name, price, and quantity. Then, use the data in the request to create a new product model. If the product successfully writes to the database, a success response is returned, otherwise a custom 500 failure response is returned.

Implementing the Update method

public function update(Request $request.$id)
{
 $product = $this->user->products()->find($id);
 if (!$product) {
 return response()->json([
 'success'= >false.'message'= >'Sorry, product with id ' . $id . ' cannot be found'
 ], 400);
 }
 $updated = $product->fill($request->all())
 ->save();
 if ($updated) {
 return response()->json([
 'success'= >true
 ]);
 } else {
 return response()->json([
 'success'= >false.'message'= >'Sorry, product could not be updated'], 500); }}Copy the code

In the update method, we get the product by ID. If the product does not exist, return a 400 response. We then populate the data from the request with the product details using the fill method. Update the product model and save it to the database, returning a 200 success response if the record is successfully updated, or 500 internal server error response to the client otherwise.

Now, let’s implement the destroy method.

public function destroy($id)
{
 $product = $this->user->products()->find($id);
 if (!$product) {
 return response()->json([
 'success'= >false.'message'= >'Sorry, product with id ' . $id . ' cannot be found'
 ], 400);
 }
 if ($product->delete()) {
 return response()->json([
 'success'= >true
 ]);
 } else {
 return response()->json([
 'success'= >false.'message'= >'Product could not be deleted'], 500); }}Copy the code

In the destroy method, we get the product by ID and return a 400 response if it doesn’t exist. We then delete the product and return the appropriate response based on the successful status of the delete operation.

The controller code is now complete, the complete controller code is here.

test

Let’s start by testing authentication. We will use the serve command to start the Web service on the development machine, or you can use a virtual host instead. Run the following command to start the Web service.

php artisan serveCopy the code

It will listen on localhost:8000

To test restful apis’, we use Postman. After filling in the request body, we request a register route.

Send the request and you will get the token.

Our users are now registered and authenticated. We can send another request to detect the LOGIN route, which returns 200 and the token.


Obtaining User Details


Test authentication is complete. Next, test the product section by first creating a product.

Now get the product by requesting the Index method.

You can test other routes and they will all work fine.

To learn more, please visit:

Tencent T3-T4 standard boutique PHP architect tutorial directory directory, as long as you finish the guarantee salary rise a step (continue to update)


I hope the above content can help you. Many PHPer will encounter some problems and bottlenecks when they are advanced, and they have no sense of direction when writing too many business codes. I have sorted out some information, including but not limited to: Distributed architecture, high scalability, high performance, high concurrency, server performance tuning, TP6, Laravel, YII2, Redis, Swoole, Swoft, Kafka, Mysql optimization, shell scripting, Docker, microservices, Nginx, etc.