Laravel Validation returns an error as a JSON response with the error messages in a strict standard format. What if you want to change it to an entirely different structure because your front-enders ask you for specific key-value pairs?
The default Laravel validation error structure usually looks like this:
But if you need to customize the structure, one of the ways you can do that globally is to override the Exception class with your own custom class.
Creating New Exception Class
Run the following command:
php artisan make:exception CustomValidationException
This will create a new file, app/Exceptions/CustomValidationException.php
with the following content:
use Exception; class CustomValidationException extends Exception{ //}
Let's leave it as it is, for now.
Registering New Exception Class
Next, we need to inform Laravel that we want to render our Exception instead of the default one:
app/Exceptions/Handler.php
// ... public function register(): void{ $this->renderable(function (ValidationException $exception, $request) { if (!$request->wantsJson()) { return null; // Laravel handles as usual } throw CustomValidationException::withMessages( $exception->validator->getMessageBag()->getMessages() ); }); $this->reportable(function (Throwable $e) { // });}
We told Laravel to render our Exception when ValidationException
is thrown. We also check if it's an API request (wanting JSON response), and if it's not, we let Laravel handle it as usual without our custom Exception.
Implementing Custom Exception Class
Let's get back to our CustomValidationException
class:
app/Exceptions/CustomValidationException.php
use Illuminate\Http\JsonResponse;use Illuminate\Validation\ValidationException;use Symfony\Component\HttpFoundation\Response; class CustomValidationException extends ValidationException{ public function render($request): JsonResponse { return new JsonResponse([ // This is the array that you will return in case of an error. // You can put whatever you want inside. 'message' => 'There were some errors', 'status' => false, 'additionalThings' => 'Some additional things', 'errors' => $this->validator->errors()->getMessages(), ], Response::HTTP_UNPROCESSABLE_ENTITY); }}
Here, we will override the render()
method of the ValidationException
class that we extend. Inside, we will return a JSON response with the desired array structure. In our case, in addition to standard errors
, we've added status
and additionalThings
keys, which resulted in the following:
From here, you can customize the structure of the error messages as you wish.
You can learn more about Exceptions in our Premium course Handling Exceptions and Errors in Laravel
u