blob: 8b8e858fadbf23c4c71ba9823a28b5ef70bbedc1 [file] [log] [blame]
/*
* Copyright 2003-2004 The Apache Software Foundation.
// (c) Copyright IBM Corp. 2004, 2005 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 org.apache.axis.wsdl.wsdl2ws.info;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Vector;
import javax.wsdl.Binding;
import javax.wsdl.BindingInput;
import javax.wsdl.BindingOperation;
import javax.wsdl.Fault;
import javax.wsdl.Operation;
import javax.wsdl.Part;
import javax.wsdl.Port;
import javax.wsdl.PortType;
import javax.wsdl.Service;
import javax.wsdl.WSDLElement;
import javax.wsdl.extensions.soap.SOAPBinding;
import javax.wsdl.extensions.soap.SOAPBody;
import javax.wsdl.extensions.soap.SOAPOperation;
import javax.wsdl.extensions.soap.SOAPAddress;
import javax.xml.namespace.QName;
import javax.xml.rpc.holders.BooleanHolder;
import javax.xml.rpc.holders.IntHolder;
import org.apache.axis.Constants;
import org.apache.axis.wsdl.gen.Parser;
import org.apache.axis.wsdl.symbolTable.BindingEntry;
import org.apache.axis.wsdl.symbolTable.CContainedAttribute;
import org.apache.axis.wsdl.symbolTable.CElementDecl;
import org.apache.axis.wsdl.symbolTable.CSchemaUtils;
import org.apache.axis.wsdl.symbolTable.CollectionElement;
import org.apache.axis.wsdl.symbolTable.CollectionType;
import org.apache.axis.wsdl.symbolTable.DefinedElement;
import org.apache.axis.wsdl.symbolTable.Element;
import org.apache.axis.wsdl.symbolTable.Parameters;
import org.apache.axis.wsdl.symbolTable.SchemaUtils;
import org.apache.axis.wsdl.symbolTable.ServiceEntry;
import org.apache.axis.wsdl.symbolTable.SymTabEntry;
import org.apache.axis.wsdl.symbolTable.SymbolTable;
import org.apache.axis.wsdl.symbolTable.TypeEntry;
import org.apache.axis.wsdl.toJava.Utils;
import org.apache.axis.wsdl.wsdl2ws.CUtils;
import org.apache.axis.wsdl.wsdl2ws.WrapperFault;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
/**
* This class initiates the collection of various bits of information needed by the
* wsdl2ws tool by parsing the WSDL file.
*
* @author nadir amra
*
*/
public class WSDLInfo
{
// Private constants for retrieving extensibility elements.
private static final int INSTANCEOF_SOAPBINDING = 1;
private static final int INSTANCEOF_SOAPADDRESS = 2;
private static final int INSTANCEOF_SOAPBODY = 3;
private static final int INSTANCEOF_SOAPOPERATION = 4;
// verbose flag
private boolean c_verbose = false;
// parser timeout value, in seconds. 0=no timeout.
private long c_timeout = 0;
// URI to WSDL document.
private String c_URIToWSDLDocument = null;
// Whether wrapper-style is not requested.
private boolean c_noWrapperStyle = false;
// WSDL parser from the last time parse() was invoked.
private Parser c_wsdlParser = null;
// Symbol table associated with the parser.
private SymbolTable c_symbolTable = null;
// Types generated as result of symbolTable
private TypeMap c_typeMap = null;
// Target name space of WSDL
private String c_targetNameSpaceOfWSDL = null;
// Service definitions in WSDL
ArrayList c_services = new ArrayList();
// Maps service definition to set of ports that use RPC binding style
ArrayList c_bindings = new ArrayList();
private static boolean useCounter = false;
private static int typeCounter = 1;
/**
* Constructor.
*/
public WSDLInfo(String uri)
{
c_URIToWSDLDocument = uri;
}
/**
* Initiates the parsing of the WSDL document. Returns the symbol table that is generated
* by the parser. After parsing the WSDL document, various artifacts that the wsdl2ws tool needs
* is collected for easy access.
*
* @throws Exception
*/
public SymbolTable parse() throws Exception
{
// ==================================================
// Parse WSDL document
// ==================================================
c_wsdlParser = new Parser();
// Set verbose in WSDL parser
c_wsdlParser.setVerbose(c_verbose);
// Set timeout for parser, setTimeout method expects the time in milliseconds.
c_wsdlParser.setTimeout(c_timeout*1000);
// Set unwrapped if requested
c_wsdlParser.setNowrap(c_noWrapperStyle);
// Parse the WSDL document.
c_wsdlParser.run(c_URIToWSDLDocument);
c_symbolTable = c_wsdlParser.getSymbolTable();
// Dump symbol table if in verbose mode.
if (c_verbose)
c_symbolTable.dump(System.out);
// ==================================================
// Collect various bits of information from the document.
// ==================================================
// Get target name space of WSDL
c_targetNameSpaceOfWSDL = c_symbolTable.getDefinition().getTargetNamespace();
// Collect services and bindings.
Iterator it = c_symbolTable.getHashMap().values().iterator();
while (it.hasNext())
{
Vector v = (Vector) it.next();
for (int i = 0; i < v.size(); ++i)
{
SymTabEntry entry = (SymTabEntry) v.elementAt(i);
if (entry instanceof org.apache.axis.wsdl.symbolTable.ServiceEntry)
c_services.add(((ServiceEntry) entry).getService());
else if (entry instanceof org.apache.axis.wsdl.symbolTable.BindingEntry)
c_bindings.add(entry);
}
}
// Iterate through the symbol table, generating user-defined types and
// storing the types in a hash table. We need to do this twice. We need
// to first go through the types and ensure there is no type with a suffix of
// _Array, which is used by this code to generate arrays. If there is, we need to
// generate array types with a modified suffix, such as _Array + number.
c_typeMap = new TypeMap();
if (c_symbolTable != null)
{
it = c_symbolTable.getTypeIndex().values().iterator();
while (it.hasNext())
{
TypeEntry type = (TypeEntry) it.next();
Node node = type.getNode();
if (node != null)
{
if (type.getQName().getLocalPart().endsWith("_Array"))
useCounter = true;
}
}
it = c_symbolTable.getTypeIndex().values().iterator();
while (it.hasNext())
{
TypeEntry type = (TypeEntry) it.next();
Node node = type.getNode();
if (node != null)
{
if (c_verbose)
{
System.out.println( "==>getTypeInfo: Processing type...." + type.getQName());
}
createTypeInfo(type);
}
}
}
// ==================================================
// Return the symbol table
// ==================================================
return c_symbolTable;
}
/**
* Sets the WSDL parser timeout value.
*
* @param t timeout value in seconds. Null implies 0 timeout (no timeout).
*/
public void setTimeout(long t)
{
c_timeout = t;
}
/**
* Sets the WSDL parser verbose mode.
*
* @param b true=verbose; false=no verbose.
*/
public void setVerbose(boolean b)
{
c_verbose = b;
}
/**
* Indicates whether wrapper-style interfaces is allowed.
*
* @param b true=no wrapper style; false=allow wrapper style.
*/
public void setNoWrapperStyle(boolean b)
{
c_noWrapperStyle = b;
}
/**
* Returns target name space of WSDL.
*
* @return String representing the target name space of WSDL.
*/
public String getTargetNameSpaceOfWSDL()
{
return c_targetNameSpaceOfWSDL;
}
/**
* Returns array of services defined in WSDL. The array
* may be empty if service was not defined in WSDL.
*
* @return array of java.wsdl.Service objects.
*/
public ArrayList getServices()
{
return c_services;
}
/**
* Returns end point URI for a Port by looking for the soap:address extensibility element.
*
* @param port
* @return
*/
public static String getTargetEndPointURI(Port port)
{
SOAPAddress e = (SOAPAddress)getExtensibilityElement(port, INSTANCEOF_SOAPADDRESS);
if (e != null)
return e.getLocationURI();
return null;
}
/**
* Returns the transport URI in a soap:binding element.
*
* @param binding
* @return
*/
public static String getTransportType(Binding binding)
{
SOAPBinding e = (SOAPBinding)getExtensibilityElement(binding, INSTANCEOF_SOAPBINDING);
if (e != null)
return e.getTransportURI();
return null;
}
/**
* @return the c_typeMap
*/
public TypeMap getTypeMap()
{
return c_typeMap;
}
/**
* Return the binding entry matching the local name.
*
* @param name
* @return
*/
public BindingEntry getBindEntry(String name)
{
Iterator it = c_bindings.iterator();
while (it.hasNext())
{
BindingEntry be = (BindingEntry)it.next();
if (be.getBinding().getQName().getLocalPart().equals(name))
return be;
}
return null;
}
/**
* Returns the Port that references the specified binding entry from a service definition.
*
* @param s
* @param be
* @return
*/
public static Port getPort(Service s, BindingEntry be)
{
Iterator ports = s.getPorts().values().iterator();
while (ports.hasNext())
{
Port p = (Port) ports.next();
Binding b = p.getBinding();
if (be.getBinding().getQName().equals(b.getQName()))
return p;
}
return null;
}
/**
* Checks if binding entry is SOAP 1.1 binding.
* @param be
* @return
*/
public static boolean isSOAP11Binding(BindingEntry be)
{
return isSOAPBinding(be, Constants.URI_WSDL11_SOAP);
}
/**
* Checks if SOAP 1.2 binding.
* @param be
* @return
*/
public static boolean isSOAP12Binding(BindingEntry be)
{
return isSOAPBinding(be, Constants.URI_WSDL12_SOAP);
}
/**
* Updates MethodInfo with information from the binding operation element.
*
* @param bindingOp
* @param method
*/
public static void updateMethodInfoFromBinding(BindingOperation bindingOp, MethodInfo method)
{
// Get SOAPAction
SOAPOperation e = (SOAPOperation)getExtensibilityElement(bindingOp, INSTANCEOF_SOAPOPERATION);
if (e != null)
method.setSoapAction(e.getSoapActionURI());
// Get information about input operation
BindingInput bi = bindingOp.getBindingInput();
SOAPBody body = (SOAPBody)getExtensibilityElement(bi, INSTANCEOF_SOAPBODY);
if (body != null)
{
method.setInputNamespaceURI(body.getNamespaceURI());
}
}
/**
* Generate service name given a binding.
*
* @param bindingEntry
* @return
* @throws WrapperFault
*/
public static String getServiceName(BindingEntry bindingEntry) throws WrapperFault
{
PortType portType = bindingEntry.getBinding().getPortType();
if (portType == null)
throw new WrapperFault("Port type specified in binding '" + bindingEntry.getBinding().getQName().getLocalPart() + "' not found");
return CUtils.getNameFromFullyQualifiedName(portType.getQName().getLocalPart());
}
/**
* Returns list of Port objects in the specified service. All ports in the list
* will have a binding style of document and uses the SOAP 1.1 binding.
*
* @param s service definition
* @return list of ports that match the criteria described above.
* @throws Exception
*/
public ArrayList getPortsSOAP11Document(Service s) throws Exception
{
return getServicePorts(s, true, true, false, false);
}
/**
* Returns list of Port objects in the specified service. All ports in the list
* will have a binding style of rpc and uses the SOAP 1.1 binding.
*
* @param s service definition
* @return list of ports that match the criteria described above.
* @throws Exception
*/
public ArrayList getPortsSOAP11RPC(Service s) throws Exception
{
return getServicePorts(s, false, true, false, false);
}
/**
* Returns list of Port objects in the specified service. All ports in the list
* will have a binding style of document and uses the SOAP 1.2 binding.
*
* @param s service definition
* @return list of ports that match the criteria described above.
* @throws Exception
*/
public ArrayList getPortsSOAP12Document(Service s) throws Exception
{
return getServicePorts(s, true, false, true, false);
}
/**
* Returns list of Port objects in the specified service. All ports in the list
* will have a binding style of rpc and uses the SOAP 1.2 binding.
*
* @param s service definition
* @return list of ports that match the criteria described above.
* @throws Exception
*/
public ArrayList getPortsSOAP12RPC(Service s) throws Exception
{
return getServicePorts(s, false, false, true, false);
}
/**
* Returns list of Port objects in the specified service. All ports in the list
* uses the HTTP binding.
*
* @param s
* @param styleDocument
* @return
* @throws Exception
*/
public ArrayList getPortsREST(Service s) throws Exception
{
return getServicePorts(s, true, false, false, true);
}
/**
* Returns list of Port objects in a service definition based on selection criteria.
*
* @param s service definition.
* @param styleDocument true=return document style; false=return "rpc" style.
* This parameter is ignored for REST (HTTP) bindings.
* @param soap11 true=return SOAP 1.1 bindings; false=SOAP 1.1 bindings are ignored.
* @param soap12 true=return SOAP 1.2 bindings; false=SOAP 1.2 bindings are ignored.
* @param rest true=return HTTP bindings; false=ignore HTTP bindings.
* @return List of ports that match selection criteria.
* @throws Exception
*/
private ArrayList getServicePorts(Service s,
boolean styleDocument,
boolean soap11,
boolean soap12,
boolean rest) throws Exception
{
ArrayList a = new ArrayList();
if (s == null)
return a;
Iterator ports = s.getPorts().values().iterator();
while (ports.hasNext())
{
Port p = (Port) ports.next();
Binding b = p.getBinding();
BindingEntry be = c_symbolTable.getBindingEntry(b.getQName());
if (b == null || be == null)
throw new WrapperFault("No binding exists for port '" + p.getName() + "'.");
if ((be.getBindingType() == BindingEntry.TYPE_SOAP) && (soap11 || soap12))
{
String style = be.getBindingStyle().getName();
if (style == null)
style = "document";
if ((styleDocument && style.equalsIgnoreCase("document"))
|| (!styleDocument && style.equalsIgnoreCase("rpc")))
{
String ns = Constants.URI_WSDL11_SOAP;
SOAPBinding soapbinding = (SOAPBinding)getExtensibilityElement(b, INSTANCEOF_SOAPBINDING);
if (soapbinding != null && null != soapbinding.getElementType().getNamespaceURI())
ns = soapbinding.getElementType().getNamespaceURI();
if ((soap11 && ns.equals(Constants.URI_WSDL11_SOAP))
|| (soap12 && ns.equals(Constants.URI_WSDL12_SOAP)))
a.add(p);
}
}
else if (rest && (be.getBindingType() == BindingEntry.TYPE_HTTP_GET
|| be.getBindingType() == BindingEntry.TYPE_HTTP_POST))
{
a.add(p);
}
}
return a;
}
/**
* Helper function that returns requested extensibility element.
*
* @param e element to retrieve extensibility elements from.
* @param clazz instance of class
* @return extensibility element.
*/
private static Object getExtensibilityElement(WSDLElement e, int clazz)
{
if (e != null)
{
List extElems = e.getExtensibilityElements();
if (extElems != null)
{
Iterator it = extElems.iterator();
while (it.hasNext())
{
Object o = it.next();
if ((clazz == INSTANCEOF_SOAPBINDING && (o instanceof javax.wsdl.extensions.soap.SOAPBinding))
|| (clazz == INSTANCEOF_SOAPADDRESS && (o instanceof javax.wsdl.extensions.soap.SOAPAddress))
|| (clazz == INSTANCEOF_SOAPOPERATION && (o instanceof javax.wsdl.extensions.soap.SOAPOperation))
|| (clazz == INSTANCEOF_SOAPBODY && (o instanceof javax.wsdl.extensions.soap.SOAPBody)))
return o;
}
}
}
return null;
}
/**
* Generate a type for the specified QName.
*
* @param typename
* @return
* @throws WrapperFault
*/
private Type createTypeInfo(QName typename) throws WrapperFault
{
TypeEntry type = c_symbolTable.getType(typename);
if (type == null)
{
type = c_symbolTable.getElement(typename);
if (type == null)
throw new WrapperFault("[" + typename + "]unexpected condition occurred. ");
}
return createTypeInfo(type);
}
/**
* Creates a type map entry from a symbol table typeentry.
*
* @param type
* @return
* @throws WrapperFault
*/
private Type createTypeInfo(TypeEntry type) throws WrapperFault
{
Type typedata = null;
Type newSecondaryType = null;
// Do not add types which are not used in the WSDL
if (!type.isReferenced())
return null;
if (c_verbose && !CUtils.isPrimitiveType(type.getQName()))
System.out.println("Attempting to create type: " + type.getQName());
if (type instanceof CollectionElement)
{ //an array
}
else if (type instanceof DefinedElement)
{
// if element references another type, process the referenced type
if (type.getRefType() != null)
{
if (c_verbose)
System.out.println("Attempting to create new type from element-ref: " + type.getRefType().getQName());
return createTypeInfo(type.getRefType());
}
return null;
}
if (-1 != type.getQName().getLocalPart().indexOf('['))
{
// An array...
// Get referenced type
if (null == type.getRefType() || null == type.getRefType().getQName())
throw new WrapperFault("Array type found without a Ref type: " + type.getQName());
// TODO not sure what we should do if array references an element following commented code is not correct
// if (type.getRefType().getRefType() != null)
// qn = type.getRefType().getRefType().getQName();
QName qn = type.getRefType().getQName();
// If referenced type is primitive, we are done...
if (CUtils.isPrimitiveType(qn))
return null;
// Create array
QName newqn;
if (useCounter)
{
newqn = CUtils.getArrayQNameForType(qn);
if (newqn == null)
newqn = new QName(type.getQName().getNamespaceURI(), CUtils.sanitizeString(qn.getLocalPart()) + "_Array" + typeCounter++);
}
else
newqn = new QName(type.getQName().getNamespaceURI(), CUtils.sanitizeString(qn.getLocalPart()) + "_Array");
// type is a inbuilt type or an already created type?
typedata = c_typeMap.getType(newqn);
if (typedata != null)
{
if (typedata.isArray())
{
if (c_verbose && !CUtils.isPrimitiveType(type.getQName()))
System.out.println("Type not created, already exists: " + type.getQName());
return typedata;
}
else
{
// There is a type with the _Array suffix in WSDL that was already processed.
// If an array type was not already created, create one with different name.
QName arrayQName = CUtils.getArrayQNameForType(qn);
if (arrayQName == null)
{
do
{
newqn = new QName(type.getQName().getNamespaceURI(), CUtils.sanitizeString(qn.getLocalPart()) + "_Array" + typeCounter++);
typedata = c_typeMap.getType(newqn);
}
while (typedata != null && !typedata.isArray());
if (typedata == null)
{
if (c_verbose)
System.out.println("Type clash, change type name to : " + newqn);
}
else
{
if (c_verbose && !CUtils.isPrimitiveType(type.getQName()))
System.out.println("Type not created, already exists: " + type.getQName());
return typedata;
}
}
else
{
if (c_verbose)
System.out.println("Type not created, already exists: " + type.getQName());
return c_typeMap.getType(arrayQName);
}
}
}
typedata = new Type(newqn, newqn.getLocalPart());
CUtils.addArrayType(qn, newqn);
if (type.getRefType().getRefType() != null)
typedata.setElementType(type.getRefType().getRefType().getQName().getLocalPart());
else
typedata.setElementType(type.getRefType().getQName().getLocalPart());
}
else
{
// type is a inbuilt type or a already created type?
typedata = c_typeMap.getType(type.getQName());
if (typedata != null)
{
if (!typedata.isArray())
{
if (c_verbose && !CUtils.isPrimitiveType(type.getQName()))
System.out.println("Type not created, already exists: " + type.getQName());
}
return typedata;
}
typedata = new Type(type.getQName(), type.getQName().getLocalPart());
}
// Add type to type map
if (c_verbose)
System.out.println("Created new type: " + typedata.getName());
c_typeMap.addType(typedata.getName(), typedata);
// TODO revisit...work out whether this type will be generated or not
typedata.externalize(isTypeGenerated(type, typedata));
Node node = type.getNode();
if (type.isSimpleType())
{
//check for extended types
TypeEntry base = CSchemaUtils.getComplexElementExtensionBase(type.getNode(), c_symbolTable);
if (base != null)
{
String localpart = type.getQName().getLocalPart() + "_value";
QName typeName = new QName(type.getQName().getNamespaceURI(), localpart);
newSecondaryType = createTypeInfo(base.getQName());
typedata.addRelatedType(newSecondaryType);
typedata.setExtensionBaseType(new CElementDecl(newSecondaryType, typeName));
if (c_verbose)
System.out.print(
"=====complexType with simpleContent is found : "
+ type.getQName().getLocalPart() + "=====\n");
}
else
setRestrictionBaseAndValues(typedata, node);
// There can be attributes in this extended basic type
Vector attributes = CSchemaUtils.getContainedAttributeTypes(type.getNode(), c_symbolTable);
if (attributes != null)
{
for (int j = 0; j < attributes.size(); j++)
{
CContainedAttribute attr = (CContainedAttribute)attributes.get(j);
newSecondaryType = createTypeInfo(attr.getTypeEntry().getQName());
attr.setType(newSecondaryType);
typedata.addRelatedType(newSecondaryType);
}
typedata.addAttributes(attributes);
}
}
else if (type instanceof CollectionType)
{
typedata.setArray(true);
newSecondaryType = createTypeInfo(type.getRefType().getQName());
typedata.addRelatedType(newSecondaryType);
typedata.setTypeNameForElementName(new CElementDecl(newSecondaryType, type.getQName()));
}
else
{
//is this a SOAPEnc array type
QName arrayType = CSchemaUtils.getArrayComponentQName(node,new IntHolder(0),c_symbolTable);
if (arrayType != null)
{
typedata.setArray(true);
newSecondaryType = createTypeInfo(arrayType);
typedata.addRelatedType(newSecondaryType);
typedata.setTypeNameForElementName(new CElementDecl(newSecondaryType, new QName("item")));
}
else if ((arrayType = CSchemaUtils.getCollectionComponentQName(node)) != null)
{
typedata.setArray(true);
newSecondaryType = createTypeInfo(arrayType);
typedata.addRelatedType(newSecondaryType);
typedata.setTypeNameForElementName(new CElementDecl(newSecondaryType, new QName("item")));
}
//Note in a array the parameter type is stored as under the name item all the time
else
{
// get all extended types
Vector extendList = new Vector();
extendList.add(type);
TypeEntry parent = CSchemaUtils.getComplexElementExtensionBase(type.getNode(), c_symbolTable);
while (parent != null)
{
extendList.add(parent);
parent = CSchemaUtils.getComplexElementExtensionBase(parent.getNode(), c_symbolTable);
}
// Now generate a list of names and types starting with
// the oldest parent. (Attrs are considered before elements).
for (int i = extendList.size() - 1; i >= 0; i--)
{
TypeEntry te = (TypeEntry) extendList.elementAt(i);
//TODO the code require the attributes name at extension base types
//different, the WSDL2Ws do not support it having same name at up and below.
// Process the attributes
if (c_verbose)
System.out.println("Processing attributes for type: " + type.getQName());
// TODO Need to handle whether attributes are qualified?
Vector attributes = CSchemaUtils.getContainedAttributeTypes(te.getNode(), c_symbolTable);
if (attributes != null)
{
for (int j = 0; j < attributes.size(); j++)
{
CContainedAttribute attr = (CContainedAttribute)attributes.get(j);
newSecondaryType = createTypeInfo(attr.getTypeEntry().getQName());
attr.setType(newSecondaryType);
typedata.addRelatedType(newSecondaryType);
}
typedata.addAttributes(attributes);
}
// Process the elements
if (c_verbose)
System.out.println("Processing elements for type: " + type.getQName());
Vector elements = CSchemaUtils.getContainedElementDeclarations(te.getNode(), c_symbolTable);
if (elements != null)
{
// The following will get elementFormDefault for the schema the element is in.
boolean nsQualifyElementDefault = CSchemaUtils.isElementFormDefaultQualified(te.getNode());
// Now process the elements.
for (int j = 0; j < elements.size(); j++)
{
CElementDecl elem = (CElementDecl) elements.get(j);
// Set whether to namespace qualify or not. We only process if not set.
if (!elem.getNsQualified())
{
boolean nsQualifyElement =
CSchemaUtils.shouldWeNamespaceQualifyNode(elem.getTypeEntry().getNode(),
nsQualifyElementDefault);
elem.setNsQualified(nsQualifyElement);
}
if (elem.getAnyElement())
{
newSecondaryType = new Type();
}
else
{
QName typeName = elem.getTypeEntry().getQName();
if (typeName.getLocalPart().indexOf('[') > 0)
{
String localpart =
typeName.getLocalPart().substring(0, typeName.getLocalPart().indexOf('['));
typeName = new QName(typeName.getNamespaceURI(), localpart);
if (CUtils.isPrimitiveType(typeName))
newSecondaryType = createTypeInfo(typeName);
else
newSecondaryType = createTypeInfo(elem.getTypeEntry());
}
else
newSecondaryType = createTypeInfo(typeName);
}
typedata.addRelatedType(newSecondaryType);
elem.setType(newSecondaryType);
typedata.setTypeNameForElementName(elem);
}
}
} // for-loop
}
}
return typedata;
}
/**
* Returns the actual referenced type (i.e. a defined type or base type)
*
* @param type
* @return
*/
private TypeEntry getActualRefType(TypeEntry type)
{
if (type == null)
return null;
TypeEntry rt = type.getRefType();
if (rt != null)
{
if (rt instanceof org.apache.axis.wsdl.symbolTable.DefinedType
|| rt instanceof org.apache.axis.wsdl.symbolTable.BaseType)
return rt;
}
return getActualRefType(rt);
}
/**
* If the specified node represents a supported JAX-RPC restriction,
* a Vector is returned which contains the base type and the values (enumerations etc).
* The first element in the vector is the base type (an TypeEntry).
* Subsequent elements are QNames.
* NEEDS WORK - CURRENTLY THE ONLY THING WE DO IS GENERATE ENUMERATOR CONSTANTS AND CREATE
* AN EMPTY RESTRICTOR FUNCTION WHEN DOING CODE GENERATION STEP.
*/
private void setRestrictionBaseAndValues(Type typedata, Node node)
{
if (node == null)
return;
// If the node kind is an element, dive into it.
QName nodeKind = Utils.getNodeQName(node);
if (nodeKind != null &&
nodeKind.getLocalPart().equals("element") &&
Constants.isSchemaXSD(nodeKind.getNamespaceURI()))
{
NodeList children = node.getChildNodes();
Node simpleNode = null;
for (int j = 0; j < children.getLength() && simpleNode == null; j++)
{
QName simpleKind = Utils.getNodeQName(children.item(j));
if (simpleKind != null &&
simpleKind.getLocalPart().equals("simpleType") &&
Constants.isSchemaXSD(simpleKind.getNamespaceURI()))
{
simpleNode = children.item(j);
node = simpleNode;
}
}
}
// Get the node kind, expecting a schema simpleType
nodeKind = Utils.getNodeQName(node);
if (nodeKind != null &&
nodeKind.getLocalPart().equals("simpleType") &&
Constants.isSchemaXSD(nodeKind.getNamespaceURI()))
{
// Under the simpleType there may be a restriction, list, or union.
// (There may be other #text nodes, which we will ignore).
// We do something special for unions and lists. We treat them
// as strings and ignore the processing of restriction nodes.
Node restrictionNode = null;
boolean isListOrUnionNode = false;
restrictionNode = CSchemaUtils.getListOrUnionNode(node);
if (restrictionNode != null)
isListOrUnionNode = true;
if (!isListOrUnionNode)
{
NodeList children = node.getChildNodes();
for (int j = 0; j < children.getLength() && restrictionNode == null; j++)
{
QName restrictionKind = Utils.getNodeQName(children.item(j));
if (restrictionKind != null &&
restrictionKind.getLocalPart().equals("restriction") &&
Constants.isSchemaXSD(restrictionKind.getNamespaceURI()))
restrictionNode = children.item(j);
}
}
// If no restriction or union or list node, just return
if (restrictionNode == null)
return;
// The restriction node indicates the type being restricted
// (the base attribute contains this type). For list or union types,
// treat as xsd:string.
QName baseType;
if (!isListOrUnionNode)
baseType = Utils.getTypeQName(restrictionNode, new BooleanHolder(), false);
else
baseType = new QName("http://www.w3.org/2001/XMLSchema", "string");
TypeEntry baseEType = c_symbolTable.getType(baseType);
if (baseEType != null)
{
QName typedataQName = typedata.getName();
String typedataLocalpart = typedataQName.getLocalPart();
String baseTypeLocalpart = baseEType.getQName().getLocalPart();
QName typedataQNameSanitized = null;
String typedataLocalpartSanitized = null;
String baseTypeLocalpartSanitized = null;
String methodSuffix = null;
String primitiveXSDType = null;
String initValueForType = null;
String classForPrimitiveType = null;
if (TypeMap.isAnonymousType(typedataLocalpart))
{
typedataQNameSanitized = new QName(typedataQName.getNamespaceURI(), CUtils.sanitizeString(typedataLocalpart));
typedataLocalpartSanitized = CUtils.sanitizeString(typedataLocalpart);
}
if (TypeMap.isAnonymousType(baseTypeLocalpart))
baseTypeLocalpartSanitized = CUtils.sanitizeString(baseTypeLocalpart);
String class4qname = null;
String class4qnameSanitized = null;
String javaName = CUtils.getPrimitiveType(baseEType.getQName());
boolean isBaseTypePrimitive = javaName != null;
QName primitiveBaseTypeQName = null;
if (javaName == null)
{
// No mapping - ensure that the base type is simple - if it is, then this
// must be a user-defined simple type that is based on another user-defined
// simple type.
if (!baseEType.isSimpleType()
&& !SchemaUtils.isSimpleSchemaType(baseEType.getQName()))
return;
// Get the primitive base type
TypeEntry primitiveBaseType = CSchemaUtils.getBaseType(baseEType, c_symbolTable);
primitiveBaseTypeQName = primitiveBaseType.getQName();
}
else if (javaName.equals("boolean"))
return;
else
primitiveBaseTypeQName = baseEType.getQName();
classForPrimitiveType = CUtils.getSimpleType(primitiveBaseTypeQName);
initValueForType = CUtils.getInitValueForType(classForPrimitiveType);
// Set the base type for Type
typedata.setBaseType(primitiveBaseTypeQName);
// We will map the user-defined type to the user-defined type, so set
// mapping for the type.
class4qname = typedataLocalpart;
class4qnameSanitized = typedataLocalpartSanitized;
// Update some commonly-used mapping tables to reflect the user-defined
// simple type. If anonymous type, we need to update mapping tables twice: once
// with the anonymous names, and once with the sanitized names.
boolean isPointerType = CUtils.isPointerType(primitiveBaseTypeQName);
primitiveXSDType = CUtils.getXSDEnumeratorForType(classForPrimitiveType);
if (!isBaseTypePrimitive)
{
typedata.setRestrictionBaseType(baseTypeLocalpart);
if (isPointerType)
CUtils.addPointerType(baseTypeLocalpart);
}
if (isPointerType)
CUtils.addPointerType(typedataLocalpart);
methodSuffix = (String)CUtils.getDeserializerMethodSuffixForType(classForPrimitiveType);
CUtils.addXSDEnumeratorForType(typedataLocalpart, primitiveXSDType);
if (initValueForType != null)
CUtils.addInitValueForType(typedataLocalpart, initValueForType);
CUtils.addDeserializerMethodSuffixForType(typedataLocalpart, methodSuffix);
if (!isBaseTypePrimitive)
{
CUtils.addXSDEnumeratorForType(baseTypeLocalpart, primitiveXSDType);
if (initValueForType != null)
CUtils.addInitValueForType(baseTypeLocalpart, initValueForType);
CUtils.addDeserializerMethodSuffixForType(baseTypeLocalpart, methodSuffix);
}
if (typedataQNameSanitized != null)
{
if (isPointerType)
CUtils.addPointerType(typedataLocalpartSanitized);
CUtils.addXSDEnumeratorForType(typedataLocalpartSanitized, primitiveXSDType);
if (initValueForType != null)
CUtils.addInitValueForType(typedataLocalpartSanitized, initValueForType);
CUtils.addDeserializerMethodSuffixForType(typedataLocalpartSanitized, methodSuffix);
}
if (baseTypeLocalpartSanitized != null)
{
if (isPointerType)
CUtils.addPointerType(baseTypeLocalpartSanitized);
CUtils.addXSDEnumeratorForType(baseTypeLocalpartSanitized, primitiveXSDType);
if (initValueForType != null)
CUtils.addInitValueForType(baseTypeLocalpartSanitized, initValueForType);
CUtils.addDeserializerMethodSuffixForType(baseTypeLocalpartSanitized, methodSuffix);
}
// Process the enumeration elements underneath the restriction node
Vector v = new Vector();
if (!isListOrUnionNode)
{
NodeList enums = restrictionNode.getChildNodes();
for (int i=0; i < enums.getLength(); i++)
{
QName enumKind = Utils.getNodeQName(enums.item(i));
if (enumKind != null && Constants.isSchemaXSD(enumKind.getNamespaceURI()))
{
Node enumNode = enums.item(i);
String value = Utils.getAttribute(enumNode, "value");
if (value.indexOf(':')>0)
value=value.substring(value.indexOf(':')+1,value.length());
v.add(new QName(value, enumKind.getLocalPart()));
}
}
}
// The first element in the vector is a TypeEntry.
v.add(0,baseEType);
typedata.setRestrictiondata(v);
typedata.setRestriction(true);
// Add schema-defined simple type to mapping table - TODO: not sure we need this anymore.
CUtils.addSchemaDefinedSimpleType(typedataQName, class4qname);
if (typedataQNameSanitized != null)
CUtils.addSchemaDefinedSimpleType(typedataQNameSanitized, class4qnameSanitized);
}
}
return;
}
/**
* Work out the various conditions that dictate whether this type will be generated into a new
* file or not.
* This method is only very partially implemented.
*
* @param type
* @param typedata
* @return true if the type will not be generated. False otherwise
*/
private boolean isTypeGenerated(TypeEntry type, Type typedata)
{
// If the referenced type is actually a type that will not get generated because it's
// a base type array then tell other people of this case. Do this to two levels of indirection
if(type.getRefType()!=null)
if(type.getRefType().getRefType()!=null && type.getRefType().getRefType().isBaseType())
return false;
if (typedata.isAnonymous())
return false;
else
return true;
}
/**
* Process service operations, generating information about each operation.
*
* @param bindingEntry
* @return array of MethodInfo objects.
* @throws WrapperFault
*/
public ArrayList processServiceMethods(BindingEntry bindingEntry,
boolean wsdlWrappingStyle,
boolean userRequestedWSDLWrappingStyle) throws WrapperFault
{
PortType portType = bindingEntry.getBinding().getPortType();
if (portType == null)
throw new WrapperFault("Port type specified in binding '" + bindingEntry.getBinding().getQName().getLocalPart() + "' not found");
ArrayList serviceMethods = new ArrayList();
//get operation list
Iterator oplist = portType.getOperations().iterator();
while (oplist.hasNext())
{
Operation op = (Operation) oplist.next();
MethodInfo minfo = new MethodInfo(op.getName());
// This chunk of code is new and we hope to use it more in the future to replace some of the
// things we do to process parameters.
// When getOperationParameters() is called, the code, assuming user did not request unwrapped,
// will determine whether the operation is eligible for wrapped-style. The bad thing is that
// isWrapped() is a method on the SymbolTable class. So before processing an operation,
// we call setWrapped(false) before calling getOperationParameters() so that we can determine
// on a per-operation basis whether the operation is eligible for wrapped-style processing.
c_symbolTable.setWrapped(false);
Parameters opParams=null;
try
{
opParams = c_symbolTable.getOperationParameters(op, "", bindingEntry);
minfo.setOperationParameters(opParams);
minfo.setEligibleForWrapped(c_symbolTable.isWrapped());
// mark the method as wrapped or unwrapped.
if (!wsdlWrappingStyle || !minfo.isEligibleForWrapped())
{
minfo.setIsUnwrapped(true);
minfo.setConsumeBodyOnMessageValidation(false);
}
}
catch (IOException e)
{
throw new WrapperFault(e);
}
if (c_verbose)
{
System.out.println("\n\n-----------------------------------------------");
System.out.println("Parameters for operation: " + op.getName());
System.out.println("-----------------------------------------------");
System.out.println(opParams);
System.out.println("-----------------------------------------------");
}
//setting the faults
addFaultInfo(op.getFaults(), minfo);
// process input and response messages
if ("document".equals(bindingEntry.getBindingStyle().getName()))
{
if (userRequestedWSDLWrappingStyle && !minfo.isEligibleForWrapped())
System.out.println("INFORMATIONAL: Operation '" + op.getName() + "' is not eligible for wrapper-style, generating non-wrapper style.");
addDocumentStyleInputMessageToMethodInfo(bindingEntry, op, minfo);
addDocumentStyleOutputMessageToMethodInfo(bindingEntry, op, minfo);
}
else
{
addRPCStyleInputMessageToMethodInfo(bindingEntry, op, minfo);
addRPCStyleOutputMessageToMethodInfo(bindingEntry, op, minfo);
}
//add operation to operation List
serviceMethods.add(minfo);
}
// Need to get some stuff from binding element such as SOAPAction and namespace for
// each operation - we store the information in the method.
List operations = bindingEntry.getBinding().getBindingOperations();
if (operations != null)
{
for (int i = 0; i < operations.size(); i++)
{
//for the each binding operation found
if (operations.get(i) instanceof javax.wsdl.BindingOperation)
{
javax.wsdl.BindingOperation bindinop = (javax.wsdl.BindingOperation) operations.get(i);
String name = bindinop.getName();
MethodInfo method = null;
for (int ii = 0; ii < serviceMethods.size(); ii++)
if (((MethodInfo) serviceMethods.get(ii)).getMethodname().equals(name))
method = (MethodInfo) serviceMethods.get(ii);
if (method == null)
throw new WrapperFault("The binding and portType elements do not match.");
// Get binding operation information and store in method for later use.
WSDLInfo.updateMethodInfoFromBinding(bindinop, method);
}
}
}
return serviceMethods;
}
/**
* @param op
* @param minfo MethodInfo object into which output message and it's elements are to be added
* @throws WrapperFault
*/
private void addRPCStyleOutputMessageToMethodInfo(BindingEntry bindingEntry, Operation op, MethodInfo minfo) throws WrapperFault
{
if (op.getOutput() == null)
return;
ParameterInfo pinfo;
Iterator returnlist;
minfo.setInputMessage(op.getInput().getMessage().getQName());
minfo.setOutputMessage(op.getOutput().getMessage().getQName());
if (op.getParameterOrdering() != null)
{
for (int ix = 0; ix < op.getParameterOrdering().size(); ix++)
{
Part p = (Part) (op.getOutput().getMessage().getParts().get((String) op.getParameterOrdering().get(ix)));
if (p == null)
continue;
pinfo = createParameterInfo(p);
if (null != pinfo)
minfo.addOutputParameter(pinfo);
}
// TODO recheck parameter ordering logic....
// there can be more output parameters than in parameterOrder list (partial parameter ordering)
returnlist = op.getOutput().getMessage().getParts().values().iterator();
while (returnlist.hasNext())
{
//RPC style messages can have multiple parts
Part p = (Part) returnlist.next();
if (op.getParameterOrdering().contains(p.getName())
|| (bindingEntry.isOutHeaderPart(op.getName(), p.getName())))
continue;
pinfo = createParameterInfo(p);
if (null != pinfo)
minfo.addOutputParameter(pinfo);
}
}
else
{
returnlist = op.getOutput().getMessage().getParts().values().iterator();
while (returnlist.hasNext())
{
//RPC style messages can have multiple parts
Part p = ((Part) returnlist.next());
if (bindingEntry.isOutHeaderPart(op.getName(), p.getName()))
continue;
pinfo = createParameterInfo(p);
if (null != pinfo)
minfo.addOutputParameter(pinfo);
}
}
}
/**
* @param minfo MethodInfo object into which output message and it's elements are to be added
* @param part
* @throws WrapperFault
*/
private void addDocumentStyleOutputMessageToMethodInfo(BindingEntry bindingEntry, Operation op, MethodInfo minfo) throws WrapperFault
{
if (op.getOutput() == null)
return;
Part part = null;
// For now, skip over soap header parts
Iterator returnlist = op.getOutput().getMessage().getParts().values().iterator();
while (returnlist.hasNext())
{
part = (Part) returnlist.next();
if (bindingEntry.isOutHeaderPart(op.getName(), part.getName()))
part = null;
else
break;
}
// If no output parameter, simply return.
if (part == null)
return;
QName qname;
QName minfoqname;
TypeEntry elementTypeEntry;
Element element = c_symbolTable.getElement(part.getElementName());
if (element == null)
{
elementTypeEntry = c_symbolTable.getType(part.getTypeName());
qname = elementTypeEntry.getQName();
minfoqname = elementTypeEntry.getQName();
}
else
{
elementTypeEntry = element.getRefType();
qname = elementTypeEntry.getQName();
minfoqname = element.getQName();
}
minfo.setOutputMessage(minfoqname);
if (qname == null)
return;
Type type = c_typeMap.getType(qname);
if (type == null)
throw new WrapperFault("Unregistered type " + qname + " referenced!");
// TODO - need to look into this more.
// For wrapped style, inner attributes and elements are added as parameters.
// For unwrapped style, objects are used for the parameters (i.e. classes or structures).
Iterator elementNames = type.getElementnames();
Iterator attributes = type.getAttributes();
if (!minfo.isUnwrapped())
{
if (!elementNames.hasNext())
{
// Type must be simple or primitive...we do a check just to make sure.
if (type.isSimpleType() || type.isPrimitiveType())
{
String elementName = (String) element.getQName().getLocalPart();
ParameterInfo pinfo = new ParameterInfo();
pinfo.setType(type);
pinfo.setParamName(elementName, c_typeMap);
pinfo.setElementName(element.getQName());
pinfo.setAnyElement(type.isAnyElement());
minfo.addOutputParameter(pinfo);
minfo.setConsumeBodyOnMessageValidation(false);
}
}
else
{
while (elementNames.hasNext())
{
String elementname = (String) elementNames.next();
CElementDecl eleinfo = type.getElementForElementName(elementname);
Type innerType = eleinfo.getType();
ParameterInfo pinfo = new ParameterInfo();
pinfo.setType(innerType);
pinfo.setParamName(elementname, c_typeMap);
pinfo.setArray(eleinfo.getMaxOccurs() > 1);
pinfo.setNillable(eleinfo.isNillable());
pinfo.setOptional(eleinfo.getMinOccurs() == 0);
pinfo.setElementName(type.getElementForElementName(elementname).getName());
pinfo.setAnyElement(innerType.isAnyElement());
minfo.addOutputParameter(pinfo);
}
}
}
else
{
// Ensure there is a response, if not, then operation is a one-way operation.
if (type.isSimpleType()
|| type.isPrimitiveType()
|| elementNames.hasNext()
|| (attributes != null && attributes.hasNext()))
{
String elementName = (String) element.getQName().getLocalPart();
ParameterInfo pinfo = new ParameterInfo();
pinfo.setType(type);
type.setIsUnwrappedOutputType(true);
pinfo.setParamName(elementName, c_typeMap);
if (element != null)
pinfo.setElementName(element.getQName());
else
pinfo.setElementName(type.getName());
pinfo.setAnyElement(type.isAnyElement());
// Let us be nice and uppercase the first character in type name,
// in addition to resolving method name/type conflicts.
type.setLanguageSpecificName(generateNewTypeName(type, minfo));
minfo.addOutputParameter(pinfo);
}
else if (!elementNames.hasNext())
{
// empty element....check message response but no deserialization necessary
minfo.setConsumeBodyOnMessageValidation(true);
}
}
}
/**
* @param op
* @param minfo
* @throws WrapperFault
*/
private void addRPCStyleInputMessageToMethodInfo(BindingEntry bindingEntry, Operation op, MethodInfo minfo)
throws WrapperFault
{
ParameterInfo pinfo;
Iterator paramlist;
minfo.setInputMessage(op.getInput().getMessage().getQName());
if (op.getParameterOrdering() != null)
{
for (int ix = 0; ix < op.getParameterOrdering().size(); ix++)
{
Part p = (Part) (op.getInput()
.getMessage()
.getParts()
.get((String) op.getParameterOrdering().get(ix)));
if (p == null
|| bindingEntry.isInHeaderPart(op.getName(), p.getName()))
continue;
pinfo = createParameterInfo(p);
if (null != pinfo)
minfo.addInputParameter(pinfo);
}
}
else
{
paramlist = op.getInput().getMessage().getParts().values().iterator();
while (paramlist.hasNext())
{
//RPC style messages can have multiple parts
Part p = (Part) paramlist.next();
if (bindingEntry.isInHeaderPart(op.getName(), p.getName()))
continue;
pinfo = createParameterInfo(p);
if (null != pinfo)
minfo.addInputParameter(pinfo);
}
}
}
/**
* @param op
* @param minfo
* @throws WrapperFault
*/
private void addDocumentStyleInputMessageToMethodInfo(BindingEntry bindingEntry, Operation op, MethodInfo minfo)
throws WrapperFault
{
Part part = null;
// For now, skip over soap header parts.
Iterator paramlist = op.getInput().getMessage().getParts().values().iterator();
while (paramlist.hasNext())
{
part = (Part) paramlist.next();
if (bindingEntry.isInHeaderPart(op.getName(), part.getName()))
part = null;
else
break;
}
// If no input parameter, simply return.
if (part == null)
return;
QName minfoqname;
QName qname;
Element element = c_symbolTable.getElement(part.getElementName());
if (element == null)
{
// the part reference a type.
qname = c_symbolTable.getType(part.getTypeName()).getQName();
minfoqname = c_symbolTable.getType(part.getTypeName()).getQName();
}
else
{
qname = element.getRefType().getQName();
minfoqname = element.getQName();
}
minfo.setInputMessage(minfoqname);
if (qname == null)
return;
Type type = c_typeMap.getType(qname);
if (type == null)
throw new WrapperFault("unregistered type " + qname + " referenced");
// For wrapped style, inner attributes and elements are added as parameters.
// For unwrapped style, objects are used for the parameters (i.e. classes or structures).
Iterator elementNames = type.getElementnames();
Iterator attributes = type.getAttributes();
if (!minfo.isUnwrapped())
{
// Add input elements to method info
while (elementNames.hasNext())
{
String elementname = (String) elementNames.next();
CElementDecl eleinfo = type.getElementForElementName(elementname);
Type innerType = eleinfo.getType();
ParameterInfo pinfo = new ParameterInfo();
pinfo.setType(innerType);
pinfo.setParamName(elementname, c_typeMap);
pinfo.setArray(eleinfo.getMaxOccurs() > 1);
pinfo.setElementName(type.getElementForElementName(elementname).getName());
pinfo.setAnyElement(innerType.isAnyElement());
pinfo.setNillable(eleinfo.isNillable());
pinfo.setOptional(eleinfo.getMinOccurs() == 0);
minfo.addInputParameter(pinfo);
}
// add input attributes to method info - TODO probably can remove this chunk of code.
if (attributes != null)
{
while (attributes.hasNext())
{
CContainedAttribute attr = (CContainedAttribute)attributes.next();
ParameterInfo pinfo = new ParameterInfo();
pinfo.setType(attr.getType());
pinfo.setParamName(attr.getName(), c_typeMap);
pinfo.setElementName(attr.getType().getName());
pinfo.setAttribute(true);
minfo.addInputParameter(pinfo);
}
}
}
else
{
// If input element is complex and does not contain any sub-elements or attributes, we ignore.
if (type.isSimpleType()
|| type.isPrimitiveType()
|| elementNames.hasNext()
|| (attributes != null && attributes.hasNext()))
{
String elementName;
if (element != null)
elementName = element.getQName().getLocalPart();
else
elementName = type.getName().getLocalPart();
ParameterInfo pinfo = new ParameterInfo();
pinfo.setType(type);
type.setIsUnwrappedInputType(true);
pinfo.setParamName(elementName, c_typeMap);
if (element != null)
pinfo.setElementName(element.getQName());
else
pinfo.setElementName(type.getName());
pinfo.setAnyElement(type.isAnyElement());
// Let us be nice and uppercase the first character in type name,
// in addition to resolving method name/type conflicts.
type.setLanguageSpecificName(generateNewTypeName(type, minfo));
minfo.addInputParameter(pinfo);
}
}
}
/**
* Adds faults.
*
* @param faults
* @param methodinfo
* @throws WrapperFault
*/
private void addFaultInfo(Map faults, MethodInfo methodinfo)
throws WrapperFault
{
if (faults == null)
return;
Iterator faultIt = faults.values().iterator();
while (faultIt.hasNext())
{
Fault fault = (Fault) faultIt.next();
FaultInfo faultinfo = new FaultInfo(fault.getName());
Map parts = fault.getMessage().getParts();
Iterator partIt = parts.values().iterator();
while (partIt.hasNext())
{
ParameterInfo pinfo = createParameterInfo((Part) partIt.next());
pinfo.getType().setAsFault(true);
faultinfo.addParam(pinfo);
}
methodinfo.addFaultType(faultinfo);
}
}
/**
*
* @param part
* @return
* @throws WrapperFault
*/
private ParameterInfo createParameterInfo(Part part) throws WrapperFault
{
QName qname = part.getTypeName();
if (qname == null)
{
Element element = c_symbolTable.getElement(part.getElementName());
qname = element.getRefType().getQName();
}
Type type = c_typeMap.getType(qname);
if (type == null)
throw new WrapperFault("unregistered type " + qname + " referred");
ParameterInfo pinfo = new ParameterInfo();
pinfo.setType(type);
pinfo.setParamName(part.getName(), c_typeMap);
pinfo.setElementName(part.getElementName());
return pinfo;
}
/**
* Resolves name conflict between a method name and a type name.
* When doing document-literal, usually the name of the wrapper element is same as the
* operation name.
*
* @param type
* @param minfo
* @return the new type name that does not conflict with the operation name.
*/
private String generateNewTypeName(Type type, MethodInfo minfo)
{
String minfo_nm = minfo.getMethodname();
String type_nm = type.getLanguageSpecificName();
if (CUtils.isPrimitiveType(type_nm))
return type_nm;
String newName = CUtils.capitalizeFirstCharacter(type_nm);
if (!minfo_nm.equals(newName))
return newName;
return newName + "_t";
}
/**
* Checks if binding entry is SOAP and specified version.
* @param be
* @return
*/
private static boolean isSOAPBinding(BindingEntry be, String soapNamespace)
{
Binding b = be.getBinding();
if ((be.getBindingType() == BindingEntry.TYPE_SOAP))
{
String ns = soapNamespace;
SOAPBinding soapbinding = (SOAPBinding)getExtensibilityElement(b, INSTANCEOF_SOAPBINDING);
if (soapbinding != null && null != soapbinding.getElementType().getNamespaceURI())
ns = soapbinding.getElementType().getNamespaceURI();
return ns.equals(soapNamespace);
}
return false;
}
}