001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: */
017:
018: package org.apache.naming.factory.webservices;
019:
020: import java.lang.reflect.InvocationHandler;
021: import java.lang.reflect.InvocationTargetException;
022: import java.lang.reflect.Method;
023: import java.rmi.Remote;
024: import java.util.Hashtable;
025: import java.util.Iterator;
026:
027: import javax.xml.namespace.QName;
028: import javax.xml.rpc.Service;
029: import javax.xml.rpc.ServiceException;
030:
031: /**
032: * Object proxy for Web Services.
033: *
034: * @author Fabien Carrion
035: */
036:
037: public class ServiceProxy implements InvocationHandler {
038:
039: /**
040: * Service object.
041: * used for delegation
042: */
043: private Service service = null;
044:
045: /**
046: * changing behavior to method : Service.getPort(QName, Class)
047: */
048: private static Method portQNameClass = null;
049:
050: /**
051: * changing behavior to method : Service.getPort(Class)
052: */
053: private static Method portClass = null;
054:
055: /**
056: * PortComponentRef list
057: */
058: private Hashtable portComponentRef = null;
059:
060: /**
061: * Constructs a new ServiceProxy wrapping given Service instance.
062: * @param service the wrapped Service instance
063: * @throws ServiceException should be never thrown
064: */
065: public ServiceProxy(Service service) throws ServiceException {
066: this .service = service;
067: try {
068: portQNameClass = Service.class.getDeclaredMethod("getPort",
069: new Class[] { QName.class, Class.class });
070: portClass = Service.class.getDeclaredMethod("getPort",
071: new Class[] { Class.class });
072: } catch (Exception e) {
073: throw new ServiceException(e);
074: }
075: }
076:
077: /**
078: * @see java.lang.reflect.InvocationHandler#invoke(java.lang.Object, java.lang.reflect.Method, java.lang.Object[])
079: */
080: public Object invoke(Object proxy, Method method, Object[] args)
081: throws Throwable {
082:
083: if (portQNameClass.equals(method)) {
084: return getProxyPortQNameClass(args);
085: }
086:
087: if (portClass.equals(method)) {
088: return getProxyPortClass(args);
089: }
090:
091: try {
092: return method.invoke(service, args);
093: } catch (InvocationTargetException ite) {
094: throw ite.getTargetException();
095: }
096: }
097:
098: /**
099: * @param args Method call arguments
100: * @return Returns the correct Port
101: * @throws ServiceException if port's QName is an unknown Port (not defined in WSDL).
102: */
103: private Object getProxyPortQNameClass(Object[] args)
104: throws ServiceException {
105: QName name = (QName) args[0];
106: String nameString = name.getLocalPart();
107: Class serviceendpointClass = (Class) args[1];
108:
109: for (Iterator ports = service.getPorts(); ports.hasNext();) {
110: QName portName = (QName) ports.next();
111: String portnameString = portName.getLocalPart();
112: if (portnameString.equals(nameString)) {
113: return service.getPort(name, serviceendpointClass);
114: }
115: }
116:
117: // no ports have been found
118: throw new ServiceException("Port-component-ref : " + name
119: + " not found");
120: }
121:
122: /**
123: * @param portComponentRef List
124: */
125: public void setPortComponentRef(Hashtable portComponentRef) {
126: this .portComponentRef = portComponentRef;
127: }
128:
129: /**
130: * @param args Method call arguments
131: * @return Returns the correct Port
132: * @throws ServiceException if port's QName is an unknown Port
133: */
134: private Remote getProxyPortClass(Object[] args)
135: throws ServiceException {
136: Class serviceendpointClass = (Class) args[0];
137:
138: if (this .portComponentRef == null)
139: return service.getPort(serviceendpointClass);
140:
141: QName portname = (QName) this.portComponentRef
142: .get(serviceendpointClass.getName());
143: if (portname != null) {
144: return service.getPort(portname, serviceendpointClass);
145: } else {
146: return service.getPort(serviceendpointClass);
147: }
148: }
149:
150: }
|