You are viewing a plain text version of this content. The canonical link for it is here.
Posted to java-dev@axis.apache.org by to...@apache.org on 2002/05/30 20:55:22 UTC
cvs commit: xml-axis/java/src/org/apache/axis/encoding/ser BeanSerializer.java
tomj 02/05/30 11:55:22
Modified: java/test/wsdl Wsdl2javaTestSuite.xml
java/src/org/apache/axis/wsdl/fromJava Types.java
java/src/org/apache/axis/message RPCElement.java
java/src/org/apache/axis/wsdl/toJava JavaStubWriter.java
JavaDeployWriter.java JavaBeanHelperWriter.java
java/src/org/apache/axis/description FieldDesc.java
java/src/org/apache/axis/encoding/ser BeanSerializer.java
Added: java/test/wsdl/omit OmitTestCase.java OmitImpl.java
omit.wsdl
Log:
Add support for omitting elements if their values is null and the WSDL
says minOccurs=0.
Add a wsdl test case: "omit".
File level changes:
wsdl2javaTestSuite: Add the omit test case
Types: add minOccurs=0 maxOccurs=1 when creating an omittable type element.
RPCElement: Set the operation if elementIsFirstParam is true.
JavaStubWriter: Use getRefType in setting the return type QName.
JavaDeployWriter: check getRefType() for null before using.
JavaBeanHelperWriter: add a call to setMinOccursIs0() in the meta
information about the fields.
FieldDesc: add minOcurrsIs0 flag (defaults to false) to field meta-data
BeanSerializer: Omit fields which are null if their metadata has the
minOccursIs0 flag set.
Revision Changes Path
1.101 +7 -1 xml-axis/java/test/wsdl/Wsdl2javaTestSuite.xml
Index: Wsdl2javaTestSuite.xml
===================================================================
RCS file: /home/cvs/xml-axis/java/test/wsdl/Wsdl2javaTestSuite.xml,v
retrieving revision 1.100
retrieving revision 1.101
diff -u -r1.100 -r1.101
--- Wsdl2javaTestSuite.xml 30 May 2002 15:47:13 -0000 1.100
+++ Wsdl2javaTestSuite.xml 30 May 2002 18:55:21 -0000 1.101
@@ -28,7 +28,13 @@
<echo message="Classpath for wsdl2java task : ${test-classpath.property}"/>
-->
<echo message="Running WSDL2Java and Java2WSDL Emitters"/>
-
+
+ <!-- Omit Test -->
+ <wsdl2java url="test/wsdl/omit/omit.wsdl"
+ output="build/work"
+ serverSide="yes">
+ </wsdl2java>
+
<!-- WidgetPrice Java to WSDL Samples -->
<java2wsdl output="build/work/samples/userguide/example6/WidgetPrice.wsdl"
className= "samples.userguide.example6.WidgetPrice"
1.29 +809 -804 xml-axis/java/src/org/apache/axis/wsdl/fromJava/Types.java
Index: Types.java
===================================================================
RCS file: /home/cvs/xml-axis/java/src/org/apache/axis/wsdl/fromJava/Types.java,v
retrieving revision 1.28
retrieving revision 1.29
diff -u -r1.28 -r1.29
--- Types.java 30 May 2002 03:06:12 -0000 1.28
+++ Types.java 30 May 2002 18:55:21 -0000 1.29
@@ -1,804 +1,809 @@
-
-/*
- * The Apache Software License, Version 1.1
- *
- *
- * Copyright (c) 2001 The Apache Software Foundation. All rights
- * reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. The end-user documentation included with the redistribution,
- * if any, must include the following acknowledgment:
- * "This product includes software developed by the
- * Apache Software Foundation (http://www.apache.org/)."
- * Alternately, this acknowledgment may appear in the software itself,
- * if and wherever such third-party acknowledgments normally appear.
- *
- * 4. The names "Axis" and "Apache Software Foundation" must
- * not be used to endorse or promote products derived from this
- * software without prior written permission. For written
- * permission, please contact apache@apache.org.
- *
- * 5. Products derived from this software may not be called "Apache",
- * nor may "Apache" appear in their name, without prior written
- * permission of the Apache Software Foundation.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
- * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
- * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
- * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
- * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
- * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
- * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
- * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- * ====================================================================
- *
- * This software consists of voluntary contributions made by many
- * individuals on behalf of the Apache Software Foundation. For more
- * information on the Apache Software Foundation, please see
- * <http://www.apache.org/>.
- */
-
-package org.apache.axis.wsdl.fromJava;
-
-import org.apache.axis.AxisFault;
-import org.apache.axis.Constants;
-import org.apache.axis.encoding.Serializer;
-import org.apache.axis.encoding.SerializerFactory;
-import org.apache.axis.encoding.SimpleType;
-import org.apache.axis.encoding.TypeMapping;
-import org.apache.axis.encoding.ser.BeanSerializerFactory;
-import org.apache.axis.utils.JavaUtils;
-import org.apache.axis.utils.XMLUtils;
-import org.w3c.dom.Attr;
-import org.w3c.dom.Document;
-import org.w3c.dom.Element;
-import org.w3c.dom.NamedNodeMap;
-import org.w3c.dom.NodeList;
-
-import javax.wsdl.Definition;
-import javax.wsdl.QName;
-import java.lang.reflect.Field;
-import java.lang.reflect.Modifier;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-
-/**
- *
- * <p>Description: </p> This class is used to recursively serializes a Java Class into
- * an XML Schema representation.
- *
- * It has utility methods to create a schema node, assosiate namespaces to the various types
- *
- *
- * @author unascribed
- */
-public class Types {
-
- Definition def;
- Namespaces namespaces = null;
- TypeMapping tm;
- TypeMapping defaultTM;
- String targetNamespace;
- Element wsdlTypesElem = null;
- HashMap schemaTypes = null;
- HashMap schemaElementNames = null;
- HashMap schemaUniqueElementNames = null;
- List stopClasses = null;
-
- /**
- * This class serailizes a <code>Class</code> to XML Schema. The constructor
- * provides the context for the streamed node within the WSDL document
- * @param def WSDL Definition Element to declare namespaces
- * @param tm TypeMappingRegistry to handle known types
- * @param defaultTM default TM
- * @param namespaces user defined or autogenerated namespace and prefix maps
- * @param targetNamespace targetNamespace of the document
- */
- public Types(Definition def,
- TypeMapping tm,
- TypeMapping defaultTM,
- Namespaces namespaces,
- String targetNamespace,
- List stopClasses) {
- this.def = def;
- createDocumentFragment();
- this.tm = tm;
- this.defaultTM = defaultTM;
- this.namespaces = namespaces;
- this.targetNamespace = targetNamespace;
- this.stopClasses = stopClasses;
- schemaElementNames = new HashMap();
- schemaUniqueElementNames = new HashMap();
- schemaTypes = new HashMap();
- }
-
- /**
- * Serialize the Class as XML schema to the document.
- * Create a types node for the WSDL if one doesn't exist
- * Create a schema node for the Class namespace, if one doesn't exist
- *
- * In case of a primitive type, no need to stream out anything, just return
- * the QName of the primitive type
- *
- * @param type <code>Class</code> to generate the XML Schema info for
- * @return the QName of the generated Schema type, null if void
- */
- public QName writePartType(Class type) throws Exception {
- if (type.getName().equals("void"))
- return null;
- if (isSimpleType(type)) {
- javax.xml.rpc.namespace.QName qName = getTypeQName(type);
- return getWsdlQName(qName);
- }else {
- if (wsdlTypesElem == null)
- writeWsdlTypesElement();
- return writeTypeAsElement(type);
- }
- }
-
- /**
- * Create a schema element for the given type
- * @param type the class type
- * @return the QName of the generated Element
- */
- private QName writeTypeAsElement(Class type) throws Exception {
- QName qName = writeTypeNamespace(type);
- String elementType = writeType(type);
- if (elementType != null) {
- Element element = createRootElement(qName, elementType, isNullable(type));
- if (element != null)
- writeSchemaElement(qName,element);
- return qName;
- }
- return null;
- }
-
- /**
- * write out the namespace declaration and return the type QName for the
- * given <code>Class</code>
- *
- * @param type input Class
- * @return QName for the schema type representing the class
- */
- private QName writeTypeNamespace(Class type) {
- javax.xml.rpc.namespace.QName qName = getTypeQName(type);
- String pref = def.getPrefix(qName.getNamespaceURI());
- if (pref == null)
- def.addNamespace(namespaces.getCreatePrefix(qName.getNamespaceURI()), qName.getNamespaceURI());
- return getWsdlQName(qName);
- }
-
- /**
- * Return the QName of the specified javaType
- * @param javaType input javaType Class
- * @return QName
- */
- private javax.xml.rpc.namespace.QName getTypeQName(Class javaType) {
- javax.xml.rpc.namespace.QName qName = null;
-
- // Use the typeMapping information to lookup the qName.
- javax.xml.rpc.namespace.QName dQName = null;
- if (defaultTM != null) {
- dQName = defaultTM.getTypeQName(javaType);
- }
- if (tm != null) {
- qName = tm.getTypeQName(javaType);
- }
- if (qName == null) {
- qName = dQName;
- } else if (qName != null && qName != dQName) {
- // If the TM and default TM resulted in different
- // names, choose qName unless it is a schema namespace.
- // (i.e. prefer soapenc primitives over schema primitives)
- if (Constants.isSchemaXSD(qName.getNamespaceURI())) {
- qName = dQName;
- }
- }
-
- // If the javaType is an array and the qName is
- // SOAP_ARRAY, construct the QName using the
- // QName of the component type
- if (javaType.isArray() &&
- qName != null &&
- Constants.equals(Constants.SOAP_ARRAY, qName)) {
- Class componentType = javaType.getComponentType();
- // If component namespace uri == targetNamespace
- // Construct ArrayOf<componentLocalPart>
- // Else
- // Construct ArrayOf_<componentPrefix>_<componentLocalPart>
- javax.xml.rpc.namespace.QName cqName = getTypeQName(componentType);
- if (targetNamespace.equals(cqName.getNamespaceURI())) {
- qName = new javax.xml.rpc.namespace.QName(
- targetNamespace,
- "ArrayOf" + cqName.getLocalPart());
- } else {
- String pre = namespaces.getCreatePrefix(cqName.getNamespaceURI());
- qName = new javax.xml.rpc.namespace.QName(
- targetNamespace,
- "ArrayOf_" + pre + "_" + cqName.getLocalPart());
- }
- return qName;
- }
-
- // If a qName was not found construct one using the
- // class name information.
- if (qName == null) {
- String pkg = getPackageNameFromFullName(javaType.getName());
- String lcl = getLocalNameFromFullName(javaType.getName());
-
- String ns = namespaces.getCreate(pkg);
- namespaces.getCreatePrefix(ns);
- String localPart = lcl.replace('$', '_');
- qName = new javax.xml.rpc.namespace.QName(ns, localPart);
- }
-
- return qName;
- }
-
- /**
- * Utility method to get the package name from a fully qualified java class name
- * @param full input class name
- * @return package name
- */
- public static String getPackageNameFromFullName(String full) {
- if (full.lastIndexOf('.') < 0)
- return "";
- else
- return full.substring(0, full.lastIndexOf('.'));
- }
-
- /**
- * Utility method to get the local class name from a fully qualified java class name
- * @param full input class name
- * @return package name
- */
- public static String getLocalNameFromFullName(String full) {
- if (full.lastIndexOf('.') < 0)
- return full;
- else
- return full.substring(full.lastIndexOf('.')+1);
- }
-
- /**
- * Write out the given Element into the appropriate schema node.
- * If need be create the schema node as well
- *
- * @param qName qName to get the namespace of the schema node
- * @param element the Element to append to the Schema node
- */
- public void writeSchemaElement(QName qName, Element element) {
- Element schemaElem = null;
- NodeList nl = wsdlTypesElem.getChildNodes();
- for (int i = 0; i < nl.getLength(); i++ ) {
- NamedNodeMap attrs = nl.item(i).getAttributes();
- for (int n = 0; n < attrs.getLength(); n++) {
- Attr a = (Attr)attrs.item(n);
- if (a.getName().equals("targetNamespace") &&
- a.getValue().equals(qName.getNamespaceURI()))
- schemaElem = (Element)nl.item(i);
- }
- }
- if (schemaElem == null) {
- schemaElem = docHolder.createElement("schema");
- wsdlTypesElem.appendChild(schemaElem);
- schemaElem.setAttribute("xmlns", Constants.NS_URI_CURRENT_SCHEMA_XSD);
- schemaElem.setAttribute("targetNamespace", qName.getNamespaceURI());
- }
- schemaElem.appendChild(element);
- }
-
- /**
- * Get the Types element for the WSDL document. If not present, create one
- * @throws Exception
- */
- private void writeWsdlTypesElement() throws Exception {
- if (wsdlTypesElem == null) {
- // Create a <wsdl:types> element corresponding to the wsdl namespaces.
- wsdlTypesElem =
- docHolder.createElementNS(Constants.NS_URI_CURRENT_WSDL, "types");
- wsdlTypesElem.setPrefix(Constants.NS_PREFIX_WSDL);
- }
- }
-
- /**
- * Write a schema representation for the given <code>Class</code>. Recurse
- * through all the public fields as well as fields represented by java
- * bean compliant accessor methods.
- *
- * Then return the qualified string representation of the generated type
- *
- * @param type Class for which to generate schema
- * @return a prefixed string for the schema type
- * @throws Exception
- */
- public String writeType(Class type) throws Exception {
-
- // Quick return if schema type
- if (isSimpleType(type)) {
- QName qName = getWsdlQName(getTypeQName(type));
- if (Constants.isSchemaXSD(qName.getNamespaceURI())) {
- return Constants.NS_PREFIX_SCHEMA_XSD + ":" +
- qName.getLocalPart();
- } else {
- return Constants.NS_PREFIX_SOAP_ENC + ":" +
- qName.getLocalPart();
- }
- }
-
- // look up the serializer in the TypeMappingRegistry
- Serializer ser = null;
- SerializerFactory factory = null;
- if (tm != null) {
- factory = (SerializerFactory)tm.getSerializer(type);
- } else {
- factory = (SerializerFactory)defaultTM.getSerializer(type);
- }
- if (factory == null) {
- // If no factory is found, try the BeanSerializerFactory if
- // the type is not Throwable. (There is no mapping for
- // java types that extend Throwable.)
- factory = new BeanSerializerFactory(type, getTypeQName(type));
- }
- if (factory != null) {
- ser = (Serializer)factory.getSerializerAs(Constants.AXIS_SAX);
- }
-
- // if we can't get a serializer, that is bad.
- if (ser == null) {
- throw new AxisFault(
- JavaUtils.getMessage("NoSerializer00", type.getName()));
- }
-
- // Write the namespace
- QName qName = writeTypeNamespace(type);
-
- // If an array the component type should be processed first
- String componentTypeName = null;
- Class componentType = null;
- if (type.isArray()) {
- String dimString = "[]";
- componentType = type.getComponentType();
- if (componentType.isArray()) {
- while (componentType.isArray()) {
- dimString += "[]";
- componentType = componentType.getComponentType();
- }
- }
- componentTypeName = writeType(componentType) + dimString;
- }
-
- String soapTypeName = qName.getLocalPart();
- String prefix = namespaces.getCreatePrefix(qName.getNamespaceURI());
- String prefixedName = prefix+":"+soapTypeName;
-
- // If processed before, or this is a known namespace, return
- if (!addToTypesList(qName, soapTypeName))
- return prefixedName;
-
- if (type.isArray()) {
- // ComplexType representation of array
- Element complexType = docHolder.createElement("complexType");
- writeSchemaElement(qName, complexType);
- complexType.setAttribute("name", soapTypeName);
-
- Element complexContent = docHolder.createElement("complexContent");
- complexType.appendChild(complexContent);
-
- Element restriction = docHolder.createElement("restriction");
- complexContent.appendChild(restriction);
- restriction.setAttribute("base",
- Constants.NS_PREFIX_SOAP_ENC + ":Array");
-
- Element attribute = docHolder.createElement("attribute");
- restriction.appendChild(attribute);
- attribute.setAttribute("ref",
- Constants.NS_PREFIX_SOAP_ENC +":arrayType");
- attribute.setAttribute(Constants.NS_PREFIX_WSDL +":arrayType",
- componentTypeName );
- } else {
- if (isEnumClass(type)) {
- writeEnumType(qName, type);
- } else {
- ser.writeSchema(this);
- }
- }
- return prefixedName;
- }
-
- /**
- * Returns true if indicated type matches the JAX-RPC enumeration class.
- * Note: supports JSR 101 version 0.6 Public Draft
- */
- public static boolean isEnumClass(Class cls) {
- try {
- java.lang.reflect.Method m = cls.getMethod("getValue", null);
- java.lang.reflect.Method m2 = cls.getMethod("toString", null);
- if (m != null && m2 != null) {
- java.lang.reflect.Method m3 =
- cls.getDeclaredMethod("fromString",
- new Class[] {java.lang.String.class});
- java.lang.reflect.Method m4 =
- cls.getDeclaredMethod("fromValue",
- new Class[] {m.getReturnType()});
-
- if (m3 != null &&
- Modifier.isStatic(m3.getModifiers()) &&
- Modifier.isPublic(m3.getModifiers()) &&
- m4 != null &&
- Modifier.isStatic(m4.getModifiers()) &&
- Modifier.isPublic(m4.getModifiers())) {
- // Return false if there is a setValue member method
- try {
- if (cls.getMethod("setValue",
- new Class[] {m.getReturnType()}) == null)
- return true;
- return false;
- } catch (java.lang.NoSuchMethodException e) {
- return true;
- }
- }
- }
- } catch (java.lang.NoSuchMethodException e) {}
- return false;
- }
-
- /**
- * Write Enumeration Complex Type
- * (Only supports enumeration classes of string types)
- * @param qName QName of type.
- * @param cls class of type
- */
- private void writeEnumType(QName qName, Class cls) throws Exception {
- if (!isEnumClass(cls))
- return;
- // Get the base type of the enum class
- java.lang.reflect.Method m = cls.getMethod("getValue", null);
- Class base = m.getReturnType();
-
- // Create simpleType, restriction elements
- Element simpleType = docHolder.createElement("simpleType");
- writeSchemaElement(qName, simpleType);
- simpleType.setAttribute("name", qName.getLocalPart());
- Element restriction = docHolder.createElement("restriction");
- simpleType.appendChild(restriction);
- String baseType = writeType(base);
- restriction.setAttribute("base", baseType);
-
- // Create an enumeration using the field values
- Field[] fields= cls.getDeclaredFields();
- for (int i=0; i < fields.length; i++) {
- Field field = fields[i];
- int mod = field.getModifiers();
-
- // Inspect each public static final field of the same type
- // as the base
- if (Modifier.isPublic(mod) &&
- Modifier.isStatic(mod) &&
- Modifier.isFinal(mod) &&
- field.getType() == base) {
- // Create an enumeration using the value specified
- Element enumeration = docHolder.createElement("enumeration");
- enumeration.setAttribute("value", field.get(null).toString());
- restriction.appendChild(enumeration);
-
- }
- }
-
- }
-
- /**
- * Create Element
- * @param qName the namespace of the created element
- * @param elementType schema type representation of the element
- * @param nullable nillable attribute of the element
- * @return the created Element
- */
- private Element createRootElement(QName qName,
- String elementType,
- boolean nullable) {
- if (!addToElementsList(qName))
- return null;
-
- Element element = docHolder.createElement("element");
-
- //Generate an element name that matches the type.
- // Previously a unique element name was generated.
- //String name = generateUniqueElementName(qName);
- String name = elementType.substring(elementType.lastIndexOf(":")+1);
-
- element.setAttribute("name", name);
- if (nullable)
- element.setAttribute("nillable", "true");
- element.setAttribute("type", elementType);
- return element;
- }
-
- /**
- * Create Element with a given name and type
- * @param elementName the name of the created element
- * @param elementType schema type representation of the element
- * @param nullable nullable attribute of the element
- * @return the created Element
- */
- public Element createElement(String elementName,
- String elementType,
- boolean nullable,
- Document docHolder) {
- Element element = docHolder.createElement("element");
- element.setAttribute("name", elementName);
- if (nullable)
- element.setAttribute("nillable", "true");
- element.setAttribute("type", elementType);
- return element;
- }
-
-
- /**
- * Create Attribute Element with a given name and type
- * @param elementName the name of the created element
- * @param elementType schema type representation of the element
- * @param nullable nullable attribute of the element
- * @return the created Element
- */
- public Element createAttributeElement(String elementName,
- String elementType,
- boolean nullable,
- Document docHolder) {
- Element element = docHolder.createElement("attribute");
- element.setAttribute("name", elementName);
- if (nullable)
- element.setAttribute("nillable", "true");
- element.setAttribute("type", elementType);
- return element;
- }
-
- /**
- * convert from JAX-RPC QName to WSDL QName
- * @param qName JAX-RPC QName
- * @return WSDL QName
- */
- public QName getWsdlQName (javax.xml.rpc.namespace.QName qName) {
- return new QName(qName.getNamespaceURI(), qName.getLocalPart());
- }
-
- /**
- * Is the given class one of the simple types defined by Schema
- * (per JSR 101 v.0.6)
- * @param type input Class
- * @return true if the type is a simple schema type
- */
- public boolean isSimpleSchemaType(Class type) {
- return (type == java.lang.String.class ||
- type == java.lang.Boolean.TYPE ||
- type == java.lang.Byte.TYPE ||
- type == java.lang.Double.TYPE ||
- type == java.lang.Float.TYPE ||
- type == java.lang.Integer.TYPE ||
- type == java.lang.Long.TYPE ||
- type == java.lang.Short.TYPE ||
- type == java.math.BigInteger.class ||
- type == java.math.BigDecimal.class ||
- type == javax.xml.rpc.namespace.QName.class ||
- type == java.util.Calendar.class ||
- type == byte[].class);
- }
-
- /**
- * Is the given class one of the simple types defined by SoapEncoding.
- * (per JSR 101 v.0.6)
- * @param type input Class
- * @return true if the type is a simple soap encoding type
- */
- boolean isSimpleSoapEncodingType(Class type) {
- return (type == java.lang.String.class ||
- type == java.lang.Boolean.class ||
- type == java.lang.Byte.class ||
- type == java.lang.Double.class ||
- type == java.lang.Float.class ||
- type == java.lang.Integer.class ||
- type == java.lang.Long.class ||
- type == java.lang.Short.class ||
- type == java.math.BigDecimal.class ||
- type == byte[].class);
- }
-
- /**
- * Is the given class one of the simple types
- * @param type input Class
- * @return true if the type is a simple type
- */
- boolean isSimpleType(Class type) {
- return (isSimpleSchemaType(type) ||
- isSimpleSoapEncodingType(type));
- }
-
- /**
- * Is the given class acceptable as an attribute
- * @param type input Class
- * @return true if the type is a simple, enum type or extends SimpleType
- */
- public boolean isAcceptableAsAttribute(Class type) {
- return isSimpleType(type) ||
- isEnumClass(type) ||
- implementsSimpleType(type);
- }
-
- /**
- * Does the class implement SimpleType
- * @param type input Class
- * @return true if the type implements SimpleType
- */
- boolean implementsSimpleType(Class type) {
- Class[] impls = type.getInterfaces();
- for(int i=0; i<impls.length; i++) {
- if (impls[i] == SimpleType.class) {
- return true;
- }
- }
- return false;
- }
- /**
- * Generates a unique element name for a given namespace of the form
- * el0, el1 ....
- *
- * @param qName the namespace for the generated element
- * @return elementname
- */
-// *** NOT USED? ***
-//
-// private String generateUniqueElementName(QName qName) {
-// Integer count = (Integer)schemaUniqueElementNames.get(qName.getNamespaceURI());
-// if (count == null)
-// count = new Integer(0);
-// else
-// count = new Integer(count.intValue() + 1);
-// schemaUniqueElementNames.put(qName.getNamespaceURI(), count);
-// return "el" + count.intValue();
-// }
-
- /**
- * Add the type to an ArrayList and return true if the Schema node
- * needs to be generated
- * If the type already exists, just return false to indicate that the type is already
- * generated in a previous iteration
- *
- * @param qName the name space of the type
- * @param typeName the name of the type
- * @return if the type is added returns true, else if the type is already present returns false
- */
- private boolean addToTypesList (QName qName, String typeName) {
- boolean added = false;
- ArrayList types = (ArrayList)schemaTypes.get(qName.getNamespaceURI());
- if (types == null) {
- types = new ArrayList();
- types.add(typeName);
- schemaTypes.put(qName.getNamespaceURI(), types);
- added = true;
- }
- else {
- if (!types.contains(typeName)) {
- types.add(typeName);
- added = true;
- }
- }
-
- // If addded, look at the namespace uri to see if the schema element should be
- // generated.
- if (added) {
- String prefix = namespaces.getCreatePrefix(qName.getNamespaceURI());
- if (prefix.equals(Constants.NS_PREFIX_SOAP_ENV) ||
- prefix.equals(Constants.NS_PREFIX_SOAP_ENC) ||
- prefix.equals(Constants.NS_PREFIX_SCHEMA_XSD) ||
- prefix.equals(Constants.NS_PREFIX_WSDL) ||
- prefix.equals(Constants.NS_PREFIX_WSDL_SOAP))
- return false;
- else
- return true;
- }
- return false;
- }
-
- /**
- * Add the element to an ArrayList and return true if the Schema element
- * needs to be generated
- * If the element already exists, just return false to indicate that the type is already
- * generated in a previous iteration
- *
- * @param qName the name space of the element
- * @return if the type is added returns true, else if the type is already present returns false
- */
- private boolean addToElementsList (QName qName) {
- boolean added = false;
- ArrayList elements = (ArrayList)schemaElementNames.get(qName.getNamespaceURI());
- if (elements == null) {
- elements = new ArrayList();
- elements.add(qName.getLocalPart());
- schemaElementNames.put(qName.getNamespaceURI(), elements);
- added = true;
- }
- else {
- if (!elements.contains(qName.getLocalPart())) {
- elements.add(qName.getLocalPart());
- added = true;
- }
- }
- return added;
- }
-
-
- /**
- * Determines if the field is nullable. All non-primitives except
- * for byte[] are nillable.
- *
- * @param type input Class
- * @return true if nullable
- */
- public boolean isNullable(Class type) {
- if (type.isPrimitive() ||
- (type.isArray() && type.getComponentType() == byte.class))
- return false;
- else
- return true;
- }
-
-
- /** @todo ravi: Get rid of Doccument fragment and import node stuuf,
- * once I have a handle on the wsdl4j mechanism to get at types.
- *
- * Switch over notes: remove docHolder, docFragment in favor of wsdl4j Types
- */
- //DocumentFragment docFragment;
- Document docHolder;
-
- private void createDocumentFragment () {
- this.docHolder = XMLUtils.newDocument();
- }
-
- /**
- * Inserts the type fragment into the given wsdl document
- * @param doc
- */
- public void insertTypesFragment(Document doc) {
-
- if (wsdlTypesElem != null) {
- // Import the wsdlTypesElement into the doc.
- org.w3c.dom.Node node = doc.importNode(wsdlTypesElem, true);
- // Insert the imported element at the beginning of the document
- doc.getDocumentElement().
- insertBefore(node,
- doc.getDocumentElement().getFirstChild());
- }
- }
-
- /**
- * Return the list of classes that we should not emit WSDL for.
- */
- public List getStopClasses() {
- return stopClasses;
- }
-
- /**
- * Create a DOM Element in this context
- */
- public Element createElement(String elementName)
- {
- return docHolder.createElement(elementName);
- }
-}
+
+/*
+ * The Apache Software License, Version 1.1
+ *
+ *
+ * Copyright (c) 2001 The Apache Software Foundation. All rights
+ * reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in
+ * the documentation and/or other materials provided with the
+ * distribution.
+ *
+ * 3. The end-user documentation included with the redistribution,
+ * if any, must include the following acknowledgment:
+ * "This product includes software developed by the
+ * Apache Software Foundation (http://www.apache.org/)."
+ * Alternately, this acknowledgment may appear in the software itself,
+ * if and wherever such third-party acknowledgments normally appear.
+ *
+ * 4. The names "Axis" and "Apache Software Foundation" must
+ * not be used to endorse or promote products derived from this
+ * software without prior written permission. For written
+ * permission, please contact apache@apache.org.
+ *
+ * 5. Products derived from this software may not be called "Apache",
+ * nor may "Apache" appear in their name, without prior written
+ * permission of the Apache Software Foundation.
+ *
+ * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
+ * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
+ * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This software consists of voluntary contributions made by many
+ * individuals on behalf of the Apache Software Foundation. For more
+ * information on the Apache Software Foundation, please see
+ * <http://www.apache.org/>.
+ */
+
+package org.apache.axis.wsdl.fromJava;
+
+import org.apache.axis.AxisFault;
+import org.apache.axis.Constants;
+import org.apache.axis.encoding.Serializer;
+import org.apache.axis.encoding.SerializerFactory;
+import org.apache.axis.encoding.SimpleType;
+import org.apache.axis.encoding.TypeMapping;
+import org.apache.axis.encoding.ser.BeanSerializerFactory;
+import org.apache.axis.utils.JavaUtils;
+import org.apache.axis.utils.XMLUtils;
+import org.w3c.dom.Attr;
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+import org.w3c.dom.NamedNodeMap;
+import org.w3c.dom.NodeList;
+
+import javax.wsdl.Definition;
+import javax.wsdl.QName;
+import java.lang.reflect.Field;
+import java.lang.reflect.Modifier;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+
+/**
+ *
+ * <p>Description: </p> This class is used to recursively serializes a Java Class into
+ * an XML Schema representation.
+ *
+ * It has utility methods to create a schema node, assosiate namespaces to the various types
+ *
+ *
+ * @author unascribed
+ */
+public class Types {
+
+ Definition def;
+ Namespaces namespaces = null;
+ TypeMapping tm;
+ TypeMapping defaultTM;
+ String targetNamespace;
+ Element wsdlTypesElem = null;
+ HashMap schemaTypes = null;
+ HashMap schemaElementNames = null;
+ HashMap schemaUniqueElementNames = null;
+ List stopClasses = null;
+
+ /**
+ * This class serailizes a <code>Class</code> to XML Schema. The constructor
+ * provides the context for the streamed node within the WSDL document
+ * @param def WSDL Definition Element to declare namespaces
+ * @param tm TypeMappingRegistry to handle known types
+ * @param defaultTM default TM
+ * @param namespaces user defined or autogenerated namespace and prefix maps
+ * @param targetNamespace targetNamespace of the document
+ */
+ public Types(Definition def,
+ TypeMapping tm,
+ TypeMapping defaultTM,
+ Namespaces namespaces,
+ String targetNamespace,
+ List stopClasses) {
+ this.def = def;
+ createDocumentFragment();
+ this.tm = tm;
+ this.defaultTM = defaultTM;
+ this.namespaces = namespaces;
+ this.targetNamespace = targetNamespace;
+ this.stopClasses = stopClasses;
+ schemaElementNames = new HashMap();
+ schemaUniqueElementNames = new HashMap();
+ schemaTypes = new HashMap();
+ }
+
+ /**
+ * Serialize the Class as XML schema to the document.
+ * Create a types node for the WSDL if one doesn't exist
+ * Create a schema node for the Class namespace, if one doesn't exist
+ *
+ * In case of a primitive type, no need to stream out anything, just return
+ * the QName of the primitive type
+ *
+ * @param type <code>Class</code> to generate the XML Schema info for
+ * @return the QName of the generated Schema type, null if void
+ */
+ public QName writePartType(Class type) throws Exception {
+ if (type.getName().equals("void"))
+ return null;
+ if (isSimpleType(type)) {
+ javax.xml.rpc.namespace.QName qName = getTypeQName(type);
+ return getWsdlQName(qName);
+ }else {
+ if (wsdlTypesElem == null)
+ writeWsdlTypesElement();
+ return writeTypeAsElement(type);
+ }
+ }
+
+ /**
+ * Create a schema element for the given type
+ * @param type the class type
+ * @return the QName of the generated Element
+ */
+ private QName writeTypeAsElement(Class type) throws Exception {
+ QName qName = writeTypeNamespace(type);
+ String elementType = writeType(type);
+ if (elementType != null) {
+ Element element = createRootElement(qName, elementType, isNullable(type));
+ if (element != null)
+ writeSchemaElement(qName,element);
+ return qName;
+ }
+ return null;
+ }
+
+ /**
+ * write out the namespace declaration and return the type QName for the
+ * given <code>Class</code>
+ *
+ * @param type input Class
+ * @return QName for the schema type representing the class
+ */
+ private QName writeTypeNamespace(Class type) {
+ javax.xml.rpc.namespace.QName qName = getTypeQName(type);
+ String pref = def.getPrefix(qName.getNamespaceURI());
+ if (pref == null)
+ def.addNamespace(namespaces.getCreatePrefix(qName.getNamespaceURI()), qName.getNamespaceURI());
+ return getWsdlQName(qName);
+ }
+
+ /**
+ * Return the QName of the specified javaType
+ * @param javaType input javaType Class
+ * @return QName
+ */
+ private javax.xml.rpc.namespace.QName getTypeQName(Class javaType) {
+ javax.xml.rpc.namespace.QName qName = null;
+
+ // Use the typeMapping information to lookup the qName.
+ javax.xml.rpc.namespace.QName dQName = null;
+ if (defaultTM != null) {
+ dQName = defaultTM.getTypeQName(javaType);
+ }
+ if (tm != null) {
+ qName = tm.getTypeQName(javaType);
+ }
+ if (qName == null) {
+ qName = dQName;
+ } else if (qName != null && qName != dQName) {
+ // If the TM and default TM resulted in different
+ // names, choose qName unless it is a schema namespace.
+ // (i.e. prefer soapenc primitives over schema primitives)
+ if (Constants.isSchemaXSD(qName.getNamespaceURI())) {
+ qName = dQName;
+ }
+ }
+
+ // If the javaType is an array and the qName is
+ // SOAP_ARRAY, construct the QName using the
+ // QName of the component type
+ if (javaType.isArray() &&
+ qName != null &&
+ Constants.equals(Constants.SOAP_ARRAY, qName)) {
+ Class componentType = javaType.getComponentType();
+ // If component namespace uri == targetNamespace
+ // Construct ArrayOf<componentLocalPart>
+ // Else
+ // Construct ArrayOf_<componentPrefix>_<componentLocalPart>
+ javax.xml.rpc.namespace.QName cqName = getTypeQName(componentType);
+ if (targetNamespace.equals(cqName.getNamespaceURI())) {
+ qName = new javax.xml.rpc.namespace.QName(
+ targetNamespace,
+ "ArrayOf" + cqName.getLocalPart());
+ } else {
+ String pre = namespaces.getCreatePrefix(cqName.getNamespaceURI());
+ qName = new javax.xml.rpc.namespace.QName(
+ targetNamespace,
+ "ArrayOf_" + pre + "_" + cqName.getLocalPart());
+ }
+ return qName;
+ }
+
+ // If a qName was not found construct one using the
+ // class name information.
+ if (qName == null) {
+ String pkg = getPackageNameFromFullName(javaType.getName());
+ String lcl = getLocalNameFromFullName(javaType.getName());
+
+ String ns = namespaces.getCreate(pkg);
+ namespaces.getCreatePrefix(ns);
+ String localPart = lcl.replace('$', '_');
+ qName = new javax.xml.rpc.namespace.QName(ns, localPart);
+ }
+
+ return qName;
+ }
+
+ /**
+ * Utility method to get the package name from a fully qualified java class name
+ * @param full input class name
+ * @return package name
+ */
+ public static String getPackageNameFromFullName(String full) {
+ if (full.lastIndexOf('.') < 0)
+ return "";
+ else
+ return full.substring(0, full.lastIndexOf('.'));
+ }
+
+ /**
+ * Utility method to get the local class name from a fully qualified java class name
+ * @param full input class name
+ * @return package name
+ */
+ public static String getLocalNameFromFullName(String full) {
+ if (full.lastIndexOf('.') < 0)
+ return full;
+ else
+ return full.substring(full.lastIndexOf('.')+1);
+ }
+
+ /**
+ * Write out the given Element into the appropriate schema node.
+ * If need be create the schema node as well
+ *
+ * @param qName qName to get the namespace of the schema node
+ * @param element the Element to append to the Schema node
+ */
+ public void writeSchemaElement(QName qName, Element element) {
+ Element schemaElem = null;
+ NodeList nl = wsdlTypesElem.getChildNodes();
+ for (int i = 0; i < nl.getLength(); i++ ) {
+ NamedNodeMap attrs = nl.item(i).getAttributes();
+ for (int n = 0; n < attrs.getLength(); n++) {
+ Attr a = (Attr)attrs.item(n);
+ if (a.getName().equals("targetNamespace") &&
+ a.getValue().equals(qName.getNamespaceURI()))
+ schemaElem = (Element)nl.item(i);
+ }
+ }
+ if (schemaElem == null) {
+ schemaElem = docHolder.createElement("schema");
+ wsdlTypesElem.appendChild(schemaElem);
+ schemaElem.setAttribute("xmlns", Constants.NS_URI_CURRENT_SCHEMA_XSD);
+ schemaElem.setAttribute("targetNamespace", qName.getNamespaceURI());
+ }
+ schemaElem.appendChild(element);
+ }
+
+ /**
+ * Get the Types element for the WSDL document. If not present, create one
+ * @throws Exception
+ */
+ private void writeWsdlTypesElement() throws Exception {
+ if (wsdlTypesElem == null) {
+ // Create a <wsdl:types> element corresponding to the wsdl namespaces.
+ wsdlTypesElem =
+ docHolder.createElementNS(Constants.NS_URI_CURRENT_WSDL, "types");
+ wsdlTypesElem.setPrefix(Constants.NS_PREFIX_WSDL);
+ }
+ }
+
+ /**
+ * Write a schema representation for the given <code>Class</code>. Recurse
+ * through all the public fields as well as fields represented by java
+ * bean compliant accessor methods.
+ *
+ * Then return the qualified string representation of the generated type
+ *
+ * @param type Class for which to generate schema
+ * @return a prefixed string for the schema type
+ * @throws Exception
+ */
+ public String writeType(Class type) throws Exception {
+
+ // Quick return if schema type
+ if (isSimpleType(type)) {
+ QName qName = getWsdlQName(getTypeQName(type));
+ if (Constants.isSchemaXSD(qName.getNamespaceURI())) {
+ return Constants.NS_PREFIX_SCHEMA_XSD + ":" +
+ qName.getLocalPart();
+ } else {
+ return Constants.NS_PREFIX_SOAP_ENC + ":" +
+ qName.getLocalPart();
+ }
+ }
+
+ // look up the serializer in the TypeMappingRegistry
+ Serializer ser = null;
+ SerializerFactory factory = null;
+ if (tm != null) {
+ factory = (SerializerFactory)tm.getSerializer(type);
+ } else {
+ factory = (SerializerFactory)defaultTM.getSerializer(type);
+ }
+ if (factory == null) {
+ // If no factory is found, try the BeanSerializerFactory if
+ // the type is not Throwable. (There is no mapping for
+ // java types that extend Throwable.)
+ factory = new BeanSerializerFactory(type, getTypeQName(type));
+ }
+ if (factory != null) {
+ ser = (Serializer)factory.getSerializerAs(Constants.AXIS_SAX);
+ }
+
+ // if we can't get a serializer, that is bad.
+ if (ser == null) {
+ throw new AxisFault(
+ JavaUtils.getMessage("NoSerializer00", type.getName()));
+ }
+
+ // Write the namespace
+ QName qName = writeTypeNamespace(type);
+
+ // If an array the component type should be processed first
+ String componentTypeName = null;
+ Class componentType = null;
+ if (type.isArray()) {
+ String dimString = "[]";
+ componentType = type.getComponentType();
+ if (componentType.isArray()) {
+ while (componentType.isArray()) {
+ dimString += "[]";
+ componentType = componentType.getComponentType();
+ }
+ }
+ componentTypeName = writeType(componentType) + dimString;
+ }
+
+ String soapTypeName = qName.getLocalPart();
+ String prefix = namespaces.getCreatePrefix(qName.getNamespaceURI());
+ String prefixedName = prefix+":"+soapTypeName;
+
+ // If processed before, or this is a known namespace, return
+ if (!addToTypesList(qName, soapTypeName))
+ return prefixedName;
+
+ if (type.isArray()) {
+ // ComplexType representation of array
+ Element complexType = docHolder.createElement("complexType");
+ writeSchemaElement(qName, complexType);
+ complexType.setAttribute("name", soapTypeName);
+
+ Element complexContent = docHolder.createElement("complexContent");
+ complexType.appendChild(complexContent);
+
+ Element restriction = docHolder.createElement("restriction");
+ complexContent.appendChild(restriction);
+ restriction.setAttribute("base",
+ Constants.NS_PREFIX_SOAP_ENC + ":Array");
+
+ Element attribute = docHolder.createElement("attribute");
+ restriction.appendChild(attribute);
+ attribute.setAttribute("ref",
+ Constants.NS_PREFIX_SOAP_ENC +":arrayType");
+ attribute.setAttribute(Constants.NS_PREFIX_WSDL +":arrayType",
+ componentTypeName );
+ } else {
+ if (isEnumClass(type)) {
+ writeEnumType(qName, type);
+ } else {
+ ser.writeSchema(this);
+ }
+ }
+ return prefixedName;
+ }
+
+ /**
+ * Returns true if indicated type matches the JAX-RPC enumeration class.
+ * Note: supports JSR 101 version 0.6 Public Draft
+ */
+ public static boolean isEnumClass(Class cls) {
+ try {
+ java.lang.reflect.Method m = cls.getMethod("getValue", null);
+ java.lang.reflect.Method m2 = cls.getMethod("toString", null);
+ if (m != null && m2 != null) {
+ java.lang.reflect.Method m3 =
+ cls.getDeclaredMethod("fromString",
+ new Class[] {java.lang.String.class});
+ java.lang.reflect.Method m4 =
+ cls.getDeclaredMethod("fromValue",
+ new Class[] {m.getReturnType()});
+
+ if (m3 != null &&
+ Modifier.isStatic(m3.getModifiers()) &&
+ Modifier.isPublic(m3.getModifiers()) &&
+ m4 != null &&
+ Modifier.isStatic(m4.getModifiers()) &&
+ Modifier.isPublic(m4.getModifiers())) {
+ // Return false if there is a setValue member method
+ try {
+ if (cls.getMethod("setValue",
+ new Class[] {m.getReturnType()}) == null)
+ return true;
+ return false;
+ } catch (java.lang.NoSuchMethodException e) {
+ return true;
+ }
+ }
+ }
+ } catch (java.lang.NoSuchMethodException e) {}
+ return false;
+ }
+
+ /**
+ * Write Enumeration Complex Type
+ * (Only supports enumeration classes of string types)
+ * @param qName QName of type.
+ * @param cls class of type
+ */
+ private void writeEnumType(QName qName, Class cls) throws Exception {
+ if (!isEnumClass(cls))
+ return;
+ // Get the base type of the enum class
+ java.lang.reflect.Method m = cls.getMethod("getValue", null);
+ Class base = m.getReturnType();
+
+ // Create simpleType, restriction elements
+ Element simpleType = docHolder.createElement("simpleType");
+ writeSchemaElement(qName, simpleType);
+ simpleType.setAttribute("name", qName.getLocalPart());
+ Element restriction = docHolder.createElement("restriction");
+ simpleType.appendChild(restriction);
+ String baseType = writeType(base);
+ restriction.setAttribute("base", baseType);
+
+ // Create an enumeration using the field values
+ Field[] fields= cls.getDeclaredFields();
+ for (int i=0; i < fields.length; i++) {
+ Field field = fields[i];
+ int mod = field.getModifiers();
+
+ // Inspect each public static final field of the same type
+ // as the base
+ if (Modifier.isPublic(mod) &&
+ Modifier.isStatic(mod) &&
+ Modifier.isFinal(mod) &&
+ field.getType() == base) {
+ // Create an enumeration using the value specified
+ Element enumeration = docHolder.createElement("enumeration");
+ enumeration.setAttribute("value", field.get(null).toString());
+ restriction.appendChild(enumeration);
+
+ }
+ }
+
+ }
+
+ /**
+ * Create Element
+ * @param qName the namespace of the created element
+ * @param elementType schema type representation of the element
+ * @param nullable nillable attribute of the element
+ * @return the created Element
+ */
+ private Element createRootElement(QName qName,
+ String elementType,
+ boolean nullable) {
+ if (!addToElementsList(qName))
+ return null;
+
+ Element element = docHolder.createElement("element");
+
+ //Generate an element name that matches the type.
+ // Previously a unique element name was generated.
+ //String name = generateUniqueElementName(qName);
+ String name = elementType.substring(elementType.lastIndexOf(":")+1);
+
+ element.setAttribute("name", name);
+ if (nullable)
+ element.setAttribute("nillable", "true");
+ element.setAttribute("type", elementType);
+ return element;
+ }
+
+ /**
+ * Create Element with a given name and type
+ * @param elementName the name of the created element
+ * @param elementType schema type representation of the element
+ * @param nullable nullable attribute of the element
+ * @return the created Element
+ */
+ public Element createElement(String elementName,
+ String elementType,
+ boolean nullable,
+ boolean omittable,
+ Document docHolder) {
+ Element element = docHolder.createElement("element");
+ element.setAttribute("name", elementName);
+ if (nullable)
+ element.setAttribute("nillable", "true");
+ if (omittable) {
+ element.setAttribute("minOccurs", "0");
+ element.setAttribute("maxOccurs", "1");
+ }
+ element.setAttribute("type", elementType);
+ return element;
+ }
+
+
+ /**
+ * Create Attribute Element with a given name and type
+ * @param elementName the name of the created element
+ * @param elementType schema type representation of the element
+ * @param nullable nullable attribute of the element
+ * @return the created Element
+ */
+ public Element createAttributeElement(String elementName,
+ String elementType,
+ boolean nullable,
+ Document docHolder) {
+ Element element = docHolder.createElement("attribute");
+ element.setAttribute("name", elementName);
+ if (nullable)
+ element.setAttribute("nillable", "true");
+ element.setAttribute("type", elementType);
+ return element;
+ }
+
+ /**
+ * convert from JAX-RPC QName to WSDL QName
+ * @param qName JAX-RPC QName
+ * @return WSDL QName
+ */
+ public QName getWsdlQName (javax.xml.rpc.namespace.QName qName) {
+ return new QName(qName.getNamespaceURI(), qName.getLocalPart());
+ }
+
+ /**
+ * Is the given class one of the simple types defined by Schema
+ * (per JSR 101 v.0.6)
+ * @param type input Class
+ * @return true if the type is a simple schema type
+ */
+ public boolean isSimpleSchemaType(Class type) {
+ return (type == java.lang.String.class ||
+ type == java.lang.Boolean.TYPE ||
+ type == java.lang.Byte.TYPE ||
+ type == java.lang.Double.TYPE ||
+ type == java.lang.Float.TYPE ||
+ type == java.lang.Integer.TYPE ||
+ type == java.lang.Long.TYPE ||
+ type == java.lang.Short.TYPE ||
+ type == java.math.BigInteger.class ||
+ type == java.math.BigDecimal.class ||
+ type == javax.xml.rpc.namespace.QName.class ||
+ type == java.util.Calendar.class ||
+ type == byte[].class);
+ }
+
+ /**
+ * Is the given class one of the simple types defined by SoapEncoding.
+ * (per JSR 101 v.0.6)
+ * @param type input Class
+ * @return true if the type is a simple soap encoding type
+ */
+ boolean isSimpleSoapEncodingType(Class type) {
+ return (type == java.lang.String.class ||
+ type == java.lang.Boolean.class ||
+ type == java.lang.Byte.class ||
+ type == java.lang.Double.class ||
+ type == java.lang.Float.class ||
+ type == java.lang.Integer.class ||
+ type == java.lang.Long.class ||
+ type == java.lang.Short.class ||
+ type == java.math.BigDecimal.class ||
+ type == byte[].class);
+ }
+
+ /**
+ * Is the given class one of the simple types
+ * @param type input Class
+ * @return true if the type is a simple type
+ */
+ boolean isSimpleType(Class type) {
+ return (isSimpleSchemaType(type) ||
+ isSimpleSoapEncodingType(type));
+ }
+
+ /**
+ * Is the given class acceptable as an attribute
+ * @param type input Class
+ * @return true if the type is a simple, enum type or extends SimpleType
+ */
+ public boolean isAcceptableAsAttribute(Class type) {
+ return isSimpleType(type) ||
+ isEnumClass(type) ||
+ implementsSimpleType(type);
+ }
+
+ /**
+ * Does the class implement SimpleType
+ * @param type input Class
+ * @return true if the type implements SimpleType
+ */
+ boolean implementsSimpleType(Class type) {
+ Class[] impls = type.getInterfaces();
+ for(int i=0; i<impls.length; i++) {
+ if (impls[i] == SimpleType.class) {
+ return true;
+ }
+ }
+ return false;
+ }
+ /**
+ * Generates a unique element name for a given namespace of the form
+ * el0, el1 ....
+ *
+ * @param qName the namespace for the generated element
+ * @return elementname
+ */
+// *** NOT USED? ***
+//
+// private String generateUniqueElementName(QName qName) {
+// Integer count = (Integer)schemaUniqueElementNames.get(qName.getNamespaceURI());
+// if (count == null)
+// count = new Integer(0);
+// else
+// count = new Integer(count.intValue() + 1);
+// schemaUniqueElementNames.put(qName.getNamespaceURI(), count);
+// return "el" + count.intValue();
+// }
+
+ /**
+ * Add the type to an ArrayList and return true if the Schema node
+ * needs to be generated
+ * If the type already exists, just return false to indicate that the type is already
+ * generated in a previous iteration
+ *
+ * @param qName the name space of the type
+ * @param typeName the name of the type
+ * @return if the type is added returns true, else if the type is already present returns false
+ */
+ private boolean addToTypesList (QName qName, String typeName) {
+ boolean added = false;
+ ArrayList types = (ArrayList)schemaTypes.get(qName.getNamespaceURI());
+ if (types == null) {
+ types = new ArrayList();
+ types.add(typeName);
+ schemaTypes.put(qName.getNamespaceURI(), types);
+ added = true;
+ }
+ else {
+ if (!types.contains(typeName)) {
+ types.add(typeName);
+ added = true;
+ }
+ }
+
+ // If addded, look at the namespace uri to see if the schema element should be
+ // generated.
+ if (added) {
+ String prefix = namespaces.getCreatePrefix(qName.getNamespaceURI());
+ if (prefix.equals(Constants.NS_PREFIX_SOAP_ENV) ||
+ prefix.equals(Constants.NS_PREFIX_SOAP_ENC) ||
+ prefix.equals(Constants.NS_PREFIX_SCHEMA_XSD) ||
+ prefix.equals(Constants.NS_PREFIX_WSDL) ||
+ prefix.equals(Constants.NS_PREFIX_WSDL_SOAP))
+ return false;
+ else
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Add the element to an ArrayList and return true if the Schema element
+ * needs to be generated
+ * If the element already exists, just return false to indicate that the type is already
+ * generated in a previous iteration
+ *
+ * @param qName the name space of the element
+ * @return if the type is added returns true, else if the type is already present returns false
+ */
+ private boolean addToElementsList (QName qName) {
+ boolean added = false;
+ ArrayList elements = (ArrayList)schemaElementNames.get(qName.getNamespaceURI());
+ if (elements == null) {
+ elements = new ArrayList();
+ elements.add(qName.getLocalPart());
+ schemaElementNames.put(qName.getNamespaceURI(), elements);
+ added = true;
+ }
+ else {
+ if (!elements.contains(qName.getLocalPart())) {
+ elements.add(qName.getLocalPart());
+ added = true;
+ }
+ }
+ return added;
+ }
+
+
+ /**
+ * Determines if the field is nullable. All non-primitives except
+ * for byte[] are nillable.
+ *
+ * @param type input Class
+ * @return true if nullable
+ */
+ public boolean isNullable(Class type) {
+ if (type.isPrimitive() ||
+ (type.isArray() && type.getComponentType() == byte.class))
+ return false;
+ else
+ return true;
+ }
+
+
+ /** @todo ravi: Get rid of Doccument fragment and import node stuuf,
+ * once I have a handle on the wsdl4j mechanism to get at types.
+ *
+ * Switch over notes: remove docHolder, docFragment in favor of wsdl4j Types
+ */
+ //DocumentFragment docFragment;
+ Document docHolder;
+
+ private void createDocumentFragment () {
+ this.docHolder = XMLUtils.newDocument();
+ }
+
+ /**
+ * Inserts the type fragment into the given wsdl document
+ * @param doc
+ */
+ public void insertTypesFragment(Document doc) {
+
+ if (wsdlTypesElem != null) {
+ // Import the wsdlTypesElement into the doc.
+ org.w3c.dom.Node node = doc.importNode(wsdlTypesElem, true);
+ // Insert the imported element at the beginning of the document
+ doc.getDocumentElement().
+ insertBefore(node,
+ doc.getDocumentElement().getFirstChild());
+ }
+ }
+
+ /**
+ * Return the list of classes that we should not emit WSDL for.
+ */
+ public List getStopClasses() {
+ return stopClasses;
+ }
+
+ /**
+ * Create a DOM Element in this context
+ */
+ public Element createElement(String elementName)
+ {
+ return docHolder.createElement(elementName);
+ }
+}
1.59 +1 -1 xml-axis/java/src/org/apache/axis/message/RPCElement.java
Index: RPCElement.java
===================================================================
RCS file: /home/cvs/xml-axis/java/src/org/apache/axis/message/RPCElement.java,v
retrieving revision 1.58
retrieving revision 1.59
diff -u -r1.58 -r1.59
--- RPCElement.java 30 May 2002 17:50:08 -0000 1.58
+++ RPCElement.java 30 May 2002 18:55:21 -0000 1.59
@@ -178,7 +178,7 @@
for (int i = 0; i < operations.length; i++) {
OperationDesc operation = operations[i];
- if (operation.getNumInParams() >= numParams) {
+ if (operation.getNumInParams() >= numParams || elementIsFirstParam ) {
// Set the operation so the RPCHandler can get at it
rpcHandler.setOperation(operation);
try {
1.1 xml-axis/java/test/wsdl/omit/OmitTestCase.java
Index: OmitTestCase.java
===================================================================
/*
* The Apache Software License, Version 1.1
*
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution,
* if any, must include the following acknowledgment:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowledgment may appear in the software itself,
* if and wherever such third-party acknowledgments normally appear.
*
* 4. The names "Axis" and "Apache Software Foundation" must
* not be used to endorse or promote products derived from this
* software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache",
* nor may "Apache" appear in their name, without prior written
* permission of the Apache Software Foundation.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
/**
* OmitTestCase.java
*
* This tests the omitting of elements when minOccurs=0 and the value
* of the element is Null.
*
* For instance:
* <Phone>
* <prefix>555</prefix>
* <number>1212</number>
* </Phone>
*
* This would normally have the additional areaCode element:
* <areaCode xsi:nil=true/>
*
*/
package test.wsdl.omit;
public class OmitTestCase extends junit.framework.TestCase {
public OmitTestCase(String name) {
super(name);
}
public void test1OmitEchoPhone() {
test.wsdl.omit.Omit binding;
try {
binding = new test.wsdl.omit.OmitTestLocator().getOmit();
}
catch (javax.xml.rpc.ServiceException jre) {
throw new junit.framework.AssertionFailedError("JAX-RPC ServiceException caught: " + jre);
}
assertTrue("binding is null", binding != null);
try {
test.wsdl.omit.Phone input = new test.wsdl.omit.Phone();
input.setPrefix("555");
input.setNumber("1212");
test.wsdl.omit.Phone out = binding.echoPhone(input);
// TODO: Verify the XML omitted the element
assertNotNull("The return value from the operation was null", out);
assertNull("areacode is not null", out.getAreaCode());
assertEquals("prefix is incorrect", "555", out.getPrefix());
assertEquals("number is incorrect", "1212", out.getNumber());
}
catch (java.rmi.RemoteException re) {
throw new junit.framework.AssertionFailedError("Remote Exception caught: " + re);
}
}
public static void main(String[] args) {
OmitTestCase tester = new OmitTestCase("tester");
tester.test1OmitEchoPhone();
}
}
1.1 xml-axis/java/test/wsdl/omit/OmitImpl.java
Index: OmitImpl.java
===================================================================
/*
* The Apache Software License, Version 1.1
*
*
* Copyright (c) 2001 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in
* the documentation and/or other materials provided with the
* distribution.
*
* 3. The end-user documentation included with the redistribution,
* if any, must include the following acknowledgment:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
* Alternately, this acknowledgment may appear in the software itself,
* if and wherever such third-party acknowledgments normally appear.
*
* 4. The names "Axis" and "Apache Software Foundation" must
* not be used to endorse or promote products derived from this
* software without prior written permission. For written
* permission, please contact apache@apache.org.
*
* 5. Products derived from this software may not be called "Apache",
* nor may "Apache" appear in their name, without prior written
* permission of the Apache Software Foundation.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
* DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
* ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
* USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
* OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
* ====================================================================
*
* This software consists of voluntary contributions made by many
* individuals on behalf of the Apache Software Foundation. For more
* information on the Apache Software Foundation, please see
* <http://www.apache.org/>.
*/
/**
* OmitImpl.java
*
*/
package test.wsdl.omit;
public class OmitImpl implements test.wsdl.omit.Omit {
public test.wsdl.omit.Phone echoPhone(test.wsdl.omit.Phone in) throws java.rmi.RemoteException {
return in;
}
}
1.1 xml-axis/java/test/wsdl/omit/omit.wsdl
Index: omit.wsdl
===================================================================
<?xml version="1.0" encoding="utf-8"?>
<!--
This tests the omission of an element which has minOccurs=0
-->
<definitions name="OmitTest" xmlns="http://schemas.xmlsoap.org/wsdl/" xmlns:s="http://www.w3.org/2001/XMLSchema" xmlns:s0="http://omit.wsdl.test/" xmlns:http="http://schemas.xmlsoap.org/wsdl/http/" xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/" targetNamespace="http://omit.wsdl.test/">
<types>
<s:schema targetNamespace="http://omit.wsdl.test/" elementFormDefault="qualified">
<s:element name="Phone">
<s:complexType>
<s:sequence>
<s:element name="areaCode" type="s:string" maxOccurs="1" minOccurs="0"/>
<s:element name="prefix" type="s:string" maxOccurs="1" minOccurs="0"/>
<s:element name="number" type="s:string" maxOccurs="1" minOccurs="0"/>
</s:sequence>
</s:complexType>
</s:element>
</s:schema>
</types>
<message name="echoPhoneIn">
<part name="in" element="s0:Phone"/>
</message>
<message name="echoPhoneOut">
<part name="out" element="s0:Phone"/>
</message>
<portType name="omit">
<operation name="echoPhone">
<input message="s0:echoPhoneIn"/>
<output message="s0:echoPhoneOut"/>
</operation>
</portType>
<binding name="omit" type="s0:omit">
<soap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http"/>
<operation name="echoPhone">
<soap:operation style="document" soapAction="http://tempuri.org/echoPhone"/>
<input>
<soap:body use="literal"/>
</input>
<output>
<soap:body use="literal"/>
</output>
</operation>
</binding>
<service name="omitTest">
<port name="omit" binding="s0:omit">
<soap:address location="http://localhost:8080/axis/services/omit"/>
</port>
</service>
</definitions>
1.63 +5 -5 xml-axis/java/src/org/apache/axis/wsdl/toJava/JavaStubWriter.java
Index: JavaStubWriter.java
===================================================================
RCS file: /home/cvs/xml-axis/java/src/org/apache/axis/wsdl/toJava/JavaStubWriter.java,v
retrieving revision 1.62
retrieving revision 1.63
diff -u -r1.62 -r1.63
--- JavaStubWriter.java 30 May 2002 03:06:13 -0000 1.62
+++ JavaStubWriter.java 30 May 2002 18:55:21 -0000 1.63
@@ -498,7 +498,8 @@
// We need to use the Qname of the actual type, not the QName of the element
TypeEntry type = p.getType();
if (type instanceof DefinedElement) {
- type = type.getRefType();
+ if (type.getRefType() != null)
+ type = type.getRefType();
}
QName qn = type.getQName();
String javaType = type.getName();
@@ -538,10 +539,9 @@
// We need to use the Qname of the actual type, not the QName of the element
QName qn = parms.returnType.getQName();
if (parms.returnType instanceof DefinedElement) {
- Node node = symbolTable.getTypeEntry(parms.returnType.getQName(), true).getNode();
- QName qn2 = Utils.getNodeTypeRefQName(node, "type");
- if (qn2 != null) {
- qn = qn2;
+ TypeEntry type = ((DefinedElement)parms.returnType).getRefType();
+ if (type != null && type.getQName() != null) {
+ qn = type.getQName();
}
}
1.43 +2 -1 xml-axis/java/src/org/apache/axis/wsdl/toJava/JavaDeployWriter.java
Index: JavaDeployWriter.java
===================================================================
RCS file: /home/cvs/xml-axis/java/src/org/apache/axis/wsdl/toJava/JavaDeployWriter.java,v
retrieving revision 1.42
retrieving revision 1.43
diff -u -r1.42 -r1.43
--- JavaDeployWriter.java 30 May 2002 03:06:13 -0000 1.42
+++ JavaDeployWriter.java 30 May 2002 18:55:21 -0000 1.43
@@ -391,7 +391,8 @@
QName paramType = null;
// Get the parameter type QName
- if (typeEntry instanceof DefinedElement) {
+ if (typeEntry instanceof DefinedElement &&
+ typeEntry.getRefType() != null) {
paramType = typeEntry.getRefType().getQName();
} else {
paramType = typeEntry.getQName();
1.11 +287 -281 xml-axis/java/src/org/apache/axis/wsdl/toJava/JavaBeanHelperWriter.java
Index: JavaBeanHelperWriter.java
===================================================================
RCS file: /home/cvs/xml-axis/java/src/org/apache/axis/wsdl/toJava/JavaBeanHelperWriter.java,v
retrieving revision 1.10
retrieving revision 1.11
diff -u -r1.10 -r1.11
--- JavaBeanHelperWriter.java 30 May 2002 03:06:13 -0000 1.10
+++ JavaBeanHelperWriter.java 30 May 2002 18:55:21 -0000 1.11
@@ -1,281 +1,287 @@
-/*
- * The Apache Software License, Version 1.1
- *
- *
- * Copyright (c) 2001 The Apache Software Foundation. All rights
- * reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in
- * the documentation and/or other materials provided with the
- * distribution.
- *
- * 3. The end-user documentation included with the redistribution,
- * if any, must include the following acknowledgment:
- * "This product includes software developed by the
- * Apache Software Foundation (http://www.apache.org/)."
- * Alternately, this acknowledgment may appear in the software itself,
- * if and wherever such third-party acknowledgments normally appear.
- *
- * 4. The names "Axis" and "Apache Software Foundation" must
- * not be used to endorse or promote products derived from this
- * software without prior written permission. For written
- * permission, please contact apache@apache.org.
- *
- * 5. Products derived from this software may not be called "Apache",
- * nor may "Apache" appear in their name, without prior written
- * permission of the Apache Software Foundation.
- *
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
- * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
- * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
- * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
- * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
- * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
- * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
- * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- * ====================================================================
- *
- * This software consists of voluntary contributions made by many
- * individuals on behalf of the Apache Software Foundation. For more
- * information on the Apache Software Foundation, please see
- * <http://www.apache.org/>.
- */
-package org.apache.axis.wsdl.toJava;
-
-import java.io.IOException;
-
-import java.util.Vector;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map;
-
-import javax.xml.rpc.namespace.QName;
-
-import org.apache.axis.utils.JavaUtils;
-
-import org.apache.axis.wsdl.symbolTable.ElementDecl;
-import org.apache.axis.wsdl.symbolTable.TypeEntry;
-
-import org.w3c.dom.Node;
-
-/**
- * This is Wsdl2java's Helper Type Writer. It writes the <typeName>.java file.
- */
-public class JavaBeanHelperWriter extends JavaWriter {
- protected TypeEntry type;
- protected Vector elements;
- protected Vector attributes;
- protected TypeEntry extendType;
- protected Vector elementMetaData = null;
-
- /**
- * Constructor.
- * @param emitter
- * @param type The type representing this class
- * @param elements Vector containing the Type and name of each property
- * @param extendType The type representing the extended class (or null)
- * @param attributes Vector containing the attribute types and names
- */
- protected JavaBeanHelperWriter(
- Emitter emitter,
- TypeEntry type,
- Vector elements,
- TypeEntry extendType,
- Vector attributes) {
- super(emitter, type, "_Helper", "java",
- JavaUtils.getMessage("genType00"), "helper");
- this.type = type;
- this.elements = elements;
- this.attributes = attributes;
- this.extendType = extendType;
- } // ctor
-
- /**
- * Generate the binding for the given complex type.
- * The elements vector contains the Types (even indices) and
- * element names (odd indices) of the contained elements
- */
- protected void writeFileBody() throws IOException {
-
- if (!embeddedCode) {
- pw.println("public class " + className + " {");
- }
-
- writeMetaData();
- writeSerializer();
- writeDeserializer();
-
- if (!embeddedCode) {
- pw.println("}");
- pw.close();
- }
-
- } // writeFileBody
-
- /**
- * write MetaData code
- */
- protected void writeMetaData() throws IOException {
- // Collect elementMetaData
- if (elements != null) {
- for (int i = 0; i < elements.size(); i++) {
- ElementDecl elem = (ElementDecl)elements.get(i);
- String elemName = elem.getName().getLocalPart();
- String javaName = Utils.xmlNameToJava(elemName);
-
- // Changed the code to write meta data
- // for all of the elements in order to
- // support sequences. Defect 9060
-
-
- // Meta data is needed if the default serializer
- // action cannot map the javaName back to the
- // element's qname. This occurs if:
- // - the javaName and element name local part are different.
- // - the javaName starts with uppercase char (this is a wierd
- // case and we have several problems with the mapping rules.
- // Seems best to gen meta data in this case.)
- // - the element name is qualified (has a namespace uri)
- //if (!javaName.equals(elemName) ||
- // Character.isUpperCase(javaName.charAt(0)) ||
- // !elem.getName().getNamespaceURI().equals("")) {
- // If we did some mangling, make sure we'll write out the XML
- // the correct way.
- if (elementMetaData == null)
- elementMetaData = new Vector();
-
- elementMetaData.add(elem);
- //}
- }
- }
- // if we have attributes, create metadata function which returns the
- // list of properties that are attributes instead of elements
-
- if (attributes != null || elementMetaData != null) {
- boolean wroteFieldType = false;
- pw.println(" // " + JavaUtils.getMessage("typeMeta"));
- pw.println(" private static org.apache.axis.description.TypeDesc typeDesc =");
- pw.println(" new org.apache.axis.description.TypeDesc(" +
- rootName + ".class);");
- pw.println();
- pw.println(" static {");
-
- if (attributes != null) {
- for (int i = 0; i < attributes.size(); i += 2) {
- String attrName = (String) attributes.get(i + 1);
- String fieldName = Utils.xmlNameToJava(attrName);
- pw.print(" ");
- if (!wroteFieldType) {
- pw.print("org.apache.axis.description.FieldDesc ");
- wroteFieldType = true;
- }
- pw.println("field = new org.apache.axis.description.AttributeDesc();");
- pw.println(" field.setFieldName(\"" + fieldName + "\");");
- if (!fieldName.equals(attrName)) {
- pw.print(" field.setXmlName(");
- pw.print("new javax.xml.rpc.namespace.QName(null, \"");
- pw.println(attrName + "\"));");
- }
- pw.println(" typeDesc.addFieldDesc(field);");
- }
- }
-
- if (elementMetaData != null) {
- for (int i=0; i<elementMetaData.size(); i++) {
- ElementDecl elem = (ElementDecl) elementMetaData.elementAt(i);
- String elemLocalName = elem.getName().getLocalPart();
- String fieldName = Utils.xmlNameToJava(elemLocalName);
- QName xmlName = elem.getName();
- pw.print(" ");
- if (!wroteFieldType) {
- pw.print("org.apache.axis.description.FieldDesc ");
- wroteFieldType = true;
- }
- pw.println("field = new org.apache.axis.description.ElementDesc();");
- pw.println(" field.setFieldName(\"" + fieldName + "\");");
- pw.print( " field.setXmlName(new javax.xml.rpc.namespace.QName(\"");
- pw.println(xmlName.getNamespaceURI() + "\", \"" +
- xmlName.getLocalPart() + "\"));");
- pw.println(" typeDesc.addFieldDesc(field);");
- }
- }
-
- pw.println(" };");
- pw.println();
-
- pw.println(" /**");
- pw.println(" * " + JavaUtils.getMessage("returnTypeMeta"));
- pw.println(" */");
- pw.println(" public static org.apache.axis.description.TypeDesc getTypeDesc() {");
- pw.println(" return typeDesc;");
- pw.println(" }");
- pw.println();
- }
- }
-
- /**
- * write Serializer getter code and pass in meta data to avoid
- * undo introspection.
- */
- protected void writeSerializer() throws IOException {
- String typeDesc = null;
- if (attributes != null || elementMetaData != null) {
- typeDesc = "typeDesc";
- }
- String ser = " org.apache.axis.encoding.ser.BeanSerializer";
- if (type.isSimpleType()) {
- ser = " org.apache.axis.encoding.ser.SimpleSerializer";
- }
- pw.println(" /**");
- pw.println(" * Get Custom Serializer");
- pw.println(" */");
- pw.println(" public static org.apache.axis.encoding.Serializer getSerializer(");
- pw.println(" String mechType, ");
- pw.println(" Class _javaType, ");
- pw.println(" javax.xml.rpc.namespace.QName _xmlType) {");
- pw.println(" return ");
- pw.println(" new " + ser +"(");
- pw.println(" _javaType, _xmlType," + typeDesc + ");");
- pw.println(" };");
- pw.println();
- }
-
- /**
- * write Deserializer getter code and pass in meta data to avoid
- * undo introspection.
- */
- protected void writeDeserializer() throws IOException {
- String typeDesc = null;
- if (attributes != null || elementMetaData != null) {
- typeDesc = "typeDesc";
- }
- String dser = " org.apache.axis.encoding.ser.BeanDeserializer";
- if (type.isSimpleType()) {
- dser = " org.apache.axis.encoding.ser.SimpleDeserializer";
- }
- pw.println(" /**");
- pw.println(" * Get Custom Deserializer");
- pw.println(" */");
- pw.println(" public static org.apache.axis.encoding.Deserializer getDeserializer(");
- pw.println(" String mechType, ");
- pw.println(" Class _javaType, ");
- pw.println(" javax.xml.rpc.namespace.QName _xmlType) {");
- pw.println(" return ");
- pw.println(" new " + dser + "(");
- pw.println(" _javaType, _xmlType," + typeDesc + ");");
- pw.println(" };");
- pw.println();
- }
-} // class JavaBeanHelperWriter
+/*
+ * The Apache Software License, Version 1.1
+ *
+ *
+ * Copyright (c) 2001 The Apache Software Foundation. All rights
+ * reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in
+ * the documentation and/or other materials provided with the
+ * distribution.
+ *
+ * 3. The end-user documentation included with the redistribution,
+ * if any, must include the following acknowledgment:
+ * "This product includes software developed by the
+ * Apache Software Foundation (http://www.apache.org/)."
+ * Alternately, this acknowledgment may appear in the software itself,
+ * if and wherever such third-party acknowledgments normally appear.
+ *
+ * 4. The names "Axis" and "Apache Software Foundation" must
+ * not be used to endorse or promote products derived from this
+ * software without prior written permission. For written
+ * permission, please contact apache@apache.org.
+ *
+ * 5. Products derived from this software may not be called "Apache",
+ * nor may "Apache" appear in their name, without prior written
+ * permission of the Apache Software Foundation.
+ *
+ * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
+ * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
+ * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
+ * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ * ====================================================================
+ *
+ * This software consists of voluntary contributions made by many
+ * individuals on behalf of the Apache Software Foundation. For more
+ * information on the Apache Software Foundation, please see
+ * <http://www.apache.org/>.
+ */
+package org.apache.axis.wsdl.toJava;
+
+import java.io.IOException;
+
+import java.util.Vector;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+
+import javax.xml.rpc.namespace.QName;
+
+import org.apache.axis.utils.JavaUtils;
+
+import org.apache.axis.wsdl.symbolTable.ElementDecl;
+import org.apache.axis.wsdl.symbolTable.TypeEntry;
+
+import org.w3c.dom.Node;
+
+/**
+ * This is Wsdl2java's Helper Type Writer. It writes the <typeName>.java file.
+ */
+public class JavaBeanHelperWriter extends JavaWriter {
+ protected TypeEntry type;
+ protected Vector elements;
+ protected Vector attributes;
+ protected TypeEntry extendType;
+ protected Vector elementMetaData = null;
+
+ /**
+ * Constructor.
+ * @param emitter
+ * @param type The type representing this class
+ * @param elements Vector containing the Type and name of each property
+ * @param extendType The type representing the extended class (or null)
+ * @param attributes Vector containing the attribute types and names
+ */
+ protected JavaBeanHelperWriter(
+ Emitter emitter,
+ TypeEntry type,
+ Vector elements,
+ TypeEntry extendType,
+ Vector attributes) {
+ super(emitter, type, "_Helper", "java",
+ JavaUtils.getMessage("genType00"), "helper");
+ this.type = type;
+ this.elements = elements;
+ this.attributes = attributes;
+ this.extendType = extendType;
+ } // ctor
+
+ /**
+ * Generate the binding for the given complex type.
+ * The elements vector contains the Types (even indices) and
+ * element names (odd indices) of the contained elements
+ */
+ protected void writeFileBody() throws IOException {
+
+ if (!embeddedCode) {
+ pw.println("public class " + className + " {");
+ }
+
+ writeMetaData();
+ writeSerializer();
+ writeDeserializer();
+
+ if (!embeddedCode) {
+ pw.println("}");
+ pw.close();
+ }
+
+ } // writeFileBody
+
+ /**
+ * write MetaData code
+ */
+ protected void writeMetaData() throws IOException {
+ // Collect elementMetaData
+ if (elements != null) {
+ for (int i = 0; i < elements.size(); i++) {
+ ElementDecl elem = (ElementDecl)elements.get(i);
+ String elemName = elem.getName().getLocalPart();
+ String javaName = Utils.xmlNameToJava(elemName);
+
+ // Changed the code to write meta data
+ // for all of the elements in order to
+ // support sequences. Defect 9060
+
+
+ // Meta data is needed if the default serializer
+ // action cannot map the javaName back to the
+ // element's qname. This occurs if:
+ // - the javaName and element name local part are different.
+ // - the javaName starts with uppercase char (this is a wierd
+ // case and we have several problems with the mapping rules.
+ // Seems best to gen meta data in this case.)
+ // - the element name is qualified (has a namespace uri)
+ // its also needed if:
+ // - the element has the minoccurs flag set
+ //if (!javaName.equals(elemName) ||
+ // Character.isUpperCase(javaName.charAt(0)) ||
+ //!elem.getName().getNamespaceURI().equals("") ||
+ //elem.getMinOccursIs0()) {
+ // If we did some mangling, make sure we'll write out the XML
+ // the correct way.
+ if (elementMetaData == null)
+ elementMetaData = new Vector();
+
+ elementMetaData.add(elem);
+ //}
+ }
+ }
+ // if we have attributes, create metadata function which returns the
+ // list of properties that are attributes instead of elements
+
+ if (attributes != null || elementMetaData != null) {
+ boolean wroteFieldType = false;
+ pw.println(" // " + JavaUtils.getMessage("typeMeta"));
+ pw.println(" private static org.apache.axis.description.TypeDesc typeDesc =");
+ pw.println(" new org.apache.axis.description.TypeDesc(" +
+ rootName + ".class);");
+ pw.println();
+ pw.println(" static {");
+
+ if (attributes != null) {
+ for (int i = 0; i < attributes.size(); i += 2) {
+ String attrName = (String) attributes.get(i + 1);
+ String fieldName = Utils.xmlNameToJava(attrName);
+ pw.print(" ");
+ if (!wroteFieldType) {
+ pw.print("org.apache.axis.description.FieldDesc ");
+ wroteFieldType = true;
+ }
+ pw.println("field = new org.apache.axis.description.AttributeDesc();");
+ pw.println(" field.setFieldName(\"" + fieldName + "\");");
+ if (!fieldName.equals(attrName)) {
+ pw.print(" field.setXmlName(");
+ pw.print("new javax.xml.rpc.namespace.QName(null, \"");
+ pw.println(attrName + "\"));");
+ }
+ pw.println(" typeDesc.addFieldDesc(field);");
+ }
+ }
+
+ if (elementMetaData != null) {
+ for (int i=0; i<elementMetaData.size(); i++) {
+ ElementDecl elem = (ElementDecl) elementMetaData.elementAt(i);
+ String elemLocalName = elem.getName().getLocalPart();
+ String fieldName = Utils.xmlNameToJava(elemLocalName);
+ QName xmlName = elem.getName();
+ pw.print(" ");
+ if (!wroteFieldType) {
+ pw.print("org.apache.axis.description.FieldDesc ");
+ wroteFieldType = true;
+ }
+ pw.println("field = new org.apache.axis.description.ElementDesc();");
+ pw.println(" field.setFieldName(\"" + fieldName + "\");");
+ pw.print( " field.setXmlName(new javax.xml.rpc.namespace.QName(\"");
+ pw.println(xmlName.getNamespaceURI() + "\", \"" +
+ xmlName.getLocalPart() + "\"));");
+ if (elem.getMinOccursIs0()) {
+ pw.println(" field.setMinOccursIs0(true);");
+ }
+ pw.println(" typeDesc.addFieldDesc(field);");
+ }
+ }
+
+ pw.println(" };");
+ pw.println();
+
+ pw.println(" /**");
+ pw.println(" * " + JavaUtils.getMessage("returnTypeMeta"));
+ pw.println(" */");
+ pw.println(" public static org.apache.axis.description.TypeDesc getTypeDesc() {");
+ pw.println(" return typeDesc;");
+ pw.println(" }");
+ pw.println();
+ }
+ }
+
+ /**
+ * write Serializer getter code and pass in meta data to avoid
+ * undo introspection.
+ */
+ protected void writeSerializer() throws IOException {
+ String typeDesc = null;
+ if (attributes != null || elementMetaData != null) {
+ typeDesc = "typeDesc";
+ }
+ String ser = " org.apache.axis.encoding.ser.BeanSerializer";
+ if (type.isSimpleType()) {
+ ser = " org.apache.axis.encoding.ser.SimpleSerializer";
+ }
+ pw.println(" /**");
+ pw.println(" * Get Custom Serializer");
+ pw.println(" */");
+ pw.println(" public static org.apache.axis.encoding.Serializer getSerializer(");
+ pw.println(" String mechType, ");
+ pw.println(" Class _javaType, ");
+ pw.println(" javax.xml.rpc.namespace.QName _xmlType) {");
+ pw.println(" return ");
+ pw.println(" new " + ser +"(");
+ pw.println(" _javaType, _xmlType, " + typeDesc + ");");
+ pw.println(" };");
+ pw.println();
+ }
+
+ /**
+ * write Deserializer getter code and pass in meta data to avoid
+ * undo introspection.
+ */
+ protected void writeDeserializer() throws IOException {
+ String typeDesc = null;
+ if (attributes != null || elementMetaData != null) {
+ typeDesc = "typeDesc";
+ }
+ String dser = " org.apache.axis.encoding.ser.BeanDeserializer";
+ if (type.isSimpleType()) {
+ dser = " org.apache.axis.encoding.ser.SimpleDeserializer";
+ }
+ pw.println(" /**");
+ pw.println(" * Get Custom Deserializer");
+ pw.println(" */");
+ pw.println(" public static org.apache.axis.encoding.Deserializer getDeserializer(");
+ pw.println(" String mechType, ");
+ pw.println(" Class _javaType, ");
+ pw.println(" javax.xml.rpc.namespace.QName _xmlType) {");
+ pw.println(" return ");
+ pw.println(" new " + dser + "(");
+ pw.println(" _javaType, _xmlType, " + typeDesc + ");");
+ pw.println(" };");
+ pw.println();
+ }
+} // class JavaBeanHelperWriter
1.3 +14 -0 xml-axis/java/src/org/apache/axis/description/FieldDesc.java
Index: FieldDesc.java
===================================================================
RCS file: /home/cvs/xml-axis/java/src/org/apache/axis/description/FieldDesc.java,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -r1.2 -r1.3
--- FieldDesc.java 28 Apr 2002 18:10:56 -0000 1.2
+++ FieldDesc.java 30 May 2002 18:55:21 -0000 1.3
@@ -77,6 +77,9 @@
// Q : should this be a boolean, or just "instanceof ElementDesc", etc.
private boolean _isElement = true;
+ /** An indication that minoccurs is zero */
+ private boolean minOccursIs0 = false;
+
/**
* Can't construct the base class directly, must construct either an
* ElementDesc or an AttributeDesc.
@@ -133,5 +136,16 @@
public boolean isIndexed() {
return false;
+ }
+
+ /**
+ * Check if this field can be omitted.
+ */
+ public boolean isMinOccursIs0() {
+ return minOccursIs0;
+ }
+
+ public void setMinOccursIs0(boolean minOccursIs0) {
+ this.minOccursIs0 = minOccursIs0;
}
}
1.34 +24 -3 xml-axis/java/src/org/apache/axis/encoding/ser/BeanSerializer.java
Index: BeanSerializer.java
===================================================================
RCS file: /home/cvs/xml-axis/java/src/org/apache/axis/encoding/ser/BeanSerializer.java,v
retrieving revision 1.33
retrieving revision 1.34
diff -u -r1.33 -r1.34
--- BeanSerializer.java 25 May 2002 00:03:16 -0000 1.33
+++ BeanSerializer.java 30 May 2002 18:55:21 -0000 1.34
@@ -128,6 +128,9 @@
// attribute list
Attributes beanAttrs = getObjectAttributes(value, attributes, context);
+ // Get the encoding style
+ String encodingStyle = context.getMessageContext().getEncodingStyle();
+
// check whether we have and xsd:any namespace="##any" type
boolean suppressElement = !context.getMessageContext().isEncoded() &&
name.getNamespaceURI().equals("") &&
@@ -143,6 +146,7 @@
if (propName.equals("class"))
continue;
QName qname = null;
+ boolean isOmittable = false;
// If we have type metadata, check to see what we're doing
// with this field. If it's an attribute, skip it. If it's
@@ -156,6 +160,7 @@
continue;
qname = field.getXmlName();
+ isOmittable = field.isMinOccursIs0();
}
}
@@ -173,6 +178,14 @@
// Normal case: serialize the value
Object propValue =
propertyDescriptor[i].get(value);
+ // if meta data says minOccurs=0, then we can skip
+ // it if its value is null and we aren't doing SOAP
+ // encoding.
+ if (propValue == null &&
+ isOmittable &&
+ !Constants.isSOAP_ENC(encodingStyle))
+ continue;
+
javaType = (propValue == null ||
baseJavaType.isPrimitive())
? baseJavaType : propValue.getClass();
@@ -305,14 +318,21 @@
writeField(types,
propName,
propertyDescriptor[i].getType(),
- propertyDescriptor[i].isIndexed(), all);
+ propertyDescriptor[i].isIndexed(),
+ field.isMinOccursIs0(),
+ all);
}
+ } else {
+ writeField(types,
+ propName,
+ propertyDescriptor[i].getType(),
+ propertyDescriptor[i].isIndexed(), false, all);
}
} else {
writeField(types,
propName,
propertyDescriptor[i].getType(),
- propertyDescriptor[i].isIndexed(), all);
+ propertyDescriptor[i].isIndexed(), false, all);
}
}
@@ -332,11 +352,12 @@
protected void writeField(Types types, String fieldName,
Class fieldType,
boolean isUnbounded,
- Element where) throws Exception {
+ boolean isOmittable, Element where) throws Exception {
String elementType = types.writeType(fieldType);
Element elem = types.createElement(fieldName,
elementType,
types.isNullable(fieldType),
+ isOmittable,
where.getOwnerDocument());
if (isUnbounded) {
elem.setAttribute("maxOccurs", "unbounded");