blob: 1e9ea5934f0789a96752eaa5b149730130c6acde [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.openejb.core.ivm.naming;
import org.apache.openejb.Injection;
import org.apache.openejb.core.webservices.HandlerChainData;
import org.apache.openejb.core.webservices.HandlerResolverImpl;
import org.apache.openejb.core.webservices.PortRefData;
import org.apache.openejb.core.webservices.ProviderWrapper;
import org.apache.openejb.core.webservices.ServiceRefData;
import org.apache.openejb.core.webservices.PortAddressRegistry;
import org.apache.openejb.core.webservices.PortAddress;
import org.apache.openejb.loader.SystemInstance;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import javax.xml.namespace.QName;
import javax.xml.ws.Service;
import javax.xml.ws.handler.HandlerResolver;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
public class JaxWsServiceReference extends Reference {
private final String id;
private final QName serviceQName;
private final QName portQName;
private final Class<? extends Service> serviceClass;
private final Class<?> referenceClass;
private final URL wsdlUrl;
private final List<HandlerChainData> handlerChains = new ArrayList<HandlerChainData>();
private final Collection<Injection> injections;
private PortAddressRegistry portAddressRegistry;
private final List<PortRefData> portRefs = new ArrayList<PortRefData>();
public JaxWsServiceReference(String id, QName serviceQName, Class<? extends Service> serviceClass, QName portQName, Class<?> referenceClass, URL wsdlUrl, List<PortRefData> portRefs, List<HandlerChainData> handlerChains, Collection<Injection> injections) {
this.id = id;
this.serviceQName = serviceQName;
this.serviceClass = serviceClass;
this.portQName = portQName;
this.referenceClass = referenceClass;
this.wsdlUrl = wsdlUrl;
if (portRefs != null) {
this.portRefs.addAll(portRefs);
}
if (handlerChains != null) {
this.handlerChains.addAll(handlerChains);
}
this.injections = injections;
}
public Object getObject() throws javax.naming.NamingException {
String referenceClassName = referenceClass != null ? referenceClass.getName() : null;
Set<PortAddress> portAddresses = getPortAddressRegistry().getPorts(id, serviceQName, referenceClassName);
// if we only have one address, use that address for the wsdl and the serviceQName
URL wsdlUrl = this.wsdlUrl;
QName serviceQName = this.serviceQName;
if (portAddresses.size() == 1) {
PortAddress portAddress = portAddresses.iterator().next();
try {
wsdlUrl = new URL(portAddress.getAddress() + "?wsdl");
} catch (MalformedURLException e) {
}
serviceQName = portAddress.getServiceQName();
}
// add the port addresses to the portRefData
Map<QName,PortRefData> portsByQName = new HashMap<QName,PortRefData>();
List<PortRefData> ports = new ArrayList<PortRefData>(portRefs.size() + portAddresses.size());
for (PortRefData portRef : portRefs) {
PortRefData port = new PortRefData(portRef);
if (port.getQName() != null) {
portsByQName.put(port.getQName(), port);
}
ports.add(port);
}
// add PortRefData for any portAddress not added above
for (PortAddress portAddress : portAddresses) {
PortRefData port = portsByQName.get(portAddress.getPortQName());
if (port == null) {
port = new PortRefData();
port.setQName(portAddress.getPortQName());
port.setServiceEndpointInterface(portAddress.getServiceEndpointInterface());
port.getAddresses().add(portAddress.getAddress());
ports.add(port);
} else {
port.getAddresses().add(portAddress.getAddress());
if (port.getServiceEndpointInterface() == null) {
port.setServiceEndpointInterface(portAddress.getServiceEndpointInterface());
}
}
}
ProviderWrapper.beforeCreate(ports);
Service instance;
try {
instance = null;
if (Service.class.equals(serviceClass)) {
instance = Service.create(wsdlUrl, serviceQName);
} else {
try {
instance = serviceClass.getConstructor(URL.class, QName.class).newInstance(wsdlUrl, serviceQName);
} catch (Throwable e) {
throw (NamingException) new NamingException("Could not instantiate jax-ws service class " + serviceClass.getName()).initCause(e);
}
}
} finally {
ProviderWrapper.afterCreate();
}
if (!handlerChains.isEmpty()) {
HandlerResolver handlerResolver = new HandlerResolverImpl(handlerChains, injections, new InitialContext());
instance.setHandlerResolver(handlerResolver);
}
Object port;
if (referenceClass != null && !Service.class.isAssignableFrom(referenceClass)) {
// do port lookup
port = instance.getPort(referenceClass);
} else {
// return service
port = instance;
}
// register the service data so it can be fetched when the service is passed over the EJBd protocol
ServiceRefData serviceRefData = new ServiceRefData(id,
serviceQName,
serviceClass, portQName,
referenceClass,
wsdlUrl,
handlerChains,
portRefs);
ServiceRefData.putServiceRefData(port, serviceRefData);
return port;
}
private PortAddressRegistry getPortAddressRegistry() {
if (portAddressRegistry == null) {
portAddressRegistry = SystemInstance.get().getComponent(PortAddressRegistry.class);
}
return portAddressRegistry;
}
}