diff --git a/spring-expression/src/main/java/org/springframework/expression/spel/support/ReflectivePropertyAccessor.java b/spring-expression/src/main/java/org/springframework/expression/spel/support/ReflectivePropertyAccessor.java index d6a8f6e218..ae05a0e8fd 100644 --- a/spring-expression/src/main/java/org/springframework/expression/spel/support/ReflectivePropertyAccessor.java +++ b/spring-expression/src/main/java/org/springframework/expression/spel/support/ReflectivePropertyAccessor.java @@ -83,7 +83,10 @@ public class ReflectivePropertyAccessor implements PropertyAccessor { private final Map typeDescriptorCache = new ConcurrentHashMap(64); - private InvokerPair lastReadInvokerPair; + private final Map, Method[]> sortedMethodsCache = + new ConcurrentHashMap, Method[]>(64); + + private volatile InvokerPair lastReadInvokerPair; /** @@ -277,6 +280,7 @@ public class ReflectivePropertyAccessor implements PropertyAccessor { throw new AccessException("Type conversion failure", evaluationException); } } + PropertyCacheKey cacheKey = new PropertyCacheKey(type, name, target instanceof Class); Member cachedMember = this.writerCache.get(cacheKey); @@ -400,7 +404,7 @@ public class ReflectivePropertyAccessor implements PropertyAccessor { private Method findMethodForProperty(String[] methodSuffixes, String prefix, Class clazz, boolean mustBeStatic, int numberOfParams, Set> requiredReturnTypes) { - Method[] methods = getSortedClassMethods(clazz); + Method[] methods = getSortedMethods(clazz); for (String methodSuffix : methodSuffixes) { for (Method method : methods) { if (isCandidateForProperty(method, clazz) && method.getName().equals(prefix + methodSuffix) && @@ -428,16 +432,20 @@ public class ReflectivePropertyAccessor implements PropertyAccessor { } /** - * Return class methods ordered with non bridge methods appearing higher. + * Return class methods ordered with non-bridge methods appearing higher. */ - private Method[] getSortedClassMethods(Class clazz) { - Method[] methods = clazz.getMethods(); - Arrays.sort(methods, new Comparator() { - @Override - public int compare(Method o1, Method o2) { - return (o1.isBridge() == o2.isBridge()) ? 0 : (o1.isBridge() ? 1 : -1); - } - }); + private Method[] getSortedMethods(Class clazz) { + Method[] methods = this.sortedMethodsCache.get(clazz); + if (methods == null) { + methods = clazz.getMethods(); + Arrays.sort(methods, new Comparator() { + @Override + public int compare(Method o1, Method o2) { + return (o1.isBridge() == o2.isBridge()) ? 0 : (o1.isBridge() ? 1 : -1); + } + }); + this.sortedMethodsCache.put(clazz, methods); + } return methods; }