/* * Click nbfs://nbhost/SystemFileSystem/Templates/Licenses/license-default.txt to change this license * Click nbfs://nbhost/SystemFileSystem/Templates/Classes/Class.java to edit this template */ package com.megatim.fdxcommons.dao.ifaces.utils; import com.megatim.fdxcommons.model.enumeration.NumberOperator; import com.megatim.fdxcommons.model.enumeration.SearchAnnotationOperateur; import com.megatim.fdxcommons.model.search.Search; import com.megatim.fdxcommons.model.search.SearchCriteria; import java.beans.IntrospectionException; import java.beans.PropertyDescriptor; import java.lang.reflect.Field; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import javax.persistence.criteria.From; import javax.persistence.criteria.Join; import javax.persistence.criteria.Root; /** * * @author ASUS */ public class SearchCriteriaBuilderUtil { private SearchCriteriaBuilderUtil() { } public static List getSearchCriterias(U searchEntity, Class entityClass, Root root, List externalSearchCriterias) { Field[] entityFields = entityClass.getDeclaredFields(); List searchCriterias = new ArrayList<>(); if (externalSearchCriterias != null) { searchCriterias.addAll(externalSearchCriterias); } if (searchEntity == null) { return searchCriterias; } Field[] searchEntityFields = searchEntity.getClass().getDeclaredFields(); for (Field searchEntityField : searchEntityFields) { Search searchAnnotation = searchEntityField.getAnnotation(Search.class); if (searchAnnotation != null && searchAnnotation.fieldName() != null && !searchAnnotation.fieldName().isEmpty()) { String[] fieldPath = searchAnnotation.fieldName().split("\\."); if (fieldPath.length == 1) { if (isSearchFieldDescriptionCorrect(searchAnnotation.fieldName(), searchEntityField, entityFields)) { searchCriterias.add(createSearchCriteria(searchAnnotation, searchAnnotation.fieldName(), searchEntityField, searchEntity, root)); } } else if (fieldPath.length > 1) { Join join = null; String fieldName = fieldPath[fieldPath.length - 1]; for (int i = 0; i < fieldPath.length - 1; i++) { if (i == 0) { join = root.join(fieldPath[i]); } else { if (join != null) { join = join.join(fieldPath[i]); } } } if (isSearchHierarchicalFieldDescriptionCorrect(fieldPath, searchEntityField, entityFields)) { searchCriterias.add(createSearchCriteria(searchAnnotation, fieldName, searchEntityField, searchEntity, join)); } } } } return searchCriterias; } private static SearchCriteria createSearchCriteria(Search searchAnnotation, String fieldName, Field searchEntityField, Object searchEntity, From from) { SearchCriteria searchCriteria = new SearchCriteria(); searchCriteria.setFrom(from); searchCriteria.setFieldName(fieldName); searchCriteria.setOperateur(searchAnnotation.operateur()); searchCriteria.setFieldType(searchEntityField.getType()); Object fieldValue = getFieldValue(searchEntityField, searchEntity); searchCriteria.setFieldValue(fieldValue); if (searchAnnotation.operateur().equals(SearchAnnotationOperateur.NUMBER_OPERATOR)) { try { searchCriteria.setNumberOperator(getNumberOperatorFieldValue(searchAnnotation.operatorFieldName(), searchEntity)); } catch (IntrospectionException ex) { } } return searchCriteria; } private static Object getFieldValue(Field field, Object searchEntity) { Object value = null; field.setAccessible(true); try { Method method = new PropertyDescriptor(field.getName(), searchEntity.getClass()).getReadMethod(); value = (Comparable) method.invoke(searchEntity); } catch (IllegalArgumentException | IllegalAccessException | InvocationTargetException | java.beans.IntrospectionException ex) { } return value; } private static NumberOperator getNumberOperatorFieldValue(String operatorFieldName, Object searchEntity) throws java.beans.IntrospectionException { NumberOperator numberOperator = NumberOperator.UNKNOW; Field[] fields = searchEntity.getClass().getDeclaredFields(); for (Field field : fields) { if (field.getName().equals(operatorFieldName)) { field.setAccessible(true); try { Method method = new PropertyDescriptor(field.getName(), searchEntity.getClass()).getReadMethod(); Object value = method.invoke(searchEntity); if (value instanceof NumberOperator) { numberOperator = (NumberOperator) value; } } catch (IllegalArgumentException | IllegalAccessException | InvocationTargetException ex) { } } } return numberOperator; } private static boolean isSearchHierarchicalFieldDescriptionCorrect(String[] fieldPath, Field searchEntityField, Field[] entityFields) { String fieldName = fieldPath[0]; if (fieldPath.length == 1) { return isSearchFieldDescriptionCorrect(fieldName, searchEntityField, entityFields); } else { Class clazz = getFieldClass(fieldName, entityFields); if (clazz != null) { Field[] subFields = clazz.getDeclaredFields(); String[] subFieldPath = Arrays.copyOfRange(fieldPath, 1, fieldPath.length); return isSearchHierarchicalFieldDescriptionCorrect(subFieldPath, searchEntityField, subFields); } else { return false; } } } private static Class getFieldClass(String fieldName, Field[] entityFields) { int index = getIndex(fieldName, entityFields); return (index != -1) ? entityFields[index].getType() : null; } private static boolean isSearchFieldDescriptionCorrect(String fieldName, Field searchEntityField, Field[] entityFields) { int index = getIndex(fieldName, entityFields); return (index != -1) && isFieldTypeEquals(searchEntityField, entityFields[index]); } private static int getIndex(String fieldName, Field[] entityFields) { int index = 0; for (Field field : entityFields) { if (fieldName.equals(field.getName())) { return index; } index++; } return -1; } private static boolean isFieldTypeEquals(Field searchEntityField, Field entityField) { return searchEntityField.getType().equals(entityField.getType()); } }