Validate Your Endpoints Using Spring

What Do We Want To Do? ?

Apply validation to the objects we receive at the endpoint controllers from clients.

What Is The First Solution That Comes To Mind? ?

it’s simple, right? write functions that validate those objects.

Say …


This content originally appeared on DEV Community and was authored by Abdulcelil Cercenazi

What Do We Want To Do? ?

Apply validation to the objects we receive at the endpoint controllers from clients.

What Is The First Solution That Comes To Mind? ?

it's simple, right? write functions that validate those objects.

Say we have an endpoint to add new Shipments. ?

Let's start with the DTO classes (Data Transfer Object)

@RequiredArgsConstructor @Getter  
public class ShipmentComponentDTO {  
    private final String productCode;  
}
@RequiredArgsConstructor @Getter  
public class ShipmentDTO {  
    private final String productCode;  
    private final int count;  
    private final List<ShipmentComponentDTO> shipmentComponentDTOs;  
}

Now, the controller

@RestController  
public class ShipmentController {  
    @PostMapping("/shipment/add")  
    public ResponseEntity<String> addShipment(@RequestBody ShipmentDTO shipmentDTO){  
        if (shipmentDTO.getProductCode() == null)  
            return ResponseEntity.badRequest().body("Product code can't be null");  

        if (shipmentDTO.getCount() <= 0)  
            return ResponseEntity.badRequest().body("Count can't be negative or zero");  

        if (!allComponentsAreValid(shipmentDTO))  
            return ResponseEntity.badRequest().body("Component product code can't be null");  

        return ResponseEntity.ok(":)");  
    }  

    private boolean allComponentsAreValid(ShipmentDTO shipmentDTO) {  
        List<ShipmentComponentDTO> shipmentComponentDTOs = shipmentDTO.getShipmentComponentDTOs();  

        return shipmentComponentDTOs != null &&  
                shipmentComponentDTOs.size() > 0 &&  
                shipmentComponentDTOs.  
                stream().  
                allMatch(shipmentComponentDTO -> shipmentComponentDTO.getProductCode() != null);  
    }  
}

Notice all the manual tedious work we had to do.?

Can't anyone help us make this task more fun??

Please meet the Javax validator.?

  • It provides a set of annotations that are used with class fields.
  • They act as constraints.
    • this field should not be null
    • this list should have a minimum size of 5
    • and many more...

How to do it??

For the object we want to validate

  • We annotate the fields we want to validate with annotations from javax.validation.constraints
  • Then, we annotate the parameter of the controller where we want to validate.

  • We then have to catch the error thrown by the validator, and return a proper response to the user.

Let's code it ?

Here are the DTO objects

@RequiredArgsConstructor @Getter  
public class ShipmentComponentDTO {  
    @NotBlank(message = "Component product code can't be null")  
    private final String productCode;  
    // required by the javax validation code  
  public ShipmentComponentDTO() {  
        this.productCode = "";  
    }  
}
@RequiredArgsConstructor @Getter  
public class ShipmentDTO {  
    @NotBlank(message = "Product code can't be null")  
    private final String productCode;  
    @Min(1)  
    private final int count;  

    @Size(min = 1, message = "Component product code can't be empty")  
    @NotNull(message = "Component product code can't be null")  
    @Valid  
  private final List<ShipmentComponentDTO> shipmentComponentDTOs;  
}

Ok, what were those annotations??

  • NotBlank
    • This field can't be null or empty string
  • Min
    • this integer should have a min value we specify
  • Size
    • this array's size should be within the boundaries we specify
  • NotNull
    • This field must not be null
  • Valid
    • Validate the fields in this object

Now, here is the controller?

@RestController  
public class ShipmentController_Validation {  
    @PostMapping("validation/shipment/add")  
    public ResponseEntity<String> addShipment(@RequestBody @Validated ShipmentDTO shipmentDTO){  
        return ResponseEntity.ok(":)");  
    }  
}

What was that @Validated annotation??

  • it tells Spring to run the validation mechanism on this object according to its validation annotations(NotBlank, etc..)

Finally, let's catch the exception thrown by the validator and generate a proper response

@Order(Ordered.HIGHEST_PRECEDENCE)  
@ControllerAdvice  
public class ValidationAdvice{  
    @ResponseStatus(BAD_REQUEST)  
    @ResponseBody  
 @ExceptionHandler(MethodArgumentNotValidException.class)  
    public ResponseEntity<?> methodArgumentNotValidException(MethodArgumentNotValidException ex) {  
        BindingResult result = ex.getBindingResult();  
        List<FieldError> fieldErrors = result.getFieldErrors();  
        String errorMessage = fieldErrors.get(0).getDefaultMessage();  
        return ResponseEntity.badRequest().body(errorMessage);  
    }  
}

In conclusion✍️

  • Imagine having an API with many endpoints that we need to validate. Which method would be better?
  • The Validator.

Code on GitHub


This content originally appeared on DEV Community and was authored by Abdulcelil Cercenazi


Print Share Comment Cite Upload Translate Updates
APA

Abdulcelil Cercenazi | Sciencx (2021-06-11T21:16:19+00:00) Validate Your Endpoints Using Spring. Retrieved from https://www.scien.cx/2021/06/11/validate-your-endpoints-using-spring/

MLA
" » Validate Your Endpoints Using Spring." Abdulcelil Cercenazi | Sciencx - Friday June 11, 2021, https://www.scien.cx/2021/06/11/validate-your-endpoints-using-spring/
HARVARD
Abdulcelil Cercenazi | Sciencx Friday June 11, 2021 » Validate Your Endpoints Using Spring., viewed ,<https://www.scien.cx/2021/06/11/validate-your-endpoints-using-spring/>
VANCOUVER
Abdulcelil Cercenazi | Sciencx - » Validate Your Endpoints Using Spring. [Internet]. [Accessed ]. Available from: https://www.scien.cx/2021/06/11/validate-your-endpoints-using-spring/
CHICAGO
" » Validate Your Endpoints Using Spring." Abdulcelil Cercenazi | Sciencx - Accessed . https://www.scien.cx/2021/06/11/validate-your-endpoints-using-spring/
IEEE
" » Validate Your Endpoints Using Spring." Abdulcelil Cercenazi | Sciencx [Online]. Available: https://www.scien.cx/2021/06/11/validate-your-endpoints-using-spring/. [Accessed: ]
rf:citation
» Validate Your Endpoints Using Spring | Abdulcelil Cercenazi | Sciencx | https://www.scien.cx/2021/06/11/validate-your-endpoints-using-spring/ |

Please log in to upload a file.




There are no updates yet.
Click the Upload button above to add an update.

You must be logged in to translate posts. Please log in or register.