com.google.api.ads.common.lib.soap.Axis2Handler Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of common-axis2 Show documentation
Show all versions of common-axis2 Show documentation
Adds support for the Axis2 framework to the Java Client Libraries. Users are
not intended to list this as a dependency on its own. Instead, there are
product-and-framework specific libraries such as "dfp-axis2" and
"adwords-axis2" that already have this listed as a dependency.
The newest version!
// Copyright 2011, Google Inc. All Rights Reserved.
//
// Licensed 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 com.google.api.ads.common.lib.soap;
import com.google.api.ads.common.lib.exception.ServiceException;
import com.google.api.ads.common.lib.soap.compatability.Axis2Compatible;
import com.google.common.annotations.VisibleForTesting;
import com.google.common.collect.Lists;
import com.google.inject.Inject;
import com.ctc.wstx.exc.WstxIOException;
import org.apache.axiom.om.OMAbstractFactory;
import org.apache.axiom.om.OMElement;
import org.apache.axiom.om.OMException;
import org.apache.axiom.om.OMFactory;
import org.apache.axiom.om.OMNamespace;
import org.apache.axiom.soap.SOAPHeaderBlock;
import org.apache.axis2.AxisFault;
import org.apache.axis2.addressing.EndpointReference;
import org.apache.axis2.client.ServiceClient;
import org.apache.axis2.client.Stub;
import org.apache.axis2.context.MessageContext;
import org.apache.axis2.saaj.SOAPHeaderElementImpl;
import org.apache.axis2.transport.http.HTTPConstants;
import org.apache.commons.httpclient.Header;
import java.io.StringWriter;
import java.io.Writer;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.xml.namespace.QName;
import javax.xml.soap.SOAPHeaderElement;
import javax.xml.stream.XMLStreamException;
/**
* Handles an Axis2 SOAP client.
*
* @author [email protected] (Adam Rogal)
*/
public class Axis2Handler extends SoapClientHandler {
private OMFactory omFactory;
/**
* Constructor.
*
* @param omFactory the {@code OMFactory} to be used for constructing elements
*/
@Inject
public Axis2Handler(OMFactory omFactory) {
this.omFactory = omFactory;
}
/**
* @see SoapClientHandlerInterface#setEndpointAddress(Object, String)
*/
public void setEndpointAddress(Stub soapClient, String endpointAddress) {
soapClient._getServiceClient().getOptions()
.setTo(new EndpointReference(endpointAddress));
}
/**
* @see SoapClientHandler#getHeader(Object, String)
*/
public Object getHeader(Stub soapClient, String headerName) {
throw new ServiceException("Method not supported for this framework.", null);
}
/**
* @see com.google.api.ads.common.lib.soap.SoapClientHandlerInterface#clearHeaders(java.lang.Object)
*/
public void clearHeaders(Stub soapClient) {
soapClient._getServiceClient().removeHeaders();
}
/**
* @see SoapClientHandler#setHeader(Object, String, String, Object)
*/
public void setHeader(Stub soapClient, String namespace, String headerName, Object headerValue)
throws ServiceException {
OMNamespace omNamespace = omFactory.createOMNamespace(namespace, "ns");
OMElement header = omFactory.createOMElement(headerName, omNamespace);
soapClient._getServiceClient().addHeader(buildOMElement(headerValue, header));
}
/**
* @see SoapClientHandler#setHttpHeaders(Object, Map)
*/
public void setHttpHeaders(Stub soapClient, Map headersMap) {
List headers = Lists.newArrayList();
for(Entry header : headersMap.entrySet()) {
headers.add(new Header(header.getKey(), header.getValue()));
}
soapClient._getServiceClient().getOptions().setProperty(HTTPConstants.HTTP_HEADERS, headers);
}
/**
* Builds an OM element and sets as a child of the {@code parentElement}.
*
* @param elementValue the element value
* @param parentElement the parent element
* @return the constructed OM element
* @throws ServiceException if there was a problem constructing the element
*/
private OMElement buildOMElement(Object elementValue, OMElement parentElement)
throws ServiceException {
try {
if (elementValue == null) {
return buildOmElementSimpleType(elementValue, parentElement);
} else {
Method getOmElementMethod =
elementValue.getClass().getMethod("getOMElement", QName.class, OMFactory.class);
try {
return (OMElement) getOmElementMethod.invoke(elementValue, parentElement.getQName(),
omFactory);
} catch (IllegalArgumentException e) {
throw new ServiceException("Unexpected exception.", e);
} catch (IllegalAccessException e) {
throw new ServiceException("Unexpected exception.", e);
} catch (InvocationTargetException e) {
throw new ServiceException("Unexpected exception.", e);
}
}
} catch (SecurityException e) {
throw new ServiceException("Unexpected exception.", e);
} catch (NoSuchMethodException e) {
// If it's not a complex type, build it as a simple type.
return buildOmElementSimpleType(elementValue, parentElement);
}
}
/**
* Builds an OM element simple type and sets it as the child of the
* {@code parentElement}.
*
* @param elementValue the element value
* @param parentElement the parent element
* @return the parent element with the child element set
*/
private OMElement buildOmElementSimpleType(Object elementValue, OMElement parentElement) {
if (elementValue != null) {
parentElement.setText(elementValue.toString());
}
return parentElement;
}
/**
* @see SoapClientHandler#setCompression(Object, boolean)
*/
public void setCompression(Stub soapClient, boolean compress) {
soapClient._getServiceClient().getOptions()
.setProperty(HTTPConstants.MC_ACCEPT_GZIP, compress);
soapClient._getServiceClient().getOptions()
.setProperty(HTTPConstants.MC_GZIP_REQUEST, compress);
}
/**
* @see SoapClientHandler#createSoapClient(SoapServiceDescriptor)
*/
public Stub createSoapClient(SoapServiceDescriptor soapServiceDescriptor)
throws ServiceException {
try {
if (soapServiceDescriptor instanceof Axis2Compatible) {
Axis2Compatible axis2CompatibleService = (Axis2Compatible) soapServiceDescriptor;
return (Stub) axis2CompatibleService.getStubClass().getConstructor(new Class[0])
.newInstance(new Object[0]);
}
throw new ServiceException("Service [" + soapServiceDescriptor
+ "] not compatible with Axis2.", null);
} catch (IllegalArgumentException e) {
throw new ServiceException("Unexpected exception.", e);
} catch (SecurityException e) {
throw new ServiceException("Unexpected exception.", e);
} catch (InstantiationException e) {
throw new ServiceException("Unexpected exception.", e);
} catch (IllegalAccessException e) {
throw new ServiceException("Unexpected exception.", e);
} catch (InvocationTargetException e) {
throw new ServiceException("Unexpected exception.", e);
} catch (NoSuchMethodException e) {
throw new ServiceException("Unexpected exception.", e);
} catch (ClassNotFoundException e) {
throw new ServiceException("Unexpected exception.", e);
}
}
/**
* @see SoapClientHandler#invokeSoapCall(SoapCall)
*/
public SoapCallReturn invokeSoapCall(SoapCall soapCall) {
Stub stub = soapCall.getSoapClient();
SoapCallReturn.Builder builder = new SoapCallReturn.Builder();
synchronized (stub) {
Object result = null;
try {
result = invoke(soapCall);
} catch (InvocationTargetException e) {
builder.withException(e.getTargetException());
} catch (Exception e) {
builder.withException(e);
} finally {
ServiceClient serviceClient = stub._getServiceClient();
try {
MessageContext messageContext =
serviceClient.getLastOperationContext().getMessageContext("Out");
builder.withRequestInfo(new RequestInfo.Builder().withSoapRequestXml(
messageContext.getEnvelope().toStringWithConsume())
.withMethodName(serviceClient.getLastOperationContext().getOperationName())
.withServiceName(
filterNumbers(serviceClient.getLastOperationContext().getServiceName()))
.withUrl(messageContext.getTo().getAddress())
.build());
} catch (XMLStreamException e) {
builder.withException(e);
} catch (AxisFault e) {
builder.withException(e);
}
try {
MessageContext messageContext =
serviceClient.getLastOperationContext().getMessageContext("In");
Writer stringWriter = new StringWriter();
try {
if (messageContext.getEnvelope() != null) {
messageContext.getEnvelope().serialize(stringWriter);
}
} catch (OMException e) {
// An exception will be thrown because the stream has already been
// closed, but the XML can still be read.
if (!(e.getCause() instanceof WstxIOException)) {
builder.withException(e);
}
}
builder.withResponseInfo(new ResponseInfo.Builder().withSoapResponseXml(
stringWriter.toString()).build());
} catch (AxisFault e) {
builder.withException(e);
} catch (XMLStreamException e) {
builder.withException(e);
}
}
return builder.withReturnValue(result).build();
}
}
@VisibleForTesting
String filterNumbers(String serviceName) {
Matcher matcher = Pattern.compile("^([a-zA-Z]*)[0-9]?.*$").matcher(serviceName);
if (matcher.matches()) {
return matcher.group(1);
} else {
return serviceName;
}
}
/**
* @see SoapClientHandlerInterface#getEndpointAddress(Object)
*/
public String getEndpointAddress(Stub soapClient) {
return soapClient._getServiceClient().getOptions().getTo().getAddress();
}
/**
* @see SoapClientHandlerInterface#createSoapHeaderElement(QName)
*/
public SOAPHeaderElement createSoapHeaderElement(QName qName) {
OMNamespace ns = omFactory.createOMNamespace(qName.getNamespaceURI(), qName.getPrefix());
SOAPHeaderBlock headerBlock = OMAbstractFactory.getSOAP12Factory()
.createSOAPHeaderBlock(qName.getLocalPart(), ns);
return new SOAPHeaderElementImpl(headerBlock);
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy