Author: jochen
Date: Mon May 22 13:31:57 2006
New Revision: 408757
URL: http://svn.apache.org/viewvc?rev=408757&view=rev
Log:
Added support for method overloading.
Modified:
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/ReflectiveXmlRpcMetaDataHandler.java
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/Util.java
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/AbstractReflectiveHandlerMapping.java
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/ReflectiveXmlRpcHandler.java
Modified:
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/ReflectiveXmlRpcMetaDataHandler.java
URL:
http://svn.apache.org/viewvc/webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/ReflectiveXmlRpcMetaDataHandler.java?rev=408757&r1=408756&r2=408757&view=diff
==============================================================================
---
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/ReflectiveXmlRpcMetaDataHandler.java
(original)
+++
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/ReflectiveXmlRpcMetaDataHandler.java
Mon May 22 13:31:57 2006
@@ -37,7 +37,7 @@
* messages only.
* @param pInstance The instance, which will be invoked for
* executing the handler.
- * @param pMethod The method, which will be invoked for
+ * @param pMethods The method, which will be invoked for
* executing the handler.
* @param pSignatures The signature, which will be returned by
* [EMAIL PROTECTED] #getSignatures()}.
@@ -45,9 +45,9 @@
* by [EMAIL PROTECTED] #getMethodHelp()}.
*/
public ReflectiveXmlRpcMetaDataHandler(AbstractReflectiveHandlerMapping
pMapping,
- Class pClass, Object pInstance, Method pMethod,
+ Class pClass, Object pInstance, Method[] pMethods,
String[][] pSignatures, String pMethodHelp) {
- super(pMapping, pClass, pInstance, pMethod);
+ super(pMapping, pClass, pInstance, pMethods);
signatures = pSignatures;
methodHelp = pMethodHelp;
}
Modified:
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/Util.java
URL:
http://svn.apache.org/viewvc/webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/Util.java?rev=408757&r1=408756&r2=408757&view=diff
==============================================================================
---
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/Util.java
(original)
+++
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/metadata/Util.java
Mon May 22 13:31:57 2006
@@ -17,6 +17,7 @@
import java.io.Serializable;
import java.lang.reflect.Method;
+import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;
@@ -94,13 +95,30 @@
return null;
}
- /** Returns a signature for the given method.
- * @param pMethod Method, for which a signature is
+ /** Returns a signature for the given methods.
+ * @param pMethods Methods, for which a signature is
* being queried.
* @return Signature string, or null, if no signature
* is available.
*/
- public static String[] getSignature(Method pMethod) {
+ public static String[][] getSignature(Method[] pMethods) {
+ final List result = new ArrayList();
+ for (int i = 0; i < pMethods.length; i++) {
+ String[] sig = getSignature(pMethods[i]);
+ if (sig != null) {
+ result.add(sig);
+ }
+ }
+ return (String[][]) result.toArray(new String[result.size()][]);
+ }
+
+ /** Returns a signature for the given methods.
+ * @param pMethod Method, for which a signature is
+ * being queried.
+ * @return Signature string, or null, if no signature
+ * is available.
+ */
+ public static String[] getSignature(Method pMethod) {
Class[] paramClasses = pMethod.getParameterTypes();
String[] sig = new String[paramClasses.length + 1];
String s = getSignatureType(pMethod.getReturnType());
@@ -118,7 +136,35 @@
return sig;
}
- /** Returns a help string for the given method, which
+ /** Returns a help string for the given method, which
+ * is applied to the given class.
+ */
+ public static String getMethodHelp(Class pClass, Method[] pMethods) {
+ final List result = new ArrayList();
+ for (int i = 0; i < pMethods.length; i++) {
+ String help = getMethodHelp(pClass, pMethods[i]);
+ if (help != null) {
+ result.add(help);
+ }
+ }
+ switch (result.size()) {
+ case 0:
+ return null;
+ case 1:
+ return (String) result.get(0);
+ default:
+ StringBuffer sb = new StringBuffer();
+ for (int i = 0; i < result.size(); i++) {
+ sb.append(i+1);
+ sb.append(": ");
+ sb.append(result.get(i));
+ sb.append("\n");
+ }
+ return sb.toString();
+ }
+ }
+
+ /** Returns a help string for the given method, which
* is applied to the given class.
*/
public static String getMethodHelp(Class pClass, Method pMethod) {
@@ -138,4 +184,78 @@
sb.append(").");
return sb.toString();
}
+
+ /** Returns, whether the given methods signature is matched by
+ * the given parameter set.
+ */
+ public static boolean isMatching(Method method, Object[] args) {
+ Class[] parameterClasses = method.getParameterTypes();
+ if (parameterClasses.length != args.length) {
+ return false;
+ }
+ for (int i = 0; i < args.length; i++) {
+ if (!isMatching(parameterClasses[i], args[i])) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /** Returns, whether the given parameter matches the given
+ * type.
+ */
+ public static boolean isMatching(Class pParameterType, Object pArg) {
+ if (pArg == null) {
+ return !pParameterType.isPrimitive();
+ }
+ final Class c;
+ if (pParameterType.isPrimitive()) {
+ c = getObjectClass(pParameterType);
+ } else {
+ c = pParameterType;
+ }
+ return c.isAssignableFrom(pArg.getClass());
+ }
+
+ /** Given a primitive class, returns the corresponding object class.
+ */
+ public static Class getObjectClass(Class pPrimitiveClass) {
+ if (byte.class.equals(pPrimitiveClass)) {
+ return Byte.class;
+ } else if (short.class.equals(pPrimitiveClass)) {
+ return Short.class;
+ } else if (int.class.equals(pPrimitiveClass)) {
+ return Integer.class;
+ } else if (long.class.equals(pPrimitiveClass)) {
+ return Long.class;
+ } else if (float.class.equals(pPrimitiveClass)) {
+ return Float.class;
+ } else if (double.class.equals(pPrimitiveClass)) {
+ return Double.class;
+ } else if (char.class.equals(pPrimitiveClass)) {
+ return Character.class;
+ } else if (boolean.class.equals(pPrimitiveClass)) {
+ return Boolean.class;
+ } else {
+ throw new IllegalStateException("Invalid primitive class: " +
pPrimitiveClass.getName());
+ }
+ }
+
+ /** Returns a signature for the given parameter set. This is used
+ * in error messages.
+ */
+ public static String getSignature(Object[] args) {
+ StringBuffer sb = new StringBuffer();
+ for (int i = 0; i < args.length; i++) {
+ if (i > 0) {
+ sb.append(", ");
+ }
+ if (args[i] == null) {
+ sb.append("null");
+ } else {
+ sb.append(args[i].getClass().getName());
+ }
+ }
+ return sb.toString();
+ }
}
Modified:
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/AbstractReflectiveHandlerMapping.java
URL:
http://svn.apache.org/viewvc/webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/AbstractReflectiveHandlerMapping.java?rev=408757&r1=408756&r2=408757&view=diff
==============================================================================
---
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/AbstractReflectiveHandlerMapping.java
(original)
+++
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/AbstractReflectiveHandlerMapping.java
Mon May 22 13:31:57 2006
@@ -91,6 +91,7 @@
if (pInstance == null) {
throw new NullPointerException("The object instance must not be
null.");
}
+ Map map = new HashMap();
Method[] methods = pType.getMethods();
for (int i = 0; i < methods.length; i++) {
final Method method = methods[i];
@@ -107,9 +108,23 @@
continue; // Ignore methods from Object.class
}
String name = pKey + "." + method.getName();
- if (!pMap.containsKey(name)) {
- pMap.put(name, newXmlRpcHandler(pType, pInstance, method));
+ Method[] mArray;
+ Method[] oldMArray = (Method[]) map.get(name);
+ if (oldMArray == null) {
+ mArray = new Method[]{method};
+ } else {
+ mArray = new Method[oldMArray.length+1];
+ System.arraycopy(oldMArray, 0, mArray, 0, oldMArray.length);
+ mArray[oldMArray.length] = method;
}
+ map.put(name, mArray);
+ }
+
+ for (Iterator iter = map.entrySet().iterator(); iter.hasNext(); ) {
+ Map.Entry entry = (Map.Entry) iter.next();
+ String name = (String) entry.getKey();
+ Method[] mArray = (Method[]) entry.getValue();
+ pMap.put(name, newXmlRpcHandler(pType, pInstance, mArray));
}
}
@@ -120,33 +135,33 @@
* @param pInstance The object, which is being invoked by
* the created handler. Typically an instance of
* <code>pClass</code>.
- * @param pMethod The method being invoked.
+ * @param pMethods The method being invoked.
*/
protected XmlRpcHandler newXmlRpcHandler(final Class pClass,
- final Object pInstance, final Method pMethod) {
+ final Object pInstance, final Method[] pMethods) {
if (pInstance == null) {
throw new NullPointerException("The object instance must not be
null.");
}
- String[] sig = getSignature(pMethod);
- String help = getMethodHelp(pClass, pMethod);
+ String[][] sig = getSignature(pMethods);
+ String help = getMethodHelp(pClass, pMethods);
if (sig == null || help == null) {
- return new ReflectiveXmlRpcHandler(this, pClass, pInstance,
pMethod);
+ return new ReflectiveXmlRpcHandler(this, pClass, pInstance,
pMethods);
}
return new ReflectiveXmlRpcMetaDataHandler(this, pClass, pInstance,
- pMethod, new String[][]{sig}, help);
+ pMethods, sig, help);
}
/** Creates a signature for the given method.
*/
- protected String[] getSignature(Method pMethod) {
- return Util.getSignature(pMethod);
+ protected String[][] getSignature(Method[] pMethods) {
+ return Util.getSignature(pMethods);
}
/** Creates a help string for the given method, when applied
* to the given class.
*/
- protected String getMethodHelp(Class pClass, Method pMethod) {
- return Util.getMethodHelp(pClass, pMethod);
+ protected String getMethodHelp(Class pClass, Method[] pMethods) {
+ return Util.getMethodHelp(pClass, pMethods);
}
/** Returns the [EMAIL PROTECTED] XmlRpcHandler} with the given name.
Modified:
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/ReflectiveXmlRpcHandler.java
URL:
http://svn.apache.org/viewvc/webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/ReflectiveXmlRpcHandler.java?rev=408757&r1=408756&r2=408757&view=diff
==============================================================================
---
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/ReflectiveXmlRpcHandler.java
(original)
+++
webservices/xmlrpc/trunk/server/src/main/java/org/apache/xmlrpc/server/ReflectiveXmlRpcHandler.java
Mon May 22 13:31:57 2006
@@ -22,6 +22,7 @@
import org.apache.xmlrpc.XmlRpcHandler;
import org.apache.xmlrpc.XmlRpcRequest;
import org.apache.xmlrpc.common.XmlRpcNotAuthorizedException;
+import org.apache.xmlrpc.metadata.Util;
import
org.apache.xmlrpc.server.AbstractReflectiveHandlerMapping.AuthenticationHandler;
@@ -31,7 +32,7 @@
private final AbstractReflectiveHandlerMapping mapping;
private final Class clazz;
private final Object instance;
- private final Method method;
+ private final Method[] methods;
/** Creates a new instance.
* @param pMapping The mapping, which creates this handler.
@@ -41,15 +42,15 @@
* messages only.
* @param pInstance The instance, which will be invoked for
* executing the handler.
- * @param pMethod The method, which will be invoked for
+ * @param pMethods The method, which will be invoked for
* executing the handler.
*/
public ReflectiveXmlRpcHandler(AbstractReflectiveHandlerMapping
pMapping,
- Class pClass, Object pInstance, Method pMethod)
{
+ Class pClass, Object pInstance, Method[]
pMethods) {
mapping = pMapping;
clazz = pClass;
instance = pInstance;
- method = pMethod;
+ methods = pMethods;
}
public Object execute(XmlRpcRequest pRequest) throws XmlRpcException {
@@ -61,20 +62,33 @@
for (int j = 0; j < args.length; j++) {
args[j] = pRequest.getParameter(j);
}
- try {
- return method.invoke(instance, args);
+ if (methods.length == 1) {
+ return invoke(methods[0], args);
+ } else {
+ for (int i = 0; i < methods.length; i++) {
+ if (Util.isMatching(methods[i], args)) {
+ return invoke(methods[i], args);
+ }
+ }
+ throw new XmlRpcException("No method matching arguments: " +
Util.getSignature(args));
+ }
+ }
+
+ private Object invoke(Method pMethod, Object[] pArgs) throws
XmlRpcException {
+ try {
+ return pMethod.invoke(instance, pArgs);
} catch (IllegalAccessException e) {
throw new XmlRpcException("Illegal access to method "
- + method.getName() + " in class "
+ + pMethod.getName() + " in class "
+ clazz.getName(), e);
} catch (IllegalArgumentException e) {
throw new XmlRpcException("Illegal argument for method "
- + method.getName() + " in class "
+ + pMethod.getName() + " in class "
+ clazz.getName(), e);
} catch (InvocationTargetException e) {
Throwable t = e.getTargetException();
throw new XmlRpcException("Failed to invoke method "
- + method.getName() + " in class "
+ + pMethod.getName() + " in class "
+ clazz.getName() + ": "
+ t.getMessage(), t);
}
---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]