@ -1,5 +1,5 @@
@@ -1,5 +1,5 @@
/ *
* Copyright 2002 - 2012 the original author or authors .
* Copyright 2002 - 2014 the original author or authors .
*
* Licensed under the Apache License , Version 2 . 0 ( the "License" ) ;
* you may not use this file except in compliance with the License .
@ -31,20 +31,23 @@ import org.springframework.util.ReflectionUtils;
@@ -31,20 +31,23 @@ import org.springframework.util.ReflectionUtils;
* Converts an entity identifier to a entity reference by calling a static finder method
* on the target entity type .
*
* < p > For this converter to match , the finder method must be public , static , have the signature
* < p > For this converter to match , the finder method must be static , have the signature
* { @code find [ EntityName ] ( [ IdType ] ) } , and return an instance of the desired entity type .
*
* @author Keith Donald
* @author Juergen Hoeller
* @since 3 . 0
* /
final class IdToEntityConverter implements ConditionalGenericConverter {
private final ConversionService conversionService ;
public IdToEntityConverter ( ConversionService conversionService ) {
this . conversionService = conversionService ;
}
@Override
public Set < ConvertiblePair > getConvertibleTypes ( ) {
return Collections . singleton ( new ConvertiblePair ( Object . class , Object . class ) ) ;
@ -53,7 +56,8 @@ final class IdToEntityConverter implements ConditionalGenericConverter {
@@ -53,7 +56,8 @@ final class IdToEntityConverter implements ConditionalGenericConverter {
@Override
public boolean matches ( TypeDescriptor sourceType , TypeDescriptor targetType ) {
Method finder = getFinder ( targetType . getType ( ) ) ;
return finder ! = null & & this . conversionService . canConvert ( sourceType , TypeDescriptor . valueOf ( finder . getParameterTypes ( ) [ 0 ] ) ) ;
return ( finder ! = null & &
this . conversionService . canConvert ( sourceType , TypeDescriptor . valueOf ( finder . getParameterTypes ( ) [ 0 ] ) ) ) ;
}
@Override
@ -62,20 +66,33 @@ final class IdToEntityConverter implements ConditionalGenericConverter {
@@ -62,20 +66,33 @@ final class IdToEntityConverter implements ConditionalGenericConverter {
return null ;
}
Method finder = getFinder ( targetType . getType ( ) ) ;
Object id = this . conversionService . convert ( source , sourceType , TypeDescriptor . valueOf ( finder . getParameterTypes ( ) [ 0 ] ) ) ;
Object id = this . conversionService . convert (
source , sourceType , TypeDescriptor . valueOf ( finder . getParameterTypes ( ) [ 0 ] ) ) ;
return ReflectionUtils . invokeMethod ( finder , source , id ) ;
}
private Method getFinder ( Class < ? > entityClass ) {
String finderMethod = "find" + getEntityName ( entityClass ) ;
Method [ ] methods = entityClass . getDeclaredMethods ( ) ;
Method [ ] methods ;
boolean localOnlyFiltered ;
try {
methods = entityClass . getDeclaredMethods ( ) ;
localOnlyFiltered = true ;
}
catch ( SecurityException ex ) {
// Not allowed to access non-public methods...
// Fallback: check locally declared public methods only.
methods = entityClass . getMethods ( ) ;
localOnlyFiltered = false ;
}
for ( Method method : methods ) {
if ( Modifier . isStatic ( method . getModifiers ( ) ) & & method . getParameterTypes ( ) . length = = 1 & & method . getReturnType ( ) . equals ( entityClass ) ) {
if ( method . getName ( ) . equals ( finderMethod ) ) {
if ( Modifier . isStatic ( method . getModifiers ( ) ) & & method . getName ( ) . equals ( finderMethod ) & &
method . getParameterTypes ( ) . length = = 1 & & method . getReturnType ( ) . equals ( entityClass ) & &
( localOnlyFiltered | | method . getDeclaringClass ( ) . equals ( entityClass ) ) ) {
return method ;
}
}
}
return null ;
}