Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Java - Designing a validator, class hierarchy

I'm working on designing a validator for certain objects (fields of those objects). These objects are enclosed in one, bigger object - container.

Example: Car as a container . Consists of Wheels, Engine, Body. Lets say i need to validate if wheels have correct diameter, engine has correct capacity, body has certain length etc.

Theoretically I think I should validate everything before construction of a container (car).

What is the best way to achieve this? Do I make an abstract validator class with validate() method and implement it in every enclosed class? What about the container, do I just not include it at all in the validation process? Thanks for help.

like image 842
Raidmaster Avatar asked Jan 14 '13 12:01

Raidmaster


2 Answers

I'd suggest you not to put the validation logic inside the classes you're going to validate.

I find it better to keep those classes as mere value objects, and create a parallel hierarchy of validators, roughly one for each entity to be validated. Alternatively, you could also create a single validator that can validate all the entities: however, this solution is less scalable and could bring you to violate the open-closed principle when you have to add a new entity (e.g. you want to deal also with the rear-view mirrors of the car).

Assuming you choose the one entity : one validator approach, the validator of the container will first validate the components inside the container and then validate if they fit together.

Please consider also the possibility of using validator frameworks such as Apache Commons Validator, that can save you from writing boilerplate code. However, since I don't know what kind of complex validation you have to perform, I don't know if it fits your needs.

Furthermore, I don't think you should be worried of validating everything before it is constructed. Just construct it and validate afterwards: then, if it violates the validation rules, you can discard it (i.e. don't persist it anywhere).

like image 157
gd1 Avatar answered Sep 21 '22 14:09

gd1


piggy backing off of gd1 answer, I agree. One such way would be to have a ValidatorAdapter for each of your value objects. So it would look like this:

public class GreenCarValidator {
   public GreenCarValidator(Car car) {
      // save reference
   }

   @Override 
   public boolean isValid() {
      return car.getColor().equals("green");
   }
}

public class RedCarValidator {
   public RedCarValidator(Car car) {
      // save reference
   }

   @Override 
   public boolean isValid() {
      // you could compose more validators here for each property in the car object as needed
      return car.getColor().equals("red");
   }
}

Now you can have many types of validators for a single type of object, dynamic and configurable at runtime. Should you put the "valid()" method inside the classes the classes as gd1 suggest you not do, you would lose this flexibility.

like image 32
user123321 Avatar answered Sep 24 '22 14:09

user123321