Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
org.droitateddb.DatabaseValidator Maven / Gradle / Ivy
package org.droitateddb;
import org.droitateddb.schema.AbstractAttribute;
import org.droitateddb.schema.ColumnValidator;
import org.droitateddb.schema.EntityInfo;
import org.droitateddb.validation.AccumulatedValidationResult;
import org.droitateddb.validation.CustomValidator;
import org.droitateddb.validation.ValidationResult;
import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Proxy;
import java.util.Collection;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import static org.droitateddb.Utilities.getFieldValue;
import static org.droitateddb.Utilities.getStaticFieldValue;
/**
* Validates entities by their schema definition
*
* @author Falk Appel
* @author Alexander Frank
*/
public class DatabaseValidator {
public AccumulatedValidationResult validate(Collection toBeValidated) {
return validate(toBeValidated, Integer.MAX_VALUE);
}
public AccumulatedValidationResult validate(Collection toBeValidated, int maxDepth) {
AccumulatedValidationResult validationResult = new AccumulatedValidationResult();
Set alreadyValidated = new HashSet();
for (T data : toBeValidated) {
validate(data, validationResult, alreadyValidated, 0, maxDepth);
}
return validationResult;
}
public AccumulatedValidationResult validate(T toBeValidated) {
return validate(toBeValidated, Integer.MAX_VALUE);
}
public AccumulatedValidationResult validate(T toBeValidated, int maxDepth) {
AccumulatedValidationResult validationResult = new AccumulatedValidationResult();
Set alreadyValidated = new HashSet();
validate(toBeValidated, validationResult, alreadyValidated, 0, maxDepth);
return validationResult;
}
private void validate(Object validatingObject, AccumulatedValidationResult validationResult, Set alreadyValidated, int currentDepth, int maxDepth) {
try {
EntityInfo entityInfo = SchemaUtil.getEntityInfo(validatingObject.getClass());
Class> definition = entityInfo.definition();
EntityData entityData = EntityData.getEntityData(validatingObject);
List allAssociations = entityData.allAssociations;
if (allAssociations.size() > 0) {
validateRelationshipsOfEntity(validatingObject, allAssociations, validationResult, alreadyValidated, currentDepth, maxDepth);
}
if (entityInfo.hasValidation()) {
validateColumnsInEntity(validatingObject, definition, entityData.columns, validationResult);
}
} catch (Exception e) {
throw new IllegalStateException(e);
}
}
private void validateColumnsInEntity(Object validatingObject, Class> definition, List columns, AccumulatedValidationResult validationResult) throws NoSuchFieldException, IllegalAccessException, InstantiationException, java.lang.reflect.InvocationTargetException, NoSuchMethodException {
for (Field column : columns) {
ValidationResult result = checkForValidatorsAndValidate(validatingObject, column, definition);
if (!result.isValid()) {
validationResult.addError(result);
}
}
}
private void validateRelationshipsOfEntity(Object validatingObject, List relationships, AccumulatedValidationResult validationResult, Set alreadyValidated, int currentDepth, int maxDepth) throws IllegalAccessException, InvocationTargetException, NoSuchMethodException, InstantiationException, NoSuchFieldException {
if (currentDepth < maxDepth) {
for (Field relationship : relationships) {
getRelatedEntityAndValidate(validatingObject, relationship, validationResult, currentDepth, maxDepth, alreadyValidated);
}
}
}
private void getRelatedEntityAndValidate(Object validatingObject, Field relationship, AccumulatedValidationResult validationResult, int currentDepth, int maxDepth, Set alreadyValidated) throws IllegalAccessException {
Object relatedEntity = getFieldValue(validatingObject,relationship);
if (relatedEntity != null) {
handleRelatedEntity(relatedEntity, validationResult, currentDepth, maxDepth, alreadyValidated);
}
}
@SuppressWarnings("unchecked")
private void handleRelatedEntity(Object relatedEntity, AccumulatedValidationResult validationResult, int currentDepth, int maxDepth, Set alreadyValidated) {
if (Collection.class.isAssignableFrom(relatedEntity.getClass())) {
handleCollectionRelationship((Collection) relatedEntity, validationResult, currentDepth, maxDepth, alreadyValidated);
} else {
checkAlreadyValidatedAndValidate(relatedEntity, validationResult, currentDepth, maxDepth, alreadyValidated);
}
}
private void handleCollectionRelationship(Collection relatedEntity, AccumulatedValidationResult validationResult, int currentDepth, int maxDepth, Set alreadyValidated) {
for (Object entity : relatedEntity) {
checkAlreadyValidatedAndValidate(entity, validationResult, currentDepth, maxDepth, alreadyValidated);
}
}
private void checkAlreadyValidatedAndValidate(Object entity, AccumulatedValidationResult validationResult, int currentDepth, int maxDepth, Set alreadyValidated) {
if (!alreadyValidated.contains(entity)) {
alreadyValidated.add(entity);
validate(entity, validationResult, alreadyValidated, currentDepth + 1, maxDepth);
}
}
private ValidationResult checkForValidatorsAndValidate(Object toBeValidated, Field column, Class> definition) throws NoSuchFieldException, IllegalAccessException, InstantiationException, java.lang.reflect.InvocationTargetException, NoSuchMethodException {
AbstractAttribute attribute = getStaticFieldValue(definition,column.getName().toUpperCase());
ColumnValidator[] columnValidators = attribute.getColumnValidators();
if (columnValidators.length > 0) {
return validateColumn(toBeValidated, attribute, columnValidators);
}
return ValidationResult.valid();
}
@SuppressWarnings("unchecked")
private ValidationResult validateColumn(Object toBeValidated, AbstractAttribute attribute, ColumnValidator[] columnValidators) throws NoSuchFieldException, IllegalAccessException, InstantiationException, java.lang.reflect.InvocationTargetException, NoSuchMethodException {
Object entityValue = getFieldValue(toBeValidated.getClass(),attribute.fieldName(),toBeValidated);
for (ColumnValidator columnValidator : columnValidators) {
Class extends Annotation> validatorAnnotation = columnValidator.getValidatorAnnotation();
Class> proxyClass=null;
try {
proxyClass = Proxy.getProxyClass(DatabaseValidator.class.getClassLoader(), validatorAnnotation);
} catch (IllegalArgumentException iae) {
proxyClass = Proxy.getProxyClass(Thread.currentThread().getContextClassLoader(), validatorAnnotation);
}
Annotation annotationInstance = (Annotation) proxyClass.getConstructor(new Class[]{InvocationHandler.class}).newInstance(new Object[]{new DatabaseValidatorAnnotationHandler(columnValidator.getParams())});
Class extends CustomValidator, ?>> validatorClass = columnValidator.getValidatorClass();
CustomValidator customValidator = (CustomValidator) validatorClass.getConstructor().newInstance();
ValidationResult result = customValidator.onValidate(validatorAnnotation.cast(annotationInstance), entityValue);
if (!result.isValid()) {
return result;
}
}
return ValidationResult.valid();
}
}