Validating Requests
Introduction
In all real world, production APIs, you don't let the server run into errors and warnings to break the execution stack. That is why we use Request Validation. After all, why should show SQL Errors to the API consumers, when you can just validate the data sent yourself?
WARNING
This section assumes that you are already familiar with what endpoints are available from this package. If you are unsure please read the Available Requests section
Typical Laravel Usage
In a typical Laravel application there are 2 ways to validate data sent, both of them are not usable in Api Auto Pilot. The first one would be to validate the request's incoming values in the controller using the
validate()
method which takes anarray
containing the formula of what the data sent should be.The other way that we could validate an incoming request to the server, would be to create our own request class, using
php artisan make:request {myRequestClass}
and then type hint it, into the controller method, that handles this particular request. Since we do not have access to thecontroller
, what approach do we choose?
Solution
The answer is, mostly the second approach. To validate incoming requests using when already having Request Classes
ready you simply add a $validationRequest
array and set it to the Request class that you want to validate against.
public $validationRequest = [
'create' => CreatePostModelRequest::class,
'update' => UpdatePostModelRequest::class,
]
TIP
You can have many types of request validation for each CRUD operation. If you have different validation requirement for Creating
and Updating
, you can set the $requestValidations['create']
for creating, and $validationRequest['update']
for updating, to the value of the request class namespace. Api Auto Pilot will detect which CRUD operation you are doing at the moment and load up the appropriate validation class.
Let's see an example here. Lets a request class and validate the incoming values to create a Post
model. Let's assume that to create a new Post
model, the API consumer is required to provide a body
JSON index, but to update it, it's not required.
First, we will 2 the request classes one by one.
php artisan make:request CreatePostModelRequest
WARNING
To not break your application's security measures, Api Auto Pilot, evaluates the return type of the authorize()
method in your request class. If it returns a falsy value, the endpoint will result with an unauthorized response followed by a 401 UNAUTHORIZED
HTTP Response Status Code
{
"error": "unauthorized"
}
This command will result in creating a new CreatePostRequest.php file that is contained in the app/Http/Requests
folder. In the rules()
method set the required values that you want your request indexes to have. In our example, we will set that body
index is required.
<?php
namespace App\Http\Requests;
use Illuminate\Foundation\Http\FormRequest;
class CreatePostModelRequest extends FormRequest
{
public function authorize()
{
return true;
}
public function rules()
{
return [
'body' =>'required'
];
}
}
Next, we set this class to the $validationRequest
variable in our model, which is App\Models\Post
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;
class Post extends Model
{
use HasFactory;
public $validationRequest = [
'create' => CreatePostModelRequest::class,
]
protected $fillable = [
'body', 'title',
];
}
Now, lets see what happens if you try to make a POST
Request to the endpoint /api/aap/post
to create a new Post
without providing a body parameter.
// Post Request to `/api/aap/post`
{
"title": "creating a post without required body"
}
We get the following error response followed by a 422 - Unprocessable Content
HTTP Response Code
{
"message": "The body field is required.",
"errors": {
"body": [
"The body field is required."
]
}
}