This is Part 2 of multi-part walk-through of a Laravel 5.5. REST API example. In Part 1 we covered how to install a fresh Laravel 5.5 project and prep it for API development, and in this part we’ll move forward with creating a User Registration endpoint. It’ll serve as a means to get user records into our API’s database, a prerequisite for later steps such as implementing JWT authentication.
Let’s get started.
Starting With A Default Migration
Before adding a user registration endpoint it’s worth running a default migration. Aside from introducing us as to Laravel’s migration mechanism, it also adds user related tables for us that’ll serve as a base for our user schema.
To run our first migration, run the following command from the project’s root:
php artisan migrate
After it completes, confirm that the database now has a users table. It’ll be empty, but that’s ok, our user registration endpoint will get user records in there soon enough.
Note: A password_resets table was also created, which can be ignored for now.
Creating the User Registration API
Now that we have a users table, we’re ready to create an API endpoint that writes to it. To start, first create the API route we’ll need for user registration. As we did w/the Hello World route, append the following to the routes/api.php file:
Route::group(['middleware' => ['api','cors']], function () { Route::post('auth/register', 'Auth\ApiRegisterController@create'); });
This will route to an ApiRegisterController we’ll create in a subsequent step.
Second, and in regard to the inclusion of cors in the route, since we’ll be making Cross Origin API requests, including with tools like Postman, Cross Origin request support is required. To add the CORS package, run the following commands in the project’s root directory:
composer require barryvdh/laravel-cors php artisan vendor:publish --provider="Barryvdh\Cors\ServiceProvider"
Then, add the following array element to the protected $routeMiddleware group in app/Http/Kernel.php:
'cors' => \Barryvdh\Cors\HandleCors::class
Third, create app/Http/Controllers/Auth/ApiRegisterController.php with the following contents:
<?php namespace App\Http\Controllers\Auth; use Illuminate\Http\Request; use Illuminate\Auth\Events\Registered; class ApiRegisterController extends RegisterController { /** * Handle a registration request for the application. * * @override * @param \Illuminate\Http\Request $request * @return \Illuminate\Http\Response */ public function register(Request $request) { $errors = $this->validator($request->all())->errors(); if(count($errors)) { return response(['errors' => $errors], 401); } event(new Registered($user = $this->create($request->all()))); $this->guard()->login($user); return response(['user' => $user]); } }
This is the ApiRegisterController that’ll handle our registration requests. It’s worth noting that this is more or less a a copy of the default app/Http/Controllers/Auth/RegisterController, with two changes. The first is the import of the Illuminate\Http\Request namespace in the file header, which allows the second change – this class’ create() method accepts a Request instance vs. an array.
Fourth, the registration endpoint is now ready to test. With Postman, and while the test server is running, send a request w/the following set in Postman:
- request method set to POST
- url set to http://localhost:8000/api/auth/register
- content type set to JSON
- for testing purposes, set the request body to the following key/value pairs in JSON:
To run our first migration, run the following command from the project’s root:
{ "name": "Walter White", "email": "wwhite@someemaildomain.net", "password": "testpassword", "password_confirmation": "testpassword" }
Here’s what the request looks like in Postman:
Once the request is sent, verify the response contains the test user represented in JSON. Also verify that a new record made it into the database. If both of those are verified, the Registration API is complete! If you have any questions or hit any issues, feel free to leave a comment below and we can try to sort things out for you.
In the next post we’ll add a login method that also implements the beginnings of a JWT authentication model.
Nice! I wanted to implement Passport’s “Password grant tokens” while I realize I could not register user with api route. After following this article I can register user now, Thanks!
with what u made u don’t use the RegistersUsers, and the validation won’t work .
And the solution?
In the route you should use the method register instead of create, because register (which is called from the trait RegistersUser) is the method that calls the validator.
Hey Juan,
Thanks for mentioning this. I’ve made a second pass through this post to clean it up – revised code for the ApiRegisterController class included, which is now much simpler. I appreciate you taking the time to reply.
If it matters, I wound up overriding RegistersUsers::register() so that my override returns a JSON response. The default behavior was to return html, perhaps via redirect, which is out of context for the API project I’m targeting.
Thanks again!
“Fourth, the registration endpoint is now ready to test. With Postman, and while the test server is running, send a test POST request to the following url: http://localhost:8000/auth/register.”
Should be http://localhost:8000/api/auth/register 😀
Indeed, that’s been corrected.
Thanks Travis!
I fallowed your instructions. but for some reson URI i got api/auth/register
Fatal error: Uncaught TypeError: Argument 2 passed to Illuminate\Routing\Router::middlewareGroup() must be of the type array, string given
Hey Juan,
Thanks for reporting this. Might you have a complete stack trace? Made another run-through of this post again today and couldn’t reproduce this.
Hi,
I am getting this error when I test on Postman:
Symfony\Component\Debug\Exception\FatalThrowableError: Type error: Argument 1 passed to App\Http\Controllers\Auth\RegisterController::create() must be of the type array, none given in file C:\wamp64\www\Folweni_Workman\app\Http\Controllers\Auth\RegisterController.php on line 63
Too few arguments to function App\Http\Controllers\Auth\RegisterController::create(), 0 passed and exactly 1 expected
Route::group([‘middleware’ => [‘api’,’cors’]], function () {
Route::post(‘auth/register’, ‘Auth\ApiRegisterController@create’);
});
fix
Route::group([‘middleware’ => [‘api’,’cors’]], function () {
Route::post(‘auth/register’, ‘Auth\ApiRegisterController@register’);
});