1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/src/share/jaxws_classes/com/sun/xml/internal/ws/api/WSService.java Wed Apr 27 01:27:09 2016 +0800 1.3 @@ -0,0 +1,248 @@ 1.4 +/* 1.5 + * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved. 1.6 + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 1.7 + * 1.8 + * This code is free software; you can redistribute it and/or modify it 1.9 + * under the terms of the GNU General Public License version 2 only, as 1.10 + * published by the Free Software Foundation. Oracle designates this 1.11 + * particular file as subject to the "Classpath" exception as provided 1.12 + * by Oracle in the LICENSE file that accompanied this code. 1.13 + * 1.14 + * This code is distributed in the hope that it will be useful, but WITHOUT 1.15 + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 1.16 + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 1.17 + * version 2 for more details (a copy is included in the LICENSE file that 1.18 + * accompanied this code). 1.19 + * 1.20 + * You should have received a copy of the GNU General Public License version 1.21 + * 2 along with this work; if not, write to the Free Software Foundation, 1.22 + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 1.23 + * 1.24 + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 1.25 + * or visit www.oracle.com if you need additional information or have any 1.26 + * questions. 1.27 + */ 1.28 + 1.29 +package com.sun.xml.internal.ws.api; 1.30 + 1.31 +import com.sun.istack.internal.NotNull; 1.32 +import com.sun.istack.internal.Nullable; 1.33 +import com.sun.xml.internal.ws.api.addressing.WSEndpointReference; 1.34 +import com.sun.xml.internal.ws.api.server.Container; 1.35 +import com.sun.xml.internal.ws.api.server.ContainerResolver; 1.36 +import com.sun.xml.internal.ws.api.server.WSEndpoint; 1.37 +import com.sun.xml.internal.ws.client.WSServiceDelegate; 1.38 + 1.39 +import javax.xml.bind.JAXBContext; 1.40 +import javax.xml.namespace.QName; 1.41 +import javax.xml.ws.Dispatch; 1.42 +import javax.xml.ws.EndpointReference; 1.43 +import javax.xml.ws.Service; 1.44 +import javax.xml.ws.Service.Mode; 1.45 +import javax.xml.ws.WebServiceException; 1.46 +import javax.xml.ws.WebServiceFeature; 1.47 +import javax.xml.ws.spi.ServiceDelegate; 1.48 +import java.lang.reflect.Field; 1.49 +import java.net.URL; 1.50 +import java.security.AccessController; 1.51 +import java.security.PrivilegedAction; 1.52 +import java.util.HashSet; 1.53 +import java.util.Set; 1.54 +import java.util.concurrent.CopyOnWriteArraySet; 1.55 + 1.56 +/** 1.57 + * JAX-WS implementation of {@link ServiceDelegate}. 1.58 + * 1.59 + * <p> 1.60 + * This abstract class is used only to improve the static type safety 1.61 + * of the JAX-WS internal API. 1.62 + * 1.63 + * <p> 1.64 + * The class name intentionally doesn't include "Delegate", 1.65 + * because the fact that it's a delegate is a detail of 1.66 + * the JSR-224 API, and for the layers above us this object 1.67 + * nevertheless represents {@link Service}. We want them 1.68 + * to think of this as an internal representation of a service. 1.69 + * 1.70 + * <p> 1.71 + * Only JAX-WS internal code may downcast this to {@link WSServiceDelegate}. 1.72 + * 1.73 + * @author Kohsuke Kawaguchi 1.74 + */ 1.75 +public abstract class WSService extends ServiceDelegate implements ComponentRegistry { 1.76 + private final Set<Component> components = new CopyOnWriteArraySet<Component>(); 1.77 + 1.78 + protected WSService() { 1.79 + } 1.80 + 1.81 + /** 1.82 + * Works like {@link #getPort(EndpointReference, Class, WebServiceFeature...)} 1.83 + * but takes {@link WSEndpointReference}. 1.84 + */ 1.85 + public abstract <T> T getPort(WSEndpointReference epr, Class<T> portInterface, WebServiceFeature... features); 1.86 + 1.87 + /** 1.88 + * Works like {@link #createDispatch(javax.xml.ws.EndpointReference, java.lang.Class, javax.xml.ws.Service.Mode, javax.xml.ws.WebServiceFeature[])} 1.89 + * but it takes the port name separately, so that EPR without embedded metadata can be used. 1.90 + */ 1.91 + public abstract <T> Dispatch<T> createDispatch(QName portName, WSEndpointReference wsepr, Class<T> aClass, Service.Mode mode, WebServiceFeature... features); 1.92 + 1.93 + /** 1.94 + * Works like {@link #createDispatch(javax.xml.ws.EndpointReference, javax.xml.bind.JAXBContext, javax.xml.ws.Service.Mode, javax.xml.ws.WebServiceFeature[])} 1.95 + * but it takes the port name separately, so that EPR without embedded metadata can be used. 1.96 + */ 1.97 + public abstract Dispatch<Object> createDispatch(QName portName, WSEndpointReference wsepr, JAXBContext jaxbContext, Service.Mode mode, WebServiceFeature... features); 1.98 + 1.99 + /** 1.100 + * Gets the {@link Container} object. 1.101 + * 1.102 + * <p> 1.103 + * The components inside {@link WSEndpoint} uses this reference 1.104 + * to communicate with the hosting environment. 1.105 + * 1.106 + * @return 1.107 + * always same object. If no "real" {@link Container} instance 1.108 + * is given, {@link Container#NONE} will be returned. 1.109 + */ 1.110 + public abstract @NotNull Container getContainer(); 1.111 + 1.112 + public @Nullable <S> S getSPI(@NotNull Class<S> spiType) { 1.113 + for (Component c : components) { 1.114 + S s = c.getSPI(spiType); 1.115 + if (s != null) 1.116 + return s; 1.117 + } 1.118 + 1.119 + return getContainer().getSPI(spiType); 1.120 + } 1.121 + 1.122 + public @NotNull Set<Component> getComponents() { 1.123 + return components; 1.124 + } 1.125 + 1.126 + /** 1.127 + * Create a <code>Service</code> instance. 1.128 + * 1.129 + * The specified WSDL document location and service qualified name MUST 1.130 + * uniquely identify a <code>wsdl:service</code> element. 1.131 + * 1.132 + * @param wsdlDocumentLocation URL for the WSDL document location 1.133 + * for the service 1.134 + * @param serviceName QName for the service 1.135 + * @throws WebServiceException If any error in creation of the 1.136 + * specified service. 1.137 + **/ 1.138 + public static WSService create( URL wsdlDocumentLocation, QName serviceName) { 1.139 + return new WSServiceDelegate(wsdlDocumentLocation,serviceName,Service.class); 1.140 + } 1.141 + 1.142 + /** 1.143 + * Create a <code>Service</code> instance. 1.144 + * 1.145 + * @param serviceName QName for the service 1.146 + * @throws WebServiceException If any error in creation of the 1.147 + * specified service 1.148 + */ 1.149 + public static WSService create(QName serviceName) { 1.150 + return create(null,serviceName); 1.151 + } 1.152 + 1.153 + /** 1.154 + * Creates a service with a dummy service name. 1.155 + */ 1.156 + public static WSService create() { 1.157 + return create(null,new QName(WSService.class.getName(),"dummy")); 1.158 + } 1.159 + 1.160 + /** 1.161 + * Typed parameter bag used by {@link WSService#create(URL, QName, InitParams)} 1.162 + * 1.163 + * @since 2.1.3 1.164 + */ 1.165 + public static final class InitParams { 1.166 + private Container container; 1.167 + /** 1.168 + * Sets the {@link Container} object used by the created service. 1.169 + * This allows the client to use a specific {@link Container} instance 1.170 + * as opposed to the one obtained by {@link ContainerResolver}. 1.171 + */ 1.172 + public void setContainer(Container c) { 1.173 + this.container = c; 1.174 + } 1.175 + public Container getContainer() { 1.176 + return container; 1.177 + } 1.178 + } 1.179 + 1.180 + /** 1.181 + * To create a {@link Service}, we need to go through the API that doesn't let us 1.182 + * pass parameters, so as a hack we use thread local. 1.183 + */ 1.184 + protected static final ThreadLocal<InitParams> INIT_PARAMS = new ThreadLocal<InitParams>(); 1.185 + 1.186 + /** 1.187 + * Used as a immutable constant so that we can avoid null check. 1.188 + */ 1.189 + protected static final InitParams EMPTY_PARAMS = new InitParams(); 1.190 + 1.191 + /** 1.192 + * Creates a {@link Service} instance. 1.193 + * 1.194 + * <p> 1.195 + * This method works really like {@link Service#create(URL, QName)} 1.196 + * except it takes one more RI specific parameter. 1.197 + * 1.198 + * @param wsdlDocumentLocation 1.199 + * {@code URL} for the WSDL document location for the service. 1.200 + * Can be null, in which case WSDL is not loaded. 1.201 + * @param serviceName 1.202 + * {@code QName} for the service. 1.203 + * @param properties 1.204 + * Additional RI specific initialization parameters. Can be null. 1.205 + * @throws WebServiceException 1.206 + * If any error in creation of the specified service. 1.207 + **/ 1.208 + public static Service create( URL wsdlDocumentLocation, QName serviceName, InitParams properties) { 1.209 + if(INIT_PARAMS.get()!=null) 1.210 + throw new IllegalStateException("someone left non-null InitParams"); 1.211 + INIT_PARAMS.set(properties); 1.212 + try { 1.213 + Service svc = Service.create(wsdlDocumentLocation, serviceName); 1.214 + if(INIT_PARAMS.get()!=null) 1.215 + throw new IllegalStateException("Service "+svc+" didn't recognize InitParams"); 1.216 + return svc; 1.217 + } finally { 1.218 + // even in case of an exception still reset INIT_PARAMS 1.219 + INIT_PARAMS.set(null); 1.220 + } 1.221 + } 1.222 + 1.223 + /** 1.224 + * Obtains the {@link WSService} that's encapsulated inside a {@link Service}. 1.225 + * 1.226 + * @throws IllegalArgumentException 1.227 + * if the given service object is not from the JAX-WS RI. 1.228 + */ 1.229 + public static WSService unwrap(final Service svc) { 1.230 + return AccessController.doPrivileged(new PrivilegedAction<WSService>() { 1.231 + public WSService run() { 1.232 + try { 1.233 + Field f = svc.getClass().getField("delegate"); 1.234 + f.setAccessible(true); 1.235 + Object delegate = f.get(svc); 1.236 + if(!(delegate instanceof WSService)) 1.237 + throw new IllegalArgumentException(); 1.238 + return (WSService) delegate; 1.239 + } catch (NoSuchFieldException e) { 1.240 + AssertionError x = new AssertionError("Unexpected service API implementation"); 1.241 + x.initCause(e); 1.242 + throw x; 1.243 + } catch (IllegalAccessException e) { 1.244 + IllegalAccessError x = new IllegalAccessError(e.getMessage()); 1.245 + x.initCause(e); 1.246 + throw x; 1.247 + } 1.248 + } 1.249 + }); 1.250 + } 1.251 +}