Return-Path: Delivered-To: apmail-ws-tuscany-commits-archive@locus.apache.org Received: (qmail 54758 invoked from network); 4 Jun 2008 01:04:50 -0000 Received: from hermes.apache.org (HELO mail.apache.org) (140.211.11.2) by minotaur.apache.org with SMTP; 4 Jun 2008 01:04:50 -0000 Received: (qmail 55602 invoked by uid 500); 4 Jun 2008 01:04:53 -0000 Delivered-To: apmail-ws-tuscany-commits-archive@ws.apache.org Received: (qmail 55565 invoked by uid 500); 4 Jun 2008 01:04:53 -0000 Mailing-List: contact tuscany-commits-help@ws.apache.org; run by ezmlm Precedence: bulk List-Help: List-Unsubscribe: List-Post: List-Id: Reply-To: tuscany-dev@ws.apache.org Delivered-To: mailing list tuscany-commits@ws.apache.org Received: (qmail 55556 invoked by uid 99); 4 Jun 2008 01:04:53 -0000 Received: from nike.apache.org (HELO nike.apache.org) (192.87.106.230) by apache.org (qpsmtpd/0.29) with ESMTP; Tue, 03 Jun 2008 18:04:53 -0700 X-ASF-Spam-Status: No, hits=-2000.0 required=10.0 tests=ALL_TRUSTED X-Spam-Check-By: apache.org Received: from [140.211.11.4] (HELO eris.apache.org) (140.211.11.4) by apache.org (qpsmtpd/0.29) with ESMTP; Wed, 04 Jun 2008 01:04:03 +0000 Received: by eris.apache.org (Postfix, from userid 65534) id A769B2388A51; Tue, 3 Jun 2008 18:04:21 -0700 (PDT) Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Subject: svn commit: r662937 [2/2] - in /incubator/tuscany/java/sca: itest/databindings/jaxb-bottom-up/src/main/java/org/apache/tuscany/sca/itest/databindings/jaxb/ itest/databindings/jaxb-bottom-up/src/main/java/org/apache/tuscany/sca/itest/databindings/jaxb/i... Date: Wed, 04 Jun 2008 01:04:20 -0000 To: tuscany-commits@ws.apache.org From: rfeng@apache.org X-Mailer: svnmailer-1.0.8 Message-Id: <20080604010421.A769B2388A51@eris.apache.org> X-Virus-Checked: Checked by ClamAV on apache.org Modified: incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/JAXWSFaultExceptionMapper.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/JAXWSFaultExceptionMapper.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/JAXWSFaultExceptionMapper.java (original) +++ incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/JAXWSFaultExceptionMapper.java Tue Jun 3 18:04:18 2008 @@ -24,6 +24,8 @@ import java.beans.PropertyDescriptor; import java.lang.reflect.Constructor; import java.lang.reflect.Method; +import java.security.AccessController; +import java.security.PrivilegedAction; import javax.xml.namespace.QName; import javax.xml.ws.WebFault; @@ -31,6 +33,7 @@ import org.apache.tuscany.sca.databinding.DataBindingExtensionPoint; import org.apache.tuscany.sca.interfacedef.DataType; import org.apache.tuscany.sca.interfacedef.FaultExceptionMapper; +import org.apache.tuscany.sca.interfacedef.impl.DataTypeImpl; import org.apache.tuscany.sca.interfacedef.util.FaultException; import org.apache.tuscany.sca.interfacedef.util.XMLType; import org.osoa.sca.ServiceRuntimeException; @@ -78,15 +81,8 @@ DataType faultBeanType = exceptionType.getLogical(); Class faultBeanClass = faultBeanType.getPhysical(); try { - Exception exc = null; - try { - Constructor constructor = - exceptionClass.getConstructor(new Class[] {String.class, faultBeanClass, Throwable.class}); - exc = (Exception)constructor.newInstance(new Object[] {message, faultInfo, cause}); - } catch (NoSuchMethodException e) { - // Create a generic fault exception - exc = new FaultException(message, faultInfo, cause); - } + Throwable exc = + newInstance((Class)exceptionClass, message, faultBeanClass, faultInfo, cause); // Include the elem name into the FaultException we build so it can be used for matching in the DataTransformationInterceptor // // Note this may happen even if we find a constructor above, that is the type of the non-generic fault exc may be an instance @@ -104,6 +100,77 @@ } } + private Throwable newInstance(Class exceptionClass, + String message, + Class faultBeanClass, + Object faultInfo, + Throwable cause) throws Exception { + Throwable ex = null; + Constructor ctor = null; + try { + // Get the message property + Method getMessage = faultBeanClass.getMethod("getMessage"); + message = (String)getMessage.invoke(faultInfo); + } catch (Throwable e) { + // Ignore + } + try { + // FIXME: What about if the faultBeanClass is a subclass of the argument type? + ctor = exceptionClass.getConstructor(String.class, faultBeanClass, Throwable.class); + ex = ctor.newInstance(message, faultInfo, cause); + } catch (NoSuchMethodException e1) { + try { + ctor = exceptionClass.getConstructor(String.class, faultInfo.getClass()); + ex = ctor.newInstance(message, faultInfo); + } catch (NoSuchMethodException e2) { + try { + ctor = exceptionClass.getConstructor(String.class, Throwable.class); + ex = ctor.newInstance(message, cause); + populateException(ex, faultInfo); + } catch (NoSuchMethodException e3) { + try { + ctor = exceptionClass.getConstructor(String.class); + ex = ctor.newInstance(message); + populateException(ex, faultInfo); + } catch (NoSuchMethodException e4) { + ctor = exceptionClass.getConstructor(); + if (ctor != null) { + ex = ctor.newInstance(); + populateException(ex, faultInfo); + } else { + ex = new FaultException(message, faultInfo, cause); + } + } + } + } + } + return ex; + } + + /** + * Populate the java exception from the fault bean + * @param ex + * @param faultBean + * @throws Exception + */ + private void populateException(Throwable ex, Object faultBean) throws Exception { + PropertyDescriptor props[] = Introspector.getBeanInfo(faultBean.getClass()).getPropertyDescriptors(); + for (PropertyDescriptor p : props) { + Method getter = p.getReadMethod(); + Method setter = p.getWriteMethod(); + if (getter == null || setter == null) { + continue; + } + try { + Method m = ex.getClass().getMethod(setter.getName(), setter.getParameterTypes()); + Object pv = getter.invoke(faultBean); + m.invoke(ex, pv); + } catch (Exception e) { + // Ignore; + } + } + } + public Object getFaultInfo(Throwable exception, Class faultBeanClass) { if (exception == null) { return null; @@ -162,21 +229,13 @@ if (!isMappedGetter(name)) { continue; } - String prefix = "get"; - if (name.startsWith("get")) { - prefix = "get"; - } else if (name.startsWith("is")) { - prefix = "is"; - } Method setter = null; try { - setter = - faultBeanClass.getMethod("set" + name.substring(prefix.length()), new Class[] {getter - .getReturnType()}); + setter = faultBeanClass.getMethod("set" + capitalize(pd.getName()), getter.getReturnType()); } catch (NoSuchMethodException e) { continue; } - Object prop = setter.invoke(faultBean, getter.invoke(exception, (Object[])null)); + Object prop = getter.invoke(exception); setter.invoke(faultBean, prop); } return faultBean; @@ -186,34 +245,37 @@ } @SuppressWarnings("unchecked") - public boolean introspectFaultDataType(DataType exceptionType) { + public boolean introspectFaultDataType(DataType exceptionType, final boolean generatingFaultBean) { QName faultName = null; boolean result = false; - Class cls = exceptionType.getPhysical(); + final Class cls = exceptionType.getPhysical(); if (cls == FaultException.class) { return true; } DataType faultType = (DataType)exceptionType.getLogical(); Class faultBean = null; - WebFault fault = cls.getAnnotation(WebFault.class); + final WebFault fault = cls.getAnnotation(WebFault.class); if (fault != null) { if (!"".equals(fault.name()) || !"".equals(fault.targetNamespace())) { - QName faultQName = ((XMLType)faultType.getLogical()).getElementName(); - String faultNS = "".equals(fault.targetNamespace()) ? - faultQName.getNamespaceURI() : fault.targetNamespace(); - String faultLocal = "".equals(fault.name()) ? - faultQName.getLocalPart() : fault.name(); + QName faultQName = ((XMLType)faultType.getLogical()).getElementName(); + String faultNS = + "".equals(fault.targetNamespace()) ? faultQName.getNamespaceURI() : fault.targetNamespace(); + String faultLocal = "".equals(fault.name()) ? faultQName.getLocalPart() : fault.name(); faultName = new QName(faultNS, faultLocal); XMLType xmlType = new XMLType(faultName, null); faultType.setLogical(xmlType); } if (!"".equals(fault.faultBean())) { - try { - faultBean = Class.forName(fault.faultBean(), false, cls.getClassLoader()); - } catch (ClassNotFoundException e) { - throw new ServiceRuntimeException(e); - } + faultBean = AccessController.doPrivileged(new PrivilegedAction>() { + public Class run() { + try { + return Class.forName(fault.faultBean(), false, cls.getClassLoader()); + } catch (ClassNotFoundException e) { + throw new ServiceRuntimeException(e); + } + } + }); } else { Method m; try { @@ -226,20 +288,38 @@ } if (faultBean == null) { - String faultBeanClassName = cls.getPackage().getName() + ".jaxws." + cls.getSimpleName() + "Bean"; - try { - faultBean = Class.forName(faultBeanClassName, false, cls.getClassLoader()); - } catch (ClassNotFoundException e) { - faultBean = cls; - } + final String faultBeanClassName = cls.getPackage().getName() + ".jaxws." + cls.getSimpleName() + "Bean"; + final QName qname = faultName; + faultType = AccessController.doPrivileged(new PrivilegedAction>() { + public DataType run() { + try { + Class faultBean = Class.forName(faultBeanClassName, false, cls.getClassLoader()); + return new DataTypeImpl(faultBean, new XMLType(qname, qname)); + } catch (ClassNotFoundException e) { + if (generatingFaultBean) { + Class t = (Class)cls; + GeneratedClassLoader cl = new GeneratedClassLoader(t.getClassLoader()); + GeneratedDataTypeImpl dt = new GeneratedDataTypeImpl(t, cl); + return dt; + } else { + return new DataTypeImpl(cls, new XMLType(qname, qname)); + } + } + } + }); + } else { + faultType.setDataBinding(null); + faultType.setGenericType(faultBean); + faultType.setPhysical(faultBean); } - faultType.setPhysical(faultBean); // TODO: Use the databinding framework to introspect the fault bean class - if (dataBindingExtensionPoint != null) { + if (faultType.getDataBinding() == null && dataBindingExtensionPoint != null) { + faultBean = faultType.getPhysical(); result = dataBindingExtensionPoint.introspectType(faultType, null, Throwable.class.isAssignableFrom(faultBean)); } + ((DataType) exceptionType).setLogical(faultType); /* The introspection of the fault DT may not have calculated the correct element name, @@ -257,8 +337,7 @@ } public static boolean isMappedGetter(String methodName) { - if (GETCAUSE.equals(methodName) - || GETLOCALIZEDMESSAGE.equals(methodName) + if (GETCAUSE.equals(methodName) || GETLOCALIZEDMESSAGE.equals(methodName) || GETSTACKTRACE.equals(methodName) || GETCLASS.equals(methodName)) { return false; @@ -267,6 +346,14 @@ } } + private static String capitalize(String name) { + if (name == null || name.length() == 0) { + return name; + } else { + return Character.toUpperCase(name.charAt(0)) + name.substring(1); + } + } + public void setDataBindingExtensionPoint(DataBindingExtensionPoint dataBindingExtensionPoint) { this.dataBindingExtensionPoint = dataBindingExtensionPoint; } Modified: incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/JAXWSJavaInterfaceProcessor.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/JAXWSJavaInterfaceProcessor.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/JAXWSJavaInterfaceProcessor.java (original) +++ incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/JAXWSJavaInterfaceProcessor.java Tue Jun 3 18:04:18 2008 @@ -23,8 +23,7 @@ import java.lang.reflect.Method; import java.lang.reflect.Modifier; import java.security.AccessController; -import java.security.PrivilegedActionException; -import java.security.PrivilegedExceptionAction; +import java.security.PrivilegedAction; import java.util.ArrayList; import java.util.Iterator; import java.util.List; @@ -77,7 +76,7 @@ public JAXWSJavaInterfaceProcessor() { super(); } - + private static String capitalize(String name) { if (name == null || name.length() == 0) { return name; @@ -108,7 +107,7 @@ for (Iterator it = contract.getOperations().iterator(); it.hasNext();) { JavaOperation operation = (JavaOperation)it.next(); - Method method = operation.getJavaMethod(); + final Method method = operation.getJavaMethod(); introspectFaultTypes(operation); // SOAP binding (doc/lit/wrapped|bare or rpc/lit) @@ -186,18 +185,29 @@ if ("".equals(wrapperBeanName)) { wrapperBeanName = clazz.getPackage().getName() + ".jaxws." + capitalize(method.getName()); } - Class inputWrapperClass = null; - try { - final String className = wrapperBeanName; - inputWrapperClass = AccessController.doPrivileged(new PrivilegedExceptionAction>() { - public Class run() throws ClassNotFoundException { - return Class.forName(className, false, clazz.getClassLoader()); + + DataType inputWrapperDT = null; + + final String inputWrapperClassName = wrapperBeanName; + final String inputNS = ns; + final String inputName = name; + inputWrapperDT = AccessController.doPrivileged(new PrivilegedAction>() { + public DataType run() { + try { + Class wrapperClass = Class.forName(inputWrapperClassName, false, clazz.getClassLoader()); + QName qname = new QName(inputNS, inputName); + DataType dt = new DataTypeImpl(wrapperClass, new XMLType(qname, qname)); + dataBindingExtensionPoint.introspectType(dt, null); + return dt; + } catch (ClassNotFoundException e) { + GeneratedClassLoader cl = new GeneratedClassLoader(clazz.getClassLoader()); + return new GeneratedDataTypeImpl(method, inputWrapperClassName, inputNS, inputName, true, + cl); } - }); - } catch (PrivilegedActionException e) { - // Ignore - } - QName inputWrapper = new QName(ns, name); + } + }); + + QName inputWrapper = inputWrapperDT.getLogical().getElementName(); ResponseWrapper responseWrapper = method.getAnnotation(ResponseWrapper.class); ns = responseWrapper == null ? tns : getValue(responseWrapper.targetNamespace(), tns); @@ -209,18 +219,29 @@ wrapperBeanName = clazz.getPackage().getName() + ".jaxws." + capitalize(method.getName()) + "Response"; } - Class outputWrapperClass = null; - try { - final String className = wrapperBeanName; - outputWrapperClass = AccessController.doPrivileged(new PrivilegedExceptionAction>() { - public Class run() throws ClassNotFoundException { - return Class.forName(className, false, clazz.getClassLoader()); + + DataType outputWrapperDT = null; + final String outputWrapperClassName = wrapperBeanName; + final String outputNS = ns; + final String outputName = name; + + outputWrapperDT = AccessController.doPrivileged(new PrivilegedAction>() { + public DataType run() { + try { + Class wrapperClass = + Class.forName(outputWrapperClassName, false, clazz.getClassLoader()); + QName qname = new QName(inputNS, inputName); + DataType dt = new DataTypeImpl(wrapperClass, new XMLType(qname, qname)); + dataBindingExtensionPoint.introspectType(dt, null); + return dt; + } catch (ClassNotFoundException e) { + GeneratedClassLoader cl = new GeneratedClassLoader(clazz.getClassLoader()); + return new GeneratedDataTypeImpl(method, outputWrapperClassName, outputNS, outputName, + false, cl); } - }); - } catch (PrivilegedActionException e) { - // Ignore - } - QName outputWrapper = new QName(ns, name); + } + }); + QName outputWrapper = outputWrapperDT.getLogical().getElementName(); List inputElements = new ArrayList(); for (int i = 0; i < method.getParameterTypes().length; i++) { @@ -255,11 +276,14 @@ outputElements.add(new ElementInfo(element, null)); } + String db = inputWrapperDT != null ? inputWrapperDT.getDataBinding() : JAXB_DATABINDING; WrapperInfo wrapperInfo = - new WrapperInfo(JAXB_DATABINDING, new ElementInfo(inputWrapper, null), - new ElementInfo(outputWrapper, null), inputElements, outputElements); - wrapperInfo.setInputWrapperClass(inputWrapperClass); - wrapperInfo.setOutputWrapperClass(outputWrapperClass); + new WrapperInfo(db, new ElementInfo(inputWrapper, null), new ElementInfo(outputWrapper, null), + inputElements, outputElements); + + wrapperInfo.setInputWrapperType(inputWrapperDT); + wrapperInfo.setOutputWrapperType(outputWrapperDT); + operation.setWrapper(wrapperInfo); } } @@ -267,9 +291,9 @@ @SuppressWarnings("unchecked") private void introspectFaultTypes(Operation operation) { - if (operation!= null && operation.getFaultTypes() != null) { + if (operation != null && operation.getFaultTypes() != null) { for (DataType exceptionType : operation.getFaultTypes()) { - faultExceptionMapper.introspectFaultDataType(exceptionType); + faultExceptionMapper.introspectFaultDataType(exceptionType, true); DataType faultType = (DataType)exceptionType.getLogical(); if (faultType.getDataBinding() == JavaExceptionDataBinding.NAME) { // The exception class doesn't have an associated bean class, so @@ -285,8 +309,7 @@ QName faultBeanName = ((XMLType)faultType.getLogical()).getElementName(); List> beanDataTypes = new ArrayList>(); for (Method aMethod : exceptionType.getPhysical().getMethods()) { - if (Modifier.isPublic(aMethod.getModifiers()) - && aMethod.getName().startsWith(GET) + if (Modifier.isPublic(aMethod.getModifiers()) && aMethod.getName().startsWith(GET) && aMethod.getParameterTypes().length == 0 && JAXWSFaultExceptionMapper.isMappedGetter(aMethod.getName())) { String propName = resolvePropertyFromMethod(aMethod.getName()); @@ -304,11 +327,10 @@ // sort the list lexicographically as specified in JAX-WS spec section 3.7 int i = 0; for (; i < beanDataTypes.size(); i++) { - if (beanDataTypes.get(i).getLogical().getElementName() - .getLocalPart().compareTo(propName) > 0) { + if (beanDataTypes.get(i).getLogical().getElementName().getLocalPart().compareTo(propName) > 0) { break; } - } + } beanDataTypes.add(i, propDT); } } Modified: incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/WrapperBeanGenerator.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/WrapperBeanGenerator.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/WrapperBeanGenerator.java (original) +++ incubator/tuscany/java/sca/modules/interface-java-jaxws/src/main/java/org/apache/tuscany/sca/interfacedef/java/jaxws/WrapperBeanGenerator.java Tue Jun 3 18:04:18 2008 @@ -25,69 +25,146 @@ import java.util.List; import org.apache.tuscany.sca.interfacedef.java.impl.JavaInterfaceUtil; -import org.objectweb.asm.ClassWriter; public class WrapperBeanGenerator extends BaseBeanGenerator { - public List> generateWrapperBeans(Class sei) { + GeneratedClassLoader cl = new GeneratedClassLoader(sei.getClassLoader()); List> classes = new ArrayList>(); for (Method m : sei.getMethods()) { if (m.getDeclaringClass() == Object.class) { continue; } - classes.add(generateRequestWrapper(sei, m)); - classes.add(generateResponseWrapper(sei, m)); + classes.add(generateRequestWrapper(sei, m, cl)); + classes.add(generateResponseWrapper(sei, m, cl)); } return classes; } - private Class generateRequestWrapper(Class sei, Method m) { + public Class generateRequestWrapper(Class sei, Method m, GeneratedClassLoader cl) { String wrapperNamespace = JavaInterfaceUtil.getNamespace(sei); + String wrapperName = m.getName(); + String wrapperBeanName = capitalize(wrapperName); + String wrapperClassName = sei.getPackage().getName() + ".jaxws." + wrapperBeanName; + + return generateRequestWrapper(m, wrapperClassName, wrapperNamespace, wrapperName, cl); + } + + public Class generateRequestWrapper(Method m, + String wrapperClassName, + String wrapperNamespace, + String wrapperName, + GeneratedClassLoader cl) { + synchronized (m.getDeclaringClass()) { + MethodKey key = new MethodKey(m, true); + Class wrapperClass = generatedClasses.get(key); + if (wrapperClass == null) { + String wrapperClassDescriptor = wrapperClassName.replace('.', '/'); + String wrapperClassSignature = "L" + wrapperClassDescriptor + ";"; + + Class[] paramTypes = m.getParameterTypes(); + Type[] genericParamTypes = m.getGenericParameterTypes(); + BeanProperty[] properties = new BeanProperty[paramTypes.length]; + for (int i = 0; i < paramTypes.length; i++) { + String propName = "arg" + i; + properties[i] = new BeanProperty(propName, paramTypes[i], genericParamTypes[i]); + } + + wrapperClass = + generate(wrapperClassDescriptor, + wrapperClassSignature, + wrapperNamespace, + wrapperName, + properties, + cl); + generatedClasses.put(key, wrapperClass); + } + return wrapperClass; - ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); - String wrapperName = capitalize(m.getName()); - String wrapperClassName = sei.getPackage().getName() + ".jaxws." + wrapperName; - String wrapperClassDescriptor = wrapperClassName.replace('.', '/'); - String wrapperClassSignature = "L" + wrapperClassDescriptor + ";"; - - Class[] paramTypes = m.getParameterTypes(); - Type[] genericParamTypes = m.getGenericParameterTypes(); - BeanProperty[] properties = new BeanProperty[paramTypes.length]; - for (int i = 0; i < paramTypes.length; i++) { - String propName = "arg" + i; - properties[i] = new BeanProperty(propName, paramTypes[i], genericParamTypes[i]); - } - - defineClass(cw, wrapperClassDescriptor, wrapperClassSignature, wrapperNamespace, m.getName(), properties); - GeneratedClassLoader cl = - new GeneratedClassLoader(sei.getClassLoader()); - Class generated = cl.getGeneratedClass(wrapperClassName, cw.toByteArray()); - return generated; + } } - private Class generateResponseWrapper(Class sei, Method m) { + public Class generateResponseWrapper(Class sei, Method m, GeneratedClassLoader cl) { String wrapperNamespace = JavaInterfaceUtil.getNamespace(sei); - ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); - String wrapperName = capitalize(m.getName()) + "Response"; - String wrapperClassName = sei.getPackage().getName() + ".jaxws." + wrapperName; - String wrapperClassDescriptor = wrapperClassName.replace('.', '/'); - String wrapperClassSignature = "L" + wrapperClassDescriptor + ";"; - - Class returnType = m.getReturnType(); - BeanProperty[] properties = null; - if (returnType != void.class) { - Type genericReturnType = m.getGenericReturnType(); - String propName = "return"; - properties = new BeanProperty[] {new BeanProperty(propName, returnType, genericReturnType)}; - } - byte[] byteCode = defineClass(cw, wrapperClassDescriptor, wrapperClassSignature, wrapperNamespace, m.getName() + "Response", properties); - GeneratedClassLoader cl = - new GeneratedClassLoader(sei.getClassLoader()); - Class generated = cl.getGeneratedClass(wrapperClassName, byteCode); - return generated; + String wrapperName = m.getName() + "Response"; + String wrapperBeanName = capitalize(wrapperName); + String wrapperClassName = sei.getPackage().getName() + ".jaxws." + wrapperBeanName; + return generateResponseWrapper(m, wrapperClassName, wrapperNamespace, wrapperName, cl); + + } + + public Class generateResponseWrapper(Method m, + String wrapperClassName, + String wrapperNamespace, + String wrapperName, + GeneratedClassLoader cl) { + synchronized (m.getDeclaringClass()) { + MethodKey key = new MethodKey(m, false); + Class wrapperClass = generatedClasses.get(key); + if (wrapperClass == null) { + String wrapperClassDescriptor = wrapperClassName.replace('.', '/'); + String wrapperClassSignature = "L" + wrapperClassDescriptor + ";"; + + Class returnType = m.getReturnType(); + BeanProperty[] properties = null; + if (returnType != void.class) { + Type genericReturnType = m.getGenericReturnType(); + String propName = "return"; + properties = new BeanProperty[] {new BeanProperty(propName, returnType, genericReturnType)}; + } + wrapperClass = + generate(wrapperClassDescriptor, + wrapperClassSignature, + wrapperNamespace, + wrapperName, + properties, + cl); + generatedClasses.put(key, wrapperClass); + } + return wrapperClass; + + } + } + + private static class MethodKey { + private Method m; + private boolean request; + + @Override + public int hashCode() { + final int prime = 31; + int result = 1; + result = prime * result + ((m == null) ? 0 : m.hashCode()); + result = prime * result + (request ? 1231 : 1237); + return result; + } + + @Override + public boolean equals(Object obj) { + if (this == obj) + return true; + if (obj == null) + return false; + if (getClass() != obj.getClass()) + return false; + final MethodKey other = (MethodKey)obj; + if (m == null) { + if (other.m != null) + return false; + } else if (!m.equals(other.m)) + return false; + if (request != other.request) + return false; + return true; + } + + public MethodKey(Method m, boolean request) { + super(); + this.m = m; + this.request = request; + } } } Modified: incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/FaultBeanGeneratorTestCase.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/FaultBeanGeneratorTestCase.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/FaultBeanGeneratorTestCase.java (original) +++ incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/FaultBeanGeneratorTestCase.java Tue Jun 3 18:04:18 2008 @@ -38,7 +38,7 @@ */ public class FaultBeanGeneratorTestCase extends TestCase { public void testGenerate() throws IOException { - byte[] content = FaultBeanGenerator.generateFaultBeanClassRep(MyException.class); + byte[] content = new FaultBeanGenerator().generate(MyException.class); ClassReader cr = new ClassReader(content); PrintWriter pw = new PrintWriter(System.out); CheckClassAdapter.verify(cr, false, pw); @@ -47,11 +47,11 @@ public void testGenerateClass() throws Exception { Class cls = FaultBeanGenerator.generateFaultBeanClass(MyException.class); Assert.assertEquals("org.apache.tuscany.sca.interfacedef.java.jaxws.jaxws.MyExceptionBean", cls.getName()); - for(Annotation a: cls.getAnnotations()) { + for (Annotation a : cls.getAnnotations()) { System.out.println(a); } -// XmlType xmlType = cls.getAnnotation(XmlType.class); -// System.out.println(xmlType); + // XmlType xmlType = cls.getAnnotation(XmlType.class); + // System.out.println(xmlType); Object bean = cls.newInstance(); JAXBContext context = JAXBContextHelper.createJAXBContext(cls); StringWriter sw = new StringWriter(); Modified: incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/TestInterface.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/TestInterface.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/TestInterface.java (original) +++ incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/TestInterface.java Tue Jun 3 18:04:18 2008 @@ -19,15 +19,36 @@ package org.apache.tuscany.sca.interfacedef.java.jaxws; +import java.util.ArrayList; +import java.util.HashMap; import java.util.List; +import org.osoa.sca.annotations.Remotable; + /** * @version $Rev$ $Date$ */ +@Remotable public interface TestInterface { int convert(String currency1, String currency2); + List getRates(String currency); + void check(boolean flag); + String[] list(int[] list); + int[][] map(String[][] strs); + + String getGreetings(String name); + + String[] getGreetingsArray(String[] names); + + List getGreetingsList(List names); + + ArrayList getGreetingsArrayList(ArrayList names); + + // Map getGreetingsMap(Map namesMap); + + HashMap getGreetingsHashMap(HashMap namesMap); } Modified: incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/WrapperBeanGeneratorTestCase.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/WrapperBeanGeneratorTestCase.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/WrapperBeanGeneratorTestCase.java (original) +++ incubator/tuscany/java/sca/modules/interface-java-jaxws/src/test/java/org/apache/tuscany/sca/interfacedef/java/jaxws/WrapperBeanGeneratorTestCase.java Tue Jun 3 18:04:18 2008 @@ -27,11 +27,9 @@ import java.util.Map; import javax.xml.bind.JAXBContext; -import javax.xml.transform.dom.DOMResult; import org.apache.tuscany.sca.databinding.jaxb.JAXBContextHelper; import org.apache.tuscany.sca.databinding.jaxb.JAXBTypeHelper; -import org.apache.tuscany.sca.databinding.xml.Node2String; import org.junit.Test; /** @@ -66,10 +64,9 @@ public void testGenerateSchema() throws Exception { List> classes = new WrapperBeanGenerator().generateWrapperBeans(TestInterface.class); JAXBContext context = JAXBContext.newInstance(classes.toArray(new Class[0])); - Map results = JAXBTypeHelper.generateSchema(context); - Node2String t = new Node2String(); - for (DOMResult d : results.values()) { - System.out.println(t.transform(d.getNode(), null)); + Map results = JAXBTypeHelper.generateSchema(context); + for (String xsd : results.values()) { + System.out.println(xsd); } } } Modified: incubator/tuscany/java/sca/modules/interface-wsdl-java2wsdl/src/main/java/org/apache/tuscany/sca/interfacedef/wsdl/interface2wsdl/Interface2WSDLGenerator.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface-wsdl-java2wsdl/src/main/java/org/apache/tuscany/sca/interfacedef/wsdl/interface2wsdl/Interface2WSDLGenerator.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface-wsdl-java2wsdl/src/main/java/org/apache/tuscany/sca/interfacedef/wsdl/interface2wsdl/Interface2WSDLGenerator.java (original) +++ incubator/tuscany/java/sca/modules/interface-wsdl-java2wsdl/src/main/java/org/apache/tuscany/sca/interfacedef/wsdl/interface2wsdl/Interface2WSDLGenerator.java Tue Jun 3 18:04:18 2008 @@ -278,7 +278,7 @@ return definition; } - + private static void loadXSD(XmlSchemaCollection schemaCollection, XSDefinition definition) { if (definition.getSchema() != null) { return; @@ -462,6 +462,17 @@ part.setElementName(wrapperName); wrappers.put(wrapperName, elements); + // FIXME: [rfeng] Ideally, we should try to register the wrappers only. But we are + // expriencing the problem that we cannot handle XSD imports + /* + Class wrapperClass = input ? opWrapper.getInputWrapperClass() : opWrapper.getOutputWrapperClass(); + DataType wrapperDT = input ? opWrapper.getInputWrapperType() : opWrapper.getOutputWrapperType(); + if (wrapperClass != null) { + getElementInfo(wrapperClass, wrapperDT, wrapperName, helpers); + return part; + } + */ + Method method = ((JavaOperation)operation).getJavaMethod(); if (input) { Class[] paramTypes = method.getParameterTypes(); @@ -489,13 +500,18 @@ dataType = (DataType)dataType.getLogical(); db = dataType.getDataBinding(); } - DataBinding dataBinding = dataBindings.getDataBinding(db); - if (dataBinding == null) { - throw new RuntimeException("no data binding for " + db); - } - XMLTypeHelper helper = dataBinding.getXMLTypeHelper(); + XMLTypeHelper helper = helpers.get(db); if (helper == null) { - helper = new JAXBTypeHelper(); + DataBinding dataBinding = dataBindings.getDataBinding(db); + if (dataBinding == null) { + throw new RuntimeException("no data binding for " + db); + } + + helper = dataBinding.getXMLTypeHelper(); + if (helper == null) { + helper = new JAXBTypeHelper(); + } + helpers.put(db, helper); } TypeInfo typeInfo = helper.getTypeInfo(javaType.isArray() ? javaType.getComponentType() : javaType, dataType.getLogical()); Modified: incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/FaultExceptionMapper.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/FaultExceptionMapper.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/FaultExceptionMapper.java (original) +++ incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/FaultExceptionMapper.java Tue Jun 3 18:04:18 2008 @@ -32,9 +32,10 @@ * type * * @param exceptionDataType The data type representing a java exception class + * @param generatingFaultBean If JAXWS Section 3.7 Fault Bean will be generated * @return true if the introspection can recognize the exception data type */ - boolean introspectFaultDataType(DataType exceptionDataType); + boolean introspectFaultDataType(DataType exceptionDataType, boolean generatingFaultBean); /** * Create a java exception to wrap the fault data Modified: incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/ElementInfo.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/ElementInfo.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/ElementInfo.java (original) +++ incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/ElementInfo.java Tue Jun 3 18:04:18 2008 @@ -78,4 +78,37 @@ public void setNillable(boolean nillable) { this.nillable = nillable; } + + @Override + public int hashCode() { + final int prime = 31; + int result = 1; + result = prime * result + ((name == null) ? 0 : name.hashCode()); + result = prime * result + ((type == null) ? 0 : type.hashCode()); + return result; + } + + @Override + public boolean equals(Object obj) { + if (this == obj) + return true; + if (obj == null) + return false; + if (getClass() != obj.getClass()) + return false; + final ElementInfo other = (ElementInfo)obj; + if (name == null) { + if (other.name != null) + return false; + } else if (!name.equals(other.name)) + return false; + /* + if (type == null) { + if (other.type != null) + return false; + } else if (!type.equals(other.type)) + return false; + */ + return true; + } } Modified: incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/TypeInfo.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/TypeInfo.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/TypeInfo.java (original) +++ incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/TypeInfo.java Tue Jun 3 18:04:18 2008 @@ -72,4 +72,29 @@ return sb.toString(); } + @Override + public int hashCode() { + final int prime = 31; + int result = 1; + result = prime * result + ((name == null) ? 0 : name.hashCode()); + return result; + } + + @Override + public boolean equals(Object obj) { + if (this == obj) + return true; + if (obj == null) + return false; + if (getClass() != obj.getClass()) + return false; + final TypeInfo other = (TypeInfo)obj; + if (name == null) { + if (other.name != null) + return false; + } else if (!name.equals(other.name)) + return false; + return true; + } + } Modified: incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/WrapperInfo.java URL: http://svn.apache.org/viewvc/incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/WrapperInfo.java?rev=662937&r1=662936&r2=662937&view=diff ============================================================================== --- incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/WrapperInfo.java (original) +++ incubator/tuscany/java/sca/modules/interface/src/main/java/org/apache/tuscany/sca/interfacedef/util/WrapperInfo.java Tue Jun 3 18:04:18 2008 @@ -64,15 +64,12 @@ // The data for the input/output wrappers private String dataBinding; - + // The data type for the input (request) wrapper bean private DataType inputWrapperType; // The data type for the output (response) wrapper bean private DataType outputWrapperType; - - private Class inputWrapperClass; - private Class outputWrapperClass; - + public WrapperInfo(String dataBinding, ElementInfo inputWrapperElement, ElementInfo outputWrapperElement, @@ -160,19 +157,11 @@ } public Class getInputWrapperClass() { - return inputWrapperClass; - } - - public void setInputWrapperClass(Class inputWrapperClass) { - this.inputWrapperClass = inputWrapperClass; + return inputWrapperType == null ? null : inputWrapperType.getPhysical(); } public Class getOutputWrapperClass() { - return outputWrapperClass; - } - - public void setOutputWrapperClass(Class outputWrapperClass) { - this.outputWrapperClass = outputWrapperClass; + return outputWrapperType == null ? null : outputWrapperType.getPhysical(); } public String getDataBinding() {