View Javadoc

    1   package org.codehaus.xfire.client;
    2
    3   import java.lang.reflect.InvocationHandler;
    4   import java.lang.reflect.Method;
    5   import java.lang.reflect.Proxy;
    6   import java.util.Arrays;
    7
    8   import org.apache.commons.logging.Log;
    9   import org.apache.commons.logging.LogFactory;
    10  import org.codehaus.xfire.XFireException;
    11  import org.codehaus.xfire.service.OperationInfo;
    12
    13  /***
    14   * Proxy implementation for XFire SOAP clients.  Applications will generally use <code>XFireProxyFactory</code> to
    15   * create proxy clients.
    16   *
    17   * @author <a href="mailto:poutsma@mac.com">Arjen Poutsma</a>
    18   * @see XFireProxyFactory#create
    19   */
    20  public class XFireProxy
    21          implements InvocationHandler
    22  {
    23      private static final Log log = LogFactory.getLog(XFireProxy.class);
    24      private Client client;
    25
    26      XFireProxy(Client client)
    27      {
    28          this.client = client;
    29      }
    30
    31      /***
    32       * Handles the object invocation.
    33       *
    34       * @param proxy  the proxy object to invoke
    35       * @param method the method to call
    36       * @param args   the arguments to the proxy object
    37       */
    38      public Object invoke(Object proxy, Method method, Object[] args)
    39              throws Throwable
    40      {
    41          String methodName = method.getName();
    42          Class[] parameterTypes = method.getParameterTypes();
    43          if (log.isDebugEnabled())
    44          {
    45              log.debug("Method [" + methodName + "] " + ((args == null) ? "" : Arrays.asList(args).toString()));
    46          }
    47
    48          Object result = handleCanonicalMethods(methodName, parameterTypes, args);
    49
    50          if (result == null)
    51          {
    52              result = handleRequest(methodName, args);
    53          }
    54          if (log.isDebugEnabled())
    55          {
    56              log.debug("Result [" + String.valueOf(result) + "]");
    57          }
    58          return result;
    59      }
    60
    61      private Object handleRequest(String methodName, Object[] args)
    62              throws XFireException
    63      {
    64          OperationInfo op = client.getService().getServiceInfo().getOperation(methodName);
    65
    66          Object[] response = (Object[]) client.invoke(op, args);
    67
    68          if (response.length > 0)
    69              return response[0];
    70          else
    71              return null;
    72      }
    73
    74      /***
    75       * Handles canonical method calls such as <code>equals</code>, <code>hashCode</code>, and <code>toString</code>.
    76       *
    77       * @param methodName the method name.
    78       * @param params     the parameter types.
    79       * @param args       the arguments
    80       * @return the result, if <code>methodName</code> is a canonical method; or <code>null</code> if not.
    81       */
    82      private Object handleCanonicalMethods(String methodName, Class[] params, Object[] args)
    83      {
    84          if (methodName.equals("equals") &&
    85                  params.length == 1
    86                  && params[0].equals(Object.class))
    87          {
    88              Object other = args[0];
    89              if (other == null ||
    90                      !Proxy.isProxyClass(other.getClass()) ||
    91                      !(Proxy.getInvocationHandler(other) instanceof XFireProxy))
    92              {
    93                  return Boolean.FALSE;
    94              }
    95
    96              XFireProxy otherClient = (XFireProxy) Proxy.getInvocationHandler(other);
    97
    98              return new Boolean(otherClient == this);
    99          }
    100         else if (methodName.equals("hashCode") && params.length == 0)
    101         {
    102             return new Integer(hashCode());
    103         }
    104         else if (methodName.equals("toString") && params.length == 0)
    105         {
    106             return "XFireProxy[" + client.getUrl() + "]";
    107         }
    108         return null;
    109     }
    110 }
    111