1
22
23 package com.liferay.portal.kernel.util;
24
25 import com.liferay.portal.kernel.log.Log;
26 import com.liferay.portal.kernel.log.LogFactoryUtil;
27
28 import java.lang.reflect.Array;
29 import java.lang.reflect.InvocationTargetException;
30 import java.lang.reflect.Method;
31
32 import java.util.ArrayList;
33 import java.util.List;
34
35
42 public class MethodInvoker {
43
44 public static Object invoke(MethodWrapper methodWrapper)
45 throws ClassNotFoundException, IllegalAccessException,
46 InstantiationException, InvocationTargetException,
47 NoSuchFieldException, NoSuchMethodException {
48
49 return invoke(methodWrapper, true);
50 }
51
52 public static Object invoke(
53 MethodWrapper methodWrapper, boolean newInstance)
54 throws ClassNotFoundException, IllegalAccessException,
55 InstantiationException, InvocationTargetException,
56 NoSuchFieldException, NoSuchMethodException {
57
58 ClassLoader contextClassLoader =
59 Thread.currentThread().getContextClassLoader();
60
61 String className = methodWrapper.getClassName();
62 String methodName = methodWrapper.getMethodName();
63 Object[] args = methodWrapper.getArgs();
64
65 List<Class<?>> parameterTypes = new ArrayList<Class<?>>();
66
67 for (int i = 0; i < args.length; i++) {
68 if (args[i] == null) {
69 _log.error(
70 "Cannot invoke " + className + " " + methodName +
71 " on position " + i + " because it is null");
72 }
73
74 Class<?> argClass = args[i].getClass();
75
76 if (ClassUtil.isSubclass(argClass, PrimitiveWrapper.class)) {
77 parameterTypes.add(
78 (Class<?>)argClass.getField("TYPE").get(args[i]));
79
80 MethodKey methodKey = new MethodKey(
81 argClass.getName(), "getValue", null);
82
83 Method method = MethodCache.get(methodKey);
84
85 args[i] = method.invoke(args[i], (Object[])null);
86 }
87 else if (args[i] instanceof NullWrapper) {
88 NullWrapper nullWrapper = (NullWrapper)args[i];
89
90 String wrappedClassName = nullWrapper.getClassName();
91
92 if (wrappedClassName.startsWith(StringPool.OPEN_BRACKET) &&
93 wrappedClassName.endsWith(StringPool.SEMICOLON)) {
94
95 wrappedClassName = wrappedClassName.substring(
96 2, wrappedClassName.length() - 1);
97
98 Class<?> wrappedClass = contextClassLoader.loadClass(
99 wrappedClassName);
100
101 parameterTypes.add(
102 Array.newInstance(wrappedClass, 0).getClass());
103 }
104 else {
105 Class<?> wrappedClass = contextClassLoader.loadClass(
106 wrappedClassName);
107
108 parameterTypes.add(wrappedClass);
109 }
110
111 args[i] = null;
112 }
113 else {
114 parameterTypes.add(argClass);
115 }
116 }
117
118 Object classObj = contextClassLoader.loadClass(className);
119
120 if (newInstance) {
121 classObj = ((Class<?>)classObj).newInstance();
122 }
123
124 Method method = null;
125
126 try {
127 MethodKey methodKey = new MethodKey(
128 methodWrapper.getClassName(), methodWrapper.getMethodName(),
129 parameterTypes.toArray(new Class[parameterTypes.size()]));
130
131 method = MethodCache.get(methodKey);
132 }
133 catch (NoSuchMethodException nsme) {
134 Method[] methods = null;
135
136 if (newInstance) {
137 methods = classObj.getClass().getMethods();
138 }
139 else {
140 methods = ((Class<?>)classObj).getMethods();
141 }
142
143 for (int i = 0; i < methods.length; i++) {
144 Class<?>[] methodParameterTypes =
145 methods[i].getParameterTypes();
146
147 if (methods[i].getName().equals(methodName) &&
148 methodParameterTypes.length == parameterTypes.size()) {
149
150 boolean correctParams = true;
151
152 for (int j = 0; j < parameterTypes.size(); j++) {
153 Class<?> a = parameterTypes.get(j);
154 Class<?> b = methodParameterTypes[j];
155
156 if (!ClassUtil.isSubclass(a, b)) {
157 correctParams = false;
158
159 break;
160 }
161 }
162
163 if (correctParams) {
164 method = methods[i];
165
166 break;
167 }
168 }
169 }
170
171 if (method == null) {
172 throw nsme;
173 }
174 }
175
176 Object returnObj = null;
177
178 if (method != null) {
179 returnObj = method.invoke(classObj, args);
180 }
181
182 return returnObj;
183 }
184
185 private static Log _log = LogFactoryUtil.getLog(MethodInvoker.class);
186
187 }