1414 */ 
1515package  org .jnosql .artemis .util ;
1616
17+ import  org .jnosql .artemis .AttributeConverter ;
1718import  org .jnosql .artemis .Converters ;
1819import  org .jnosql .artemis .reflection .ClassRepresentation ;
1920import  org .jnosql .artemis .reflection .FieldRepresentation ;
2021import  org .jnosql .diana .api .Value ;
2122
2223import  java .lang .reflect .Field ;
24+ import  java .lang .reflect .ParameterizedType ;
25+ import  java .lang .reflect .Type ;
2326import  java .util .Optional ;
27+ import  java .util .function .Function ;
28+ import  java .util .function .Predicate ;
2429
2530public  class  ConverterUtil  {
2631
@@ -30,7 +35,7 @@ private ConverterUtil() {
3035    }
3136
3237    /** 
33-      * Converts 
38+      * Converts the value to database format  
3439     * 
3540     * @param value          the value 
3641     * @param representation the class representation 
@@ -48,24 +53,49 @@ public static Object getValue(Object value, ClassRepresentation representation,
4853    }
4954
5055    /** 
51-      * Converts the value from the field with {@link FieldRepresentation} 
52-      * @param value the value to be converted 
56+      * Converts the value from the field with {@link FieldRepresentation} to database format 
57+      * 
58+      * @param value      the value to be converted 
5359     * @param converters the converter 
54-      * @param field the field 
60+      * @param field       the field 
5561     * @return tje value converted 
5662     */ 
5763    public  static  Object  getValue (Object  value , Converters  converters , FieldRepresentation  field ) {
5864        Field  nativeField  = field .getNativeField ();
5965        if  (!nativeField .getType ().equals (value .getClass ())) {
6066            return  field .getConverter ()
6167                    .map (converters ::get )
62-                     .map (a  ->  a . convertToDatabaseColumn (value ))
68+                     .map (useConverter (value ))
6369                    .orElseGet (() -> Value .of (value ).get (nativeField .getType ()));
6470        }
6571
6672        return  field .getConverter ()
6773                .map (converters ::get )
68-                 .map (a  ->  a . convertToDatabaseColumn (value ))
74+                 .map (useConverter (value ))
6975                .orElse (value );
7076    }
77+ 
78+     private  static  Function <AttributeConverter , Object > useConverter (Object  value ) {
79+         return  a  -> {
80+             if  (isNative (value ).test (a )) {
81+                 return  value ;
82+             }
83+             return  a .convertToDatabaseColumn (value );
84+         };
85+     }
86+ 
87+     private  static  Predicate <AttributeConverter > isNative (Object  value ) {
88+         return  a  -> getGenericInterface (a ).getActualTypeArguments ()[1 ].equals (value .getClass ());
89+     }
90+ 
91+ 
92+     private  static  ParameterizedType  getGenericInterface (AttributeConverter  a ) {
93+         for  (Type  genericInterface  : a .getClass ().getGenericInterfaces ()) {
94+             if  (ParameterizedType .class .isAssignableFrom (genericInterface .getClass ()) &&
95+                     ParameterizedType .class .cast (genericInterface ).getRawType ().equals (AttributeConverter .class )) {
96+                 return  (ParameterizedType ) genericInterface ;
97+             }
98+         }
99+         throw  new  IllegalArgumentException ("It does not found AttributeConverter implementation to this converter" );
100+     }
71101}
0 commit comments