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 gd...@apache.org on 2005/09/08 04:39:30 UTC
svn commit: r279491 [2/2] - in /webservices/axis2/trunk/java: ./
modules/databinding/ modules/databinding/src/ modules/databinding/src/org/
modules/databinding/src/org/apache/ modules/databinding/src/org/apache/axis2/
modules/databinding/src/org/apache...
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/metadata/TypeDesc.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/metadata/TypeDesc.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/metadata/TypeDesc.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/metadata/TypeDesc.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,109 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.databinding.metadata;
+
+import org.apache.axis2.util.MethodCache;
+
+import javax.xml.namespace.QName;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.HashMap;
+import java.util.Hashtable;
+import java.lang.reflect.Method;
+
+/**
+ * TypeDesc
+ */
+public class TypeDesc {
+ public static final Class [] noClasses = new Class [] {};
+ public static final Object[] noObjects = new Object[] {};
+
+ /** A map of class -> TypeDesc */
+ private static Map classMap = new Hashtable();
+
+ /**
+ * Static function for centralizing access to type metadata for a
+ * given class.
+ *
+ * This checks for a static getTypeDesc() method on the
+ * class or _Helper class.
+ * Eventually we may extend this to provide for external
+ * metadata config (via files sitting in the classpath, etc).
+ *
+ */
+ public static TypeDesc getTypeDescForClass(Class cls)
+ {
+ // First see if we have one explicitly registered
+ // or cached from previous lookup
+ TypeDesc result = (TypeDesc)classMap.get(cls);
+
+ if (result == null) {
+ try {
+ Method getTypeDesc =
+ MethodCache.getInstance().getMethod(cls,
+ "getTypeDesc",
+ noClasses);
+ if (getTypeDesc != null) {
+ result = (TypeDesc)getTypeDesc.invoke(null, noObjects);
+ if (result != null) {
+ classMap.put(cls, result);
+ }
+ }
+ } catch (Exception e) {
+ }
+ }
+
+ return result;
+ }
+
+ Map elements = new HashMap();
+ Map fieldsByName = new HashMap();
+ Map attrs = new HashMap();
+ Class javaClass;
+
+ public Iterator getAttributeDescs() {
+ return attrs.values().iterator();
+ }
+
+ public void addField(ElementDesc fieldDesc) {
+ elements.put(fieldDesc.getQName(), fieldDesc);
+ fieldsByName.put(fieldDesc.getFieldName(), fieldDesc);
+ }
+
+ public void addField(AttributeDesc fieldDesc) {
+ attrs.put(fieldDesc.getQName(), fieldDesc);
+ }
+
+ public ElementDesc getElementDesc(QName qname) {
+ return (ElementDesc)elements.get(qname);
+ }
+
+ public ElementDesc getElementDesc(String fieldName) {
+ return (ElementDesc)fieldsByName.get(fieldName);
+ }
+
+ public Iterator getElementDescs() {
+ return elements.values().iterator();
+ }
+
+ public Class getJavaClass() {
+ return javaClass;
+ }
+
+ public void setJavaClass(Class javaClass) {
+ this.javaClass = javaClass;
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/AbstractSerializer.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/AbstractSerializer.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/AbstractSerializer.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/AbstractSerializer.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,31 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.databinding.serializers;
+
+import org.apache.axis2.databinding.Serializer;
+import org.apache.axis2.databinding.SerializationContext;
+
+/**
+ * AbstractSerializer
+ */
+public abstract class AbstractSerializer implements Serializer {
+ public void serialize(Object object, SerializationContext context)
+ throws Exception {
+ if (!context.checkMultiref(object, this)) {
+ serializeData(object, context);
+ }
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/BeanSerializer.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/BeanSerializer.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/BeanSerializer.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/BeanSerializer.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,51 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.databinding.serializers;
+
+import org.apache.axis2.databinding.SerializationContext;
+import org.apache.axis2.databinding.Serializer;
+import org.apache.axis2.databinding.metadata.ElementDesc;
+import org.apache.axis2.databinding.metadata.TypeDesc;
+
+import javax.xml.namespace.QName;
+import java.util.Iterator;
+
+/**
+ * BeanSerializer
+ */
+public class BeanSerializer extends AbstractSerializer {
+ TypeDesc typeDesc;
+
+ public BeanSerializer(TypeDesc typeDesc) {
+ this.typeDesc = typeDesc;
+ }
+
+ public void serializeData(Object object, SerializationContext context)
+ throws Exception {
+ // Write any attributes that need writing here
+
+ Iterator elements = typeDesc.getElementDescs();
+ while (elements.hasNext()) {
+ ElementDesc desc = (ElementDesc) elements.next();
+ Object fieldValue = desc.getValue(object);
+ Serializer ser = desc.getSerializer();
+ QName qname = desc.getQName();
+ context.serializeElement(qname, fieldValue, ser);
+ }
+
+ context.getWriter().writeEndElement();
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/CollectionSerializer.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/CollectionSerializer.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/CollectionSerializer.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/CollectionSerializer.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,94 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.databinding.serializers;
+
+import org.apache.axis2.databinding.Serializer;
+import org.apache.axis2.databinding.SerializationContext;
+import org.apache.axis2.databinding.utils.Converter;
+
+import javax.xml.namespace.QName;
+import javax.xml.stream.XMLStreamWriter;
+import java.lang.reflect.Array;
+import java.util.Collection;
+
+/**
+ * CollectionSerializer
+ */
+public class CollectionSerializer extends AbstractSerializer {
+ public final QName DEFAULT_ITEM_QNAME = new QName("item");
+
+ boolean isWrapped;
+ QName itemQName;
+ Serializer serializer;
+
+ public CollectionSerializer(QName itemQName,
+ boolean isWrapped,
+ Serializer serializer) {
+ this.isWrapped = isWrapped;
+ this.itemQName = itemQName == null ? DEFAULT_ITEM_QNAME : itemQName;
+ this.serializer = serializer;
+ }
+
+ public void serialize(Object object, SerializationContext context) throws Exception {
+ if (isWrapped) {
+ // We have a wrapper element, so it's fine to do multiref checking
+ // on the actual collection object
+ super.serialize(object, context);
+ return;
+ }
+
+ // No wrapper, so need to do multiref checks on individual elements.
+ serializeData(object, context);
+ }
+
+ public void serializeData(Object object, SerializationContext context)
+ throws Exception {
+ if (object instanceof Collection) {
+ Converter.convert(object, Object[].class);
+ }
+ XMLStreamWriter writer = context.getWriter();
+ if (isWrapped) {
+ writer.writeStartElement(itemQName.getNamespaceURI(),
+ itemQName.getLocalPart());
+ }
+
+ int len = Array.getLength(object);
+ for (int i = 0; i < len; i++) {
+ Object item = Array.get(object, i);
+ if (i == 0) {
+ if (isWrapped) {
+ if (!context.checkMultiref(item, serializer)) {
+ serializer.serializeData(item, context);
+ }
+ } else {
+ serializer.serializeData(item, context);
+ }
+ } else {
+ context.serializeElement(itemQName, item, serializer);
+ }
+ }
+
+// Collection coll = (Collection)object;
+// for (Iterator i = coll.iterator(); i.hasNext();) {
+// Object item = i.next();
+// context.serializeElement(itemQName, item, serializer);
+// }
+
+ if (isWrapped) {
+ writer.writeEndElement();
+ }
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/SimpleSerializer.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/SimpleSerializer.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/SimpleSerializer.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/serializers/SimpleSerializer.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,73 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.databinding.serializers;
+
+import org.apache.axis2.databinding.SerializationContext;
+
+import javax.xml.namespace.QName;
+import java.text.SimpleDateFormat;
+import java.util.TimeZone;
+
+/**
+ * SimpleSerializer
+ */
+public class SimpleSerializer extends AbstractSerializer {
+ private static SimpleDateFormat zulu =
+ new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'");
+ // 0123456789 0 123456789
+
+ static {
+ zulu.setTimeZone(TimeZone.getTimeZone("GMT"));
+ }
+
+ public void serialize(Object object, SerializationContext context) throws Exception {
+ // Simple types never get multiref'd, so just write the data now.
+ serializeData(object, context);
+ }
+
+ public void serializeData(Object object, SerializationContext context)
+ throws Exception {
+ String value = object.toString();
+ context.getWriter().writeCharacters(value);
+ context.getWriter().writeEndElement();
+ }
+
+ public String getValueAsString(Object value, SerializationContext context) {
+ // We could have separate serializers/deserializers to take
+ // care of Float/Double cases, but it makes more sence to
+ // put them here with the rest of the java lang primitives.
+ if (value instanceof Float ||
+ value instanceof Double) {
+ double data = 0.0;
+ if (value instanceof Float) {
+ data = ((Float) value).doubleValue();
+ } else {
+ data = ((Double) value).doubleValue();
+ }
+ if (Double.isNaN(data)) {
+ return "NaN";
+ } else if (data == Double.POSITIVE_INFINITY) {
+ return "INF";
+ } else if (data == Double.NEGATIVE_INFINITY) {
+ return "-INF";
+ }
+ } else if (value instanceof QName) {
+ return context.qName2String((QName)value);
+ }
+
+ return value.toString();
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/typemapping/TypeMappingRegistry.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/typemapping/TypeMappingRegistry.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/typemapping/TypeMappingRegistry.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/typemapping/TypeMappingRegistry.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,127 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.databinding.typemapping;
+
+import org.apache.axis2.databinding.metadata.BeanManager;
+import org.apache.axis2.databinding.DeserializerFactory;
+import org.apache.axis2.databinding.Serializer;
+import org.apache.axis2.databinding.metadata.BeanManager;
+import org.apache.axis2.databinding.deserializers.BeanDeserializerFactory;
+import org.apache.axis2.databinding.deserializers.SimpleDeserializerFactory;
+import org.apache.axis2.databinding.serializers.BeanSerializer;
+import org.apache.axis2.databinding.serializers.SimpleSerializer;
+import org.apache.axis.xsd.Constants;
+import org.w3c.dom.Element;
+
+import javax.xml.namespace.QName;
+import java.util.Calendar;
+import java.util.Date;
+
+/**
+ * TypeMappingRegistry
+ */
+public class TypeMappingRegistry {
+ public static boolean isPrimitive(Object value) {
+ if (value == null) return true;
+
+ Class javaType = (value instanceof Class) ? (Class)value :
+ value.getClass();
+
+ if (javaType.isPrimitive()) return true;
+
+ if (javaType == String.class) return true;
+ if (Calendar.class.isAssignableFrom(javaType)) return true;
+ if (Date.class.isAssignableFrom(javaType)) return true;
+// if (HexBinary.class.isAssignableFrom(javaType)) return true;
+ if (Element.class.isAssignableFrom(javaType)) return true;
+ if (javaType == byte[].class) return true;
+ if (Number.class.isAssignableFrom(javaType)) return true;
+
+ // There has been discussion as to whether arrays themselves should
+ // be regarded as multi-ref.
+ // Here are the three options:
+ // 1) Arrays are full-fledged Objects and therefore should always be
+ // multi-ref'd (Pro: This is like java. Con: Some runtimes don't
+ // support this yet, and it requires more stuff to be passed over the wire.)
+ // 2) Arrays are not full-fledged Objects and therefore should
+ // always be passed as single ref (note the elements of the array
+ // may be multi-ref'd.) (Pro: This seems reasonable, if a user
+ // wants multi-referencing put the array in a container. Also
+ // is more interop compatible. Con: Not like java serialization.)
+ // 3) Arrays of primitives should be single ref, and arrays of
+ // non-primitives should be multi-ref. (Pro: Takes care of the
+ // looping case. Con: Seems like an obtuse rule.)
+ //
+ // Changing the code from (1) to (2) to see if interop fairs better.
+ if (javaType.isArray()) return true;
+
+ return false;
+ }
+
+ public DeserializerFactory getDeserializerFactory(Class cls) {
+ if (isPrimitive(cls)) {
+ return new SimpleDeserializerFactory(cls, new QName("xsd", cls.getName()));
+ }
+
+ return new BeanDeserializerFactory(BeanManager.getTypeDesc(cls));
+ }
+
+ public Serializer getSerializer(Class cls) {
+ if (isPrimitive(cls)) {
+ return new SimpleSerializer();
+ }
+
+ return new BeanSerializer(BeanManager.getTypeDesc(cls));
+ }
+
+ public void registerMapping(Class javaType,
+ QName xmlType,
+ Serializer serializer,
+ DeserializerFactory deserFactory) {
+
+ }
+
+ public void initializeSchemaTypes() {
+ myRegisterSimple(Constants.XSD_STRING, java.lang.String.class);
+ myRegisterSimple(Constants.XSD_BOOLEAN, java.lang.Boolean.class);
+ myRegisterSimple(Constants.XSD_DOUBLE, java.lang.Double.class);
+ myRegisterSimple(Constants.XSD_FLOAT, java.lang.Float.class);
+ myRegisterSimple(Constants.XSD_INT, java.lang.Integer.class);
+ myRegisterSimple(Constants.XSD_INTEGER, java.math.BigInteger.class
+ );
+ myRegisterSimple(Constants.XSD_DECIMAL, java.math.BigDecimal.class
+ );
+ myRegisterSimple(Constants.XSD_LONG, java.lang.Long.class);
+ myRegisterSimple(Constants.XSD_SHORT, java.lang.Short.class);
+ myRegisterSimple(Constants.XSD_BYTE, java.lang.Byte.class);
+
+ // The XSD Primitives are mapped to java primitives.
+ myRegisterSimple(Constants.XSD_BOOLEAN, boolean.class);
+ myRegisterSimple(Constants.XSD_DOUBLE, double.class);
+ myRegisterSimple(Constants.XSD_FLOAT, float.class);
+ myRegisterSimple(Constants.XSD_INT, int.class);
+ myRegisterSimple(Constants.XSD_LONG, long.class);
+ myRegisterSimple(Constants.XSD_SHORT, short.class);
+ myRegisterSimple(Constants.XSD_BYTE, byte.class);
+ }
+
+ private void myRegisterSimple(QName xmlType, Class javaType) {
+ DeserializerFactory dser = new SimpleDeserializerFactory(javaType,
+ xmlType);
+ Serializer ser = new SimpleSerializer();
+ registerMapping(javaType, xmlType, ser, dser);
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/utils/Converter.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/utils/Converter.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/utils/Converter.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/databinding/utils/Converter.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,225 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.databinding.utils;
+
+import java.lang.reflect.Array;
+import java.util.ArrayList;
+import java.util.Calendar;
+import java.util.Collection;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Hashtable;
+import java.util.Iterator;
+import java.util.Set;
+
+/**
+ * Converter
+ */
+public class Converter {
+ public static Object convert(Object arg, Class destClass)
+ {
+ if (destClass == null) {
+ return arg;
+ }
+
+ Class argHeldType = null;
+ if (arg != null) {
+ argHeldType = getHolderValueType(arg.getClass());
+ }
+
+ if (arg != null && argHeldType == null && destClass.isAssignableFrom(arg.getClass())) {
+ return arg;
+ }
+
+ // See if a previously converted value is stored in the argument.
+ Object destValue = null;
+
+ // Get the destination held type or the argument held type if they exist
+ Class destHeldType = getHolderValueType(destClass);
+
+ // Convert between Axis special purpose HexBinary and byte[]
+// if (arg instanceof HexBinary &&
+// destClass == byte[].class) {
+// return ((HexBinary) arg).getBytes();
+// } else if (arg instanceof byte[] &&
+// destClass == HexBinary.class) {
+// return new HexBinary((byte[]) arg);
+// }
+
+ // Convert between Calendar and Date
+ if (arg instanceof Calendar && destClass == Date.class) {
+ return ((Calendar) arg).getTime();
+ }
+ if (arg instanceof Date && destClass == Calendar.class) {
+ Calendar calendar = Calendar.getInstance();
+ calendar.setTime((Date) arg);
+ return calendar;
+ }
+
+ // Convert between Calendar and java.sql.Date
+ if (arg instanceof Calendar && destClass == java.sql.Date.class) {
+ return new java.sql.Date(((Calendar) arg).getTime().getTime());
+ }
+
+ // Convert between HashMap and Hashtable
+ if (arg instanceof HashMap && destClass == Hashtable.class) {
+ return new Hashtable((HashMap)arg);
+ }
+
+ // If the destination is an array and the source
+ // is a suitable component, return an array with
+ // the single item.
+ if (arg != null &&
+ destClass.isArray() &&
+ !destClass.getComponentType().equals(Object.class) &&
+ destClass.getComponentType().isAssignableFrom(arg.getClass())) {
+ Object array =
+ Array.newInstance(destClass.getComponentType(), 1);
+ Array.set(array, 0, arg);
+ return array;
+ }
+
+ // Return if no conversion is available
+ if (!(arg instanceof Collection ||
+ (arg != null && arg.getClass().isArray())) &&
+ ((destHeldType == null && argHeldType == null) ||
+ (destHeldType != null && argHeldType != null))) {
+ return arg;
+ }
+
+ // Take care of Holder conversion
+/*
+ if (destHeldType != null) {
+ // Convert arg into Holder holding arg.
+ Object newArg = convert(arg, destHeldType);
+ Object argHolder = null;
+ try {
+ argHolder = destClass.newInstance();
+ setHolderValue(argHolder, newArg);
+ return argHolder;
+ } catch (Exception e) {
+ return arg;
+ }
+ } else if (argHeldType != null) {
+ // Convert arg into the held type
+ try {
+ Object newArg = getHolderValue(arg);
+ return convert(newArg, destClass);
+ } catch (HolderException e) {
+ return arg;
+ }
+ }
+*/
+
+ // Flow to here indicates that neither arg or destClass is a Holder
+
+ if (arg == null) {
+ return arg;
+ }
+
+ // The arg may be an array or List
+ int length = 0;
+ if (arg.getClass().isArray()) {
+ length = Array.getLength(arg);
+ } else {
+ length = ((Collection) arg).size();
+ }
+ if (destClass.isArray()) {
+ if (destClass.getComponentType().isPrimitive()) {
+
+ Object array = Array.newInstance(destClass.getComponentType(),
+ length);
+ // Assign array elements
+ if (arg.getClass().isArray()) {
+ for (int i = 0; i < length; i++) {
+ Array.set(array, i, Array.get(arg, i));
+ }
+ } else {
+ int idx = 0;
+ for (Iterator i = ((Collection)arg).iterator();
+ i.hasNext();) {
+ Array.set(array, idx++, i.next());
+ }
+ }
+ destValue = array;
+
+ } else {
+ Object [] array;
+ try {
+ array = (Object [])Array.newInstance(destClass.getComponentType(),
+ length);
+ } catch (Exception e) {
+ return arg;
+ }
+
+ // Use convert to assign array elements.
+ if (arg.getClass().isArray()) {
+ for (int i = 0; i < length; i++) {
+ array[i] = convert(Array.get(arg, i),
+ destClass.getComponentType());
+ }
+ } else {
+ int idx = 0;
+ for (Iterator i = ((Collection)arg).iterator();
+ i.hasNext();) {
+ array[idx++] = convert(i.next(),
+ destClass.getComponentType());
+ }
+ }
+ destValue = array;
+ }
+ }
+ else if (Collection.class.isAssignableFrom(destClass)) {
+ Collection newList = null;
+ try {
+ // if we are trying to create an interface, build something
+ // that implements the interface
+ if (destClass == Collection.class || destClass == java.util.List.class) {
+ newList = new ArrayList();
+ } else if (destClass == Set.class) {
+ newList = new HashSet();
+ } else {
+ newList = (Collection)destClass.newInstance();
+ }
+ } catch (Exception e) {
+ // Couldn't build one for some reason... so forget it.
+ return arg;
+ }
+
+ if (arg.getClass().isArray()) {
+ for (int j = 0; j < length; j++) {
+ newList.add(Array.get(arg, j));
+ }
+ } else {
+ for (Iterator j = ((Collection)arg).iterator();
+ j.hasNext();) {
+ newList.add(j.next());
+ }
+ }
+ destValue = newList;
+ }
+ else {
+ destValue = arg;
+ }
+
+ return destValue;
+ }
+
+ private static Class getHolderValueType(Class aClass) {
+ return null;
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCInOutMessageReceiver.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCInOutMessageReceiver.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCInOutMessageReceiver.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCInOutMessageReceiver.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,139 @@
+/*
+ * Copyright 2004,2005 The Apache Software Foundation.
+ *
+ * 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.axis2.rpc;
+
+import org.apache.axis2.AxisFault;
+import org.apache.axis2.context.MessageContext;
+import org.apache.axis2.context.OperationContext;
+import org.apache.axis2.databinding.DeserializationContext;
+import org.apache.axis2.databinding.Deserializer;
+import org.apache.axis2.om.OMAbstractFactory;
+import org.apache.axis2.om.OMElement;
+import org.apache.axis2.receivers.AbstractInOutSyncMessageReceiver;
+import org.apache.axis2.soap.SOAPBody;
+import org.apache.axis2.soap.SOAPEnvelope;
+import org.apache.axis2.soap.SOAPFactory;
+
+import javax.xml.namespace.QName;
+import java.lang.reflect.Method;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+
+/**
+ *
+ */
+public class RPCInOutMessageReceiver extends AbstractInOutSyncMessageReceiver {
+ public static final String RPCMETHOD_PROPERTY = "rpc.method";
+
+ public RPCInOutMessageReceiver() {
+ }
+
+ public void invokeBusinessLogic(MessageContext inMessage,
+ MessageContext outMessage) throws AxisFault {
+ SOAPEnvelope env = inMessage.getEnvelope();
+ SOAPBody body = env.getBody();
+ OMElement rpcElement = body.getFirstElement();
+
+ /**
+ * Locate method descriptor using QName or action
+ */
+ OperationContext oc = inMessage.getOperationContext();
+ RPCMethod method = (RPCMethod)oc.getProperty(RPCMETHOD_PROPERTY);
+ if (method == null) {
+ throw new AxisFault("Couldn't find RPCMethod in OperationContext");
+ }
+
+ Method javaMethod = method.getJavaMethod();
+ Object [] arguments = null;
+ Object targetObject = this.getTheImplementationObject(inMessage);
+ DeserializationContext dserContext = new DeserializationContext();
+
+ // Run each argument (sub-element) through the appropriate deser
+ Iterator args = rpcElement.getChildElements();
+ Map elementCounts = new HashMap();
+ while (args.hasNext()) {
+ OMElement arg = (OMElement) args.next();
+ QName qname = arg.getQName();
+ RPCParameter param = method.getParameter(qname);
+ if (param == null) {
+ // unknown parameter. Fault or continue depending on
+ // strictness configuration.
+ continue;
+ }
+ Integer count = (Integer)elementCounts.get(qname);
+ if (count == null) count = new Integer(0);
+ elementCounts.put(qname, new Integer(count.intValue() + 1));
+ Deserializer dser = param.getDeserializer(count.intValue());
+ // Got a recognized param, so feed this through the deserializer
+ try {
+ dserContext.deserialize(arg.getXMLStreamReader(), dser);
+ } catch (Exception e) {
+ throw AxisFault.makeFault(e);
+ }
+ }
+
+ // OK, now we're done with the children. If this is SOAP 1.2, we're
+ // finished. If it's SOAP 1.1, there may be multirefs which still
+ // need to be deserialized after the RPC element.
+ if (dserContext.isIncomplete()) {
+ try {
+ dserContext.processRest(rpcElement);
+ } catch (Exception e) {
+ throw AxisFault.makeFault(e);
+ }
+
+ if (dserContext.isIncomplete()) {
+ throw new AxisFault("Unresolved multirefs!");
+ }
+ }
+
+ arguments = new Object [method.getNumInParams()];
+ Iterator params = method.getInParams();
+ for (int i = 0; i < arguments.length; i++) {
+ arguments[i] = ((RPCParameter)params.next()).getValue();
+ }
+
+ Object returnValue = null;
+ try {
+ returnValue = javaMethod.invoke(targetObject, arguments);
+ } catch (Exception e) {
+ throw AxisFault.makeFault(e);
+ }
+
+ // The response parameter, if any, is where the return value should go
+ RPCParameter responseParam = method.getResponseParameter();
+ if (responseParam != null) {
+ responseParam.setValue(returnValue);
+ }
+
+ // Now make the response message.
+ try {
+ SOAPFactory factory = OMAbstractFactory.getSOAP11Factory();
+ SOAPEnvelope responseEnv = factory.createSOAPEnvelope();
+ SOAPBody respBody = factory.createSOAPBody(responseEnv);
+
+ // Just need to create this, since it automatically links itself
+ // to the response body and will therefore get serialize()d at
+ // the appropriate time.
+ new RPCResponseElement(method, respBody);
+
+ outMessage.setEnvelope(responseEnv);
+ } catch (Exception e) {
+ throw AxisFault.makeFault(e);
+ }
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCMethod.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCMethod.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCMethod.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCMethod.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,148 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.rpc;
+
+import org.apache.axis2.soap.SOAPEnvelope;
+import org.apache.axis2.soap.SOAPFactory;
+import org.apache.axis2.soap.SOAPBody;
+import org.apache.axis2.om.OMAbstractFactory;
+import org.apache.axis2.om.OMElement;
+
+import javax.xml.namespace.QName;
+import java.lang.reflect.Method;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+
+/**
+ * RPCMethod
+ */
+public class RPCMethod {
+ static class Outerator implements Iterator {
+ ArrayList params;
+ RPCParameter cache = null;
+ int badMode;
+ int idx = 0;
+
+ public Outerator(ArrayList params, int badMode) {
+ this.params = params;
+ this.badMode = badMode;
+ }
+
+ public void remove() {
+
+ }
+
+ public boolean hasNext() {
+ if (cache != null) return true;
+ while (idx < params.size()) {
+ RPCParameter param = (RPCParameter)params.get(idx);
+ idx++;
+ if (param.mode != badMode) {
+ cache = param;
+ return true;
+ }
+ }
+ return false;
+ }
+
+ public Object next() {
+ RPCParameter ret = null;
+ if (hasNext()) {
+ ret = cache;
+ cache = null;
+ }
+ return ret;
+ }
+ }
+
+ int numInParams, numOutParams;
+ Map parameters = new HashMap();
+ ArrayList orderedParameters = new ArrayList();
+ Method javaMethod;
+
+ QName qname;
+ QName responseQName;
+
+ public RPCMethod(QName qname) {
+ this.qname = qname;
+ }
+
+ public ArrayList getParams() {
+ return orderedParameters;
+ }
+
+ public void addParameter(RPCParameter param) {
+ orderedParameters.add(param);
+ parameters.put(param.getQName(), param);
+ if (param.getMode() != RPCParameter.MODE_OUT) {
+ numInParams++;
+ }
+ if (param.getMode() != RPCParameter.MODE_IN) {
+ numOutParams++;
+ }
+ }
+
+ public RPCParameter getParameter(QName qname) {
+ return (RPCParameter)parameters.get(qname);
+ }
+
+ public Method getJavaMethod() {
+ return javaMethod;
+ }
+
+ public void setJavaMethod(Method javaMethod) {
+ this.javaMethod = javaMethod;
+ }
+
+ public QName getResponseQName() {
+ return responseQName;
+ }
+
+ public void setResponseQName(QName responseQName) {
+ this.responseQName = responseQName;
+ }
+
+ public QName getQName() {
+ return qname;
+ }
+
+ public RPCParameter getResponseParameter() {
+ for (Iterator i = orderedParameters.iterator(); i.hasNext();) {
+ RPCParameter parameter = (RPCParameter) i.next();
+ if (parameter.getMode() == RPCParameter.MODE_OUT)
+ return parameter;
+ }
+ return null;
+ }
+
+ public Iterator getOutParams() {
+ return new Outerator(orderedParameters, RPCParameter.MODE_IN);
+ }
+
+ public Iterator getInParams() {
+ return new Outerator(orderedParameters, RPCParameter.MODE_OUT);
+ }
+
+ public int getNumInParams() {
+ return numInParams;
+ }
+
+ public int getNumOutParams() {
+ return numOutParams;
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCParameter.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCParameter.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCParameter.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCParameter.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,130 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.rpc;
+
+import org.apache.axis2.databinding.DeserializationTarget;
+import org.apache.axis2.databinding.Deserializer;
+import org.apache.axis2.databinding.SerializationContext;
+import org.apache.axis2.databinding.utils.Converter;
+import org.apache.axis2.databinding.metadata.ElementDesc;
+
+import java.util.ArrayList;
+
+/**
+ * RPCParameter
+ */
+public class RPCParameter extends ElementDesc {
+ class ParamTarget implements DeserializationTarget {
+ RPCParameter param;
+
+ public ParamTarget(RPCParameter param) {
+ this.param = param;
+ }
+
+ public void setValue(Object value) throws Exception {
+ param.setValue(value);
+ }
+ }
+
+ class IndexedParamTarget implements DeserializationTarget {
+ RPCParameter param;
+ int index;
+
+ public IndexedParamTarget(RPCParameter param, int index) {
+ this.param = param;
+ this.index = index;
+ }
+
+ public void setValue(Object value) throws Exception {
+ param.setIndexedValue(index, value);
+ }
+ }
+
+ public static final int MODE_IN = 0;
+ public static final int MODE_OUT = 1;
+ public static final int MODE_INOUT = 2;
+
+ Object value;
+ int mode;
+ Class destClass;
+
+ public Object getValue() {
+ if (destClass != null)
+ return Converter.convert(value, destClass);
+
+ return value;
+ }
+
+ public void setValue(Object value) {
+ this.value = value;
+ }
+
+ public int getMode() {
+ return mode;
+ }
+
+ public void setMode(int mode) {
+ this.mode = mode;
+ }
+
+ public Class getDestClass() {
+ return destClass;
+ }
+
+ public void setDestClass(Class destClass) {
+ this.destClass = destClass;
+ }
+
+ public void serialize(SerializationContext context) throws Exception {
+ if (ser == null) {
+ // no serializer!
+ throw new Exception("No serializer in RPCParameter");
+ }
+ context.serializeElement(qname, value, ser);
+ }
+
+ public Deserializer getDeserializer(int i) {
+ if (i > maxOccurs && maxOccurs > -1) {
+ // fail
+ throw new RuntimeException("Too many elements");
+ }
+
+ DeserializationTarget target;
+ if (maxOccurs == -1 || maxOccurs > 1) {
+ if (value == null) value = new ArrayList();
+ target = new IndexedParamTarget(this, i);
+ } else {
+ target = new ParamTarget(this);
+ }
+
+ Deserializer dser = deserializerFactory.getDeserializer();
+ dser.setTarget(target);
+ return dser;
+ }
+
+ public void setIndexedValue(int index, Object value) {
+ ArrayList coll = (ArrayList)this.value;
+ if (coll.size() == index) {
+ coll.add(value);
+ return;
+ }
+
+ while (index + 1 > coll.size()) {
+ coll.add(null);
+ }
+ coll.set(index, value);
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCRequestElement.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCRequestElement.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCRequestElement.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCRequestElement.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,67 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.rpc;
+
+import org.apache.axis2.databinding.SerializationContext;
+import org.apache.axis2.om.OMElement;
+import org.apache.axis2.om.impl.OMOutputImpl;
+import org.apache.axis2.om.impl.llom.OMElementImpl;
+
+import javax.xml.stream.XMLStreamException;
+import javax.xml.stream.XMLStreamWriter;
+import java.util.Iterator;
+
+/**
+ * RPCResponseElement
+ */
+public class RPCRequestElement extends OMElementImpl {
+ RPCMethod method;
+
+ public RPCRequestElement(RPCMethod method, OMElement parent) {
+ super(method.getQName(), parent);
+ this.method = method;
+ }
+
+ protected void serialize(OMOutputImpl omOutput, boolean cache)
+ throws XMLStreamException {
+ XMLStreamWriter writer = omOutput.getXmlStreamWriter();
+ SerializationContext context = new SerializationContext(writer);
+
+ // Write wrapper element
+ if (ns == null) {
+ writer.writeStartElement(localName);
+ } else {
+ writer.writeStartElement(localName, ns.getName(), ns.getPrefix());
+ }
+ Iterator inParams = method.getInParams();
+ while (inParams.hasNext()) {
+ RPCParameter parameter = (RPCParameter) inParams.next();
+ try {
+ parameter.serialize(context);
+ } catch (Exception e) {
+ throw new XMLStreamException("Couldn't serialize RPCParameter",
+ e);
+ }
+ }
+ writer.writeEndElement();
+
+ try {
+ context.finish();
+ } catch (Exception e) {
+ throw new XMLStreamException(e);
+ }
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCResponseElement.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCResponseElement.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCResponseElement.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/rpc/RPCResponseElement.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,67 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.rpc;
+
+import org.apache.axis2.databinding.SerializationContext;
+import org.apache.axis2.om.OMElement;
+import org.apache.axis2.om.impl.OMOutputImpl;
+import org.apache.axis2.om.impl.llom.OMElementImpl;
+
+import javax.xml.stream.XMLStreamException;
+import javax.xml.stream.XMLStreamWriter;
+import java.util.Iterator;
+
+/**
+ * RPCResponseElement
+ */
+public class RPCResponseElement extends OMElementImpl {
+ RPCMethod method;
+
+ public RPCResponseElement(RPCMethod method, OMElement parent) {
+ super(method.getResponseQName(), parent);
+ this.method = method;
+ }
+
+ protected void serialize(OMOutputImpl omOutput, boolean cache)
+ throws XMLStreamException {
+ XMLStreamWriter writer = omOutput.getXmlStreamWriter();
+ SerializationContext context = new SerializationContext(writer);
+
+ // Write wrapper element
+ if (ns == null) {
+ writer.writeStartElement(localName);
+ } else {
+ writer.writeStartElement(localName, ns.getName(), ns.getPrefix());
+ }
+ Iterator outParams = method.getOutParams();
+ while (outParams.hasNext()) {
+ RPCParameter parameter = (RPCParameter) outParams.next();
+ try {
+ parameter.serialize(context);
+ } catch (Exception e) {
+ throw new XMLStreamException("Couldn't serialize RPCParameter",
+ e);
+ }
+ }
+ writer.writeEndElement();
+
+ try {
+ context.finish();
+ } catch (Exception e) {
+ throw new XMLStreamException(e);
+ }
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/util/MethodCache.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/util/MethodCache.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/util/MethodCache.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/src/org/apache/axis2/util/MethodCache.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,208 @@
+/*
+ * Copyright 2001-2004 The Apache Software Foundation.
+ *
+ * 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.axis2.util;
+
+import java.lang.reflect.Method;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * A cache for methods.
+ * Used to get methods by their signature and stores them in a local
+ * cache for performance reasons.
+ * This class is a singleton - so use getInstance to get an instance of it.
+ *
+ * @author Davanum Srinivas <di...@yahoo.com>
+ * @author Sebastian Dietrich <se...@anecon.com>
+ */
+public class MethodCache {
+ /**
+ * The only instance of this class
+ */
+ transient private static MethodCache instance;
+
+ /**
+ * Cache for Methods
+ * In fact this is a map (with classes as keys) of a map (with method-names as keys)
+ */
+ transient private static ThreadLocal cache;
+
+ /**
+ * The <i>private</i> constructor for this class.
+ * Use getInstance to get an instance (the only one).
+ */
+ private MethodCache() {
+ cache = new ThreadLocal();
+ }
+
+ /**
+ * Gets the only instance of this class
+ * @return the only instance of this class
+ */
+ public static MethodCache getInstance() {
+ if (instance == null) {
+ instance = new MethodCache();
+ }
+ return instance;
+ }
+
+ /**
+ * Returns the per thread hashmap (for method caching)
+ */
+ private Map getMethodCache() {
+ Map map = (Map) cache.get();
+ if (map == null) {
+ map = new HashMap();
+ cache.set(map);
+ }
+ return map;
+ }
+
+ /**
+ * Class used as the key for the method cache table.
+ *
+ */
+ static class MethodKey {
+ /** the name of the method in the cache */
+ private final String methodName;
+ /** the list of types accepted by the method as arguments */
+ private final Class[] parameterTypes;
+
+ /**
+ * Creates a new <code>MethodKey</code> instance.
+ *
+ * @param methodName a <code>String</code> value
+ * @param parameterTypes a <code>Class[]</code> value
+ */
+ MethodKey(String methodName, Class[] parameterTypes) {
+ this.methodName = methodName;
+ this.parameterTypes = parameterTypes;
+ }
+
+ public boolean equals(Object other) {
+ MethodKey that = (MethodKey) other;
+ return this.methodName.equals(that.methodName)
+ && Arrays.equals(this.parameterTypes,
+ that.parameterTypes);
+ }
+
+ public int hashCode() {
+ // allow overloaded methods to collide; we'll sort it out
+ // in equals(). Note that String's implementation of
+ // hashCode already caches its value, so there's no point
+ // in doing so here.
+ return methodName.hashCode();
+ }
+ }
+
+ /** used to track methods we've sought but not found in the past */
+ private static final Object NULL_OBJECT = new Object();
+
+ /**
+ * Returns the specified method - if any.
+ *
+ * @param clazz the class to get the method from
+ * @param methodName the name of the method
+ * @param parameterTypes the parameters of the method
+ * @return the found method
+ *
+ * @throws NoSuchMethodException if the method can't be found
+ */
+ public Method getMethod(Class clazz,
+ String methodName,
+ Class[] parameterTypes)
+ throws NoSuchMethodException {
+ String className = clazz.getName();
+ Map cache = getMethodCache();
+ Method method = null;
+ Map methods = null;
+
+ // Strategy is as follows:
+ // construct a MethodKey to represent the name/arguments
+ // of a method's signature.
+ //
+ // use the name of the class to retrieve a map of that
+ // class' methods
+ //
+ // if a map exists, use the MethodKey to find the
+ // associated value object. if that object is a Method
+ // instance, return it. if that object is anything
+ // else, then it's a reference to our NULL_OBJECT
+ // instance, indicating that we've previously tried
+ // and failed to find a method meeting our requirements,
+ // so return null
+ //
+ // if the map of methods for the class doesn't exist,
+ // or if no value is associated with our key in that map,
+ // then we perform a reflection-based search for the method.
+ //
+ // if we find a method in that search, we store it in the
+ // map using the key; otherwise, we store a reference
+ // to NULL_OBJECT using the key.
+
+ // Check the cache first.
+ MethodKey key = new MethodKey(methodName, parameterTypes);
+ methods = (Map) cache.get(clazz);
+ if (methods != null) {
+ Object o = methods.get(key);
+ if (o != null) { // cache hit
+ if (o instanceof Method) { // good cache hit
+ return (Method) o;
+ } else { // bad cache hit
+ // we hit the NULL_OBJECT, so this is a search
+ // that previously failed; no point in doing
+ // it again as it is a worst case search
+ // through the entire classpath.
+ return null;
+ }
+ } else {
+ // cache miss: fall through to reflective search
+ }
+ } else {
+ // cache miss: fall through to reflective search
+ }
+
+ try {
+ method = clazz.getMethod(methodName, parameterTypes);
+ } catch (NoSuchMethodException e1) {
+ if (!clazz.isPrimitive() && !className.startsWith("java.") && !className.startsWith("javax.")) {
+ try {
+ Class helper = Class.forName(className + "_Helper");
+ method = helper.getMethod(methodName, parameterTypes);
+ } catch (ClassNotFoundException e2) {
+ }
+ }
+ }
+
+ // first time we've seen this class: set up its method cache
+ if (methods == null) {
+ methods = new HashMap();
+ cache.put(clazz, methods);
+ }
+
+ // when no method is found, cache the NULL_OBJECT
+ // so that we don't have to repeat worst-case searches
+ // every time.
+
+ if (null == method) {
+ methods.put(key, NULL_OBJECT);
+ } else {
+ methods.put(key, method);
+ }
+ return method;
+ }
+}
Added: webservices/axis2/trunk/java/modules/databinding/test-resources/xmls/array1.xml
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/test-resources/xmls/array1.xml?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/test-resources/xmls/array1.xml (added)
+++ webservices/axis2/trunk/java/modules/databinding/test-resources/xmls/array1.xml Wed Sep 7 19:39:15 2005
@@ -0,0 +1,5 @@
+<wrapper>
+ <item>one</item>
+ <item>two</item>
+ <item>three</item>
+</wrapper>
\ No newline at end of file
Added: webservices/axis2/trunk/java/modules/databinding/test/org/apache/axis2/databinding/ArrayTest.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/databinding/test/org/apache/axis2/databinding/ArrayTest.java?rev=279491&view=auto
==============================================================================
--- webservices/axis2/trunk/java/modules/databinding/test/org/apache/axis2/databinding/ArrayTest.java (added)
+++ webservices/axis2/trunk/java/modules/databinding/test/org/apache/axis2/databinding/ArrayTest.java Wed Sep 7 19:39:15 2005
@@ -0,0 +1,104 @@
+/*
+* Copyright 2004,2005 The Apache Software Foundation.
+*
+* 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.axis2.databinding;
+
+import junit.framework.TestCase;
+import org.apache.axis2.databinding.deserializers.BeanDeserializer;
+import org.apache.axis2.databinding.metadata.BeanManager;
+import org.apache.axis2.databinding.metadata.ElementDesc;
+import org.apache.axis2.databinding.metadata.TypeDesc;
+import org.apache.axis2.om.OMAbstractFactory;
+import org.apache.axis2.om.OMElement;
+import org.apache.axis2.om.impl.llom.builder.StAXOMBuilder;
+import org.apache.axis2.om.impl.llom.factory.OMXMLBuilderFactory;
+
+import javax.xml.namespace.QName;
+import javax.xml.stream.XMLInputFactory;
+import javax.xml.stream.XMLStreamReader;
+import java.io.FileInputStream;
+import java.io.InputStream;
+import java.util.ArrayList;
+
+/**
+ * ArrayTest
+ */
+public class ArrayTest extends TestCase {
+ public static class TestBean {
+ static TypeDesc typeDesc;
+
+ public static TypeDesc getTypeDesc() {
+ if (typeDesc == null) {
+ typeDesc = new TypeDesc();
+ typeDesc.setJavaClass(ArrayTest.class);
+ ElementDesc desc = new ElementDesc();
+ desc.setFieldName("collection");
+ desc.setQName(new QName("item"));
+ desc.setMaxOccurs(-1);
+ typeDesc.addField(desc);
+ }
+ return typeDesc;
+ }
+
+ ArrayList coll;
+
+ public TestBean() {
+ coll = new ArrayList();
+ }
+
+ public String [] getCollection() {
+ return (String[])(coll.toArray(new String [coll.size()]));
+ }
+
+ public void setCollection(int index, String val) {
+ if (index + 1 > coll.size()) {
+ while (index + 1 > coll.size()) {
+ coll.add(null);
+ }
+ }
+ coll.set(index, val);
+ }
+
+ public String getCollection(int index) {
+ return (String)coll.get(index);
+ }
+ }
+
+ public void testArray() throws Exception {
+ InputStream is = new FileInputStream("test-resources/xmls/array1.xml");
+ XMLStreamReader reader = XMLInputFactory.newInstance().createXMLStreamReader(is);
+
+ StAXOMBuilder builder = OMXMLBuilderFactory.createStAXOMBuilder(OMAbstractFactory.getOMFactory(), reader);
+ OMElement el = builder.getDocumentElement();
+ XMLStreamReader omReader = el.getXMLStreamReaderWithoutCaching();
+ omReader.next();
+ DeserializationContext context = new DeserializationContext();
+
+ TypeDesc typeDesc = BeanManager.getTypeDesc(TestBean.class);
+ BeanDeserializer dser = new BeanDeserializer(typeDesc);
+
+ dser.setTarget(new DeserializationTarget() {
+ public void setValue(Object value) {
+ assertTrue(value instanceof TestBean);
+ TestBean bean = (TestBean)value;
+ assertEquals("Wrong # of items", 3, bean.coll.size());
+ assertEquals("one", bean.getCollection(0));
+ assertEquals("two", bean.getCollection(1));
+ assertEquals("three", bean.getCollection(2));
+ }
+ });
+ dser.deserialize(omReader, context);
+ }
+}
Modified: webservices/axis2/trunk/java/modules/wsdl/project.properties
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/wsdl/project.properties?rev=279491&r1=279490&r2=279491&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/wsdl/project.properties (original)
+++ webservices/axis2/trunk/java/modules/wsdl/project.properties Wed Sep 7 19:39:15 2005
@@ -14,6 +14,5 @@
# limitations under the License.
# -------------------------------------------------------------------
-maven.repo.remote=http://cvs.apache.org/repository/,http://www.apache.org/dist/java-repository,http://www.ibiblio.org/maven,http://www.apache.org/dist/java-repository/,http://people.apache.org/~dims/maven/
+maven.repo.remote=http://cvs.apache.org/repository/,http://www.apache.org/dist/java-repository,http://www.ibiblio.org/maven,http://www.apache.org/dist/java-repository/,http://people.apache.org/~gdaniels/maven/
maven.multiproject.type=jar
-maven.jar.XmlSchema=${basedir}/lib/XmlSchema.jar
\ No newline at end of file
Modified: webservices/axis2/trunk/java/modules/wsdl/project.xml
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/wsdl/project.xml?rev=279491&r1=279490&r2=279491&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/wsdl/project.xml (original)
+++ webservices/axis2/trunk/java/modules/wsdl/project.xml Wed Sep 7 19:39:15 2005
@@ -37,7 +37,7 @@
<dependency>
<groupId>axis</groupId>
<artifactId>XmlSchema</artifactId>
- <version>0.9</version>
+ <version>SNAPSHOT</version>
</dependency>
<!-- external JARs -->
<dependency>
Modified: webservices/axis2/trunk/java/modules/xml/src/org/apache/axis2/om/impl/OMOutputImpl.java
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/modules/xml/src/org/apache/axis2/om/impl/OMOutputImpl.java?rev=279491&r1=279490&r2=279491&view=diff
==============================================================================
--- webservices/axis2/trunk/java/modules/xml/src/org/apache/axis2/om/impl/OMOutputImpl.java (original)
+++ webservices/axis2/trunk/java/modules/xml/src/org/apache/axis2/om/impl/OMOutputImpl.java Wed Sep 7 19:39:15 2005
@@ -84,18 +84,16 @@
if (charSetEncoding == null) //Default encoding is UTF-8
this.charSetEncoding = DEFAULT_CHAR_SET_ENCODING;
+ XMLOutputFactory factory = XMLOutputFactory.newInstance();
+// factory.setProperty("javax.xml.stream.isRepairingNamespaces", Boolean.TRUE);
if (doOptimize) {
bufferedSoapOutStream = new ByteArrayOutputStream();
- xmlWriter =
- XMLOutputFactory.newInstance().createXMLStreamWriter(
- bufferedSoapOutStream,
- this.charSetEncoding);
+ xmlWriter = factory.createXMLStreamWriter(bufferedSoapOutStream,
+ this.charSetEncoding);
binaryNodeList = new LinkedList();
} else {
- xmlWriter =
- XMLOutputFactory.newInstance().createXMLStreamWriter(
- outStream,
- this.charSetEncoding);
+ xmlWriter = factory.createXMLStreamWriter(outStream,
+ this.charSetEncoding);
}
}
Modified: webservices/axis2/trunk/java/project.properties
URL: http://svn.apache.org/viewcvs/webservices/axis2/trunk/java/project.properties?rev=279491&r1=279490&r2=279491&view=diff
==============================================================================
--- webservices/axis2/trunk/java/project.properties (original)
+++ webservices/axis2/trunk/java/project.properties Wed Sep 7 19:39:15 2005
@@ -19,6 +19,7 @@
maven.multiproject.includes=\
modules/common/project.xml,\
modules/xml/project.xml,\
+modules/databinding/project.xml,\
modules/wsdl/project.xml,\
modules/core/project.xml,\
modules/addressing/project.xml,\