Commits

plightbo  committed da78147

if a method isn't being called, let's remember that (2X speedup in monthlist)

git-svn-id: http://svn.opensymphony.com/svn/xwork/trunk@108e221344d-f017-0410-9bd5-d282ab1896d7

  • Participants
  • Parent commits 9e1e587

Comments (0)

Files changed (1)

File src/java/com/opensymphony/xwork/util/CompoundRootAccessor.java

 import java.beans.IntrospectionException;
 import java.util.Iterator;
 import java.util.Map;
+import java.util.HashMap;
+import java.util.Arrays;
 
 
 /**
 
     //~ Methods ////////////////////////////////////////////////////////////////
 
+    private static Map invalidMethods = new HashMap();
+
     public void setProperty(Map context, Object target, Object name, Object value) throws OgnlException {
         CompoundRoot root = (CompoundRoot) target;
         OgnlContext ognlContext = (OgnlContext) context;
         for (Iterator iterator = root.iterator(); iterator.hasNext();) {
             Object o = iterator.next();
 
-            try {
-                Object value = OgnlRuntime.callMethod((OgnlContext) context, o, name, name, objects);
+            Class clazz = o.getClass();
+            Class[] argTypes = getArgTypes(objects);
+            CompoundRootAccessor.MethodCall mc = new CompoundRootAccessor.MethodCall(clazz, name, argTypes);
+            if (!invalidMethods.containsKey(mc)) {
+                try {
+                    Object value = OgnlRuntime.callMethod((OgnlContext) context, o, name, name, objects);
 
-                if (value != null) {
-                    return value;
+                    if (value != null) {
+                        return value;
+                    }
+                } catch (OgnlException e) {
+                    // try the next one
+                    invalidMethods.put(mc, Boolean.TRUE);
                 }
-            } catch (OgnlException e) {
-                // try the next one
             }
         }
 
         return null;
     }
 
+    private Class[] getArgTypes(Object[] args) {
+        if (args == null) {
+            return new Class[0];
+        }
+
+        Class[] classes = new Class[args.length];
+        for (int i = 0; i < args.length; i++) {
+            Object arg = args[i];
+            classes[i] = arg.getClass();
+        }
+
+        return classes;
+    }
+
     public Object callStaticMethod(Map transientVars, Class aClass, String s, Object[] objects) throws MethodFailedException {
         return null;
     }
 
         return Thread.currentThread().getContextClassLoader().loadClass(className);
     }
+
+    static class MethodCall {
+        Class clazz;
+        String name;
+        Class[] args;
+        int hash;
+
+        public MethodCall(Class clazz, String name, Class[] args) {
+            this.clazz = clazz;
+            this.name = name;
+            this.args = args;
+            this.hash = clazz.hashCode() + name.hashCode();
+
+            for (int i = 0; i < args.length; i++) {
+                Class arg = args[i];
+                hash += arg.hashCode();
+            }
+        }
+
+        public int hashCode() {
+            return hash;
+        }
+
+        public boolean equals(Object obj) {
+            MethodCall mc = (CompoundRootAccessor.MethodCall) obj;
+            return (mc.clazz.equals(clazz) && mc.name.equals(name) && Arrays.equals(mc.args, args));
+        }
+    }
 }