diff --git a/archetype/src/main/resources/archetype-resources/pom.xml b/archetype/src/main/resources/archetype-resources/pom.xml
index ec5d04be..df6b65a4 100644
--- a/archetype/src/main/resources/archetype-resources/pom.xml
+++ b/archetype/src/main/resources/archetype-resources/pom.xml
@@ -15,12 +15,12 @@
Marshaller interface for JAXB 2.0.
*
Marshaller.Listener to be registered with the JAXB Marshaller. */
+ /**
+ * Sets the Marshaller.Listener to be registered with the JAXB Marshaller.
+ */
public void setMarshallerListener(Marshaller.Listener marshallerListener) {
this.marshallerListener = marshallerListener;
}
@@ -152,17 +148,23 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
this.schemaLanguage = schemaLanguage;
}
- /** Sets the schema resource to use for validation. */
+ /**
+ * Sets the schema resource to use for validation.
+ */
public void setSchema(Resource schemaResource) {
schemaResources = new Resource[]{schemaResource};
}
- /** Sets the schema resources to use for validation. */
+ /**
+ * Sets the schema resources to use for validation.
+ */
public void setSchemas(Resource[] schemaResources) {
this.schemaResources = schemaResources;
}
- /** Sets the Unmarshaller.Listener to be registered with the JAXB Unmarshaller. */
+ /**
+ * Sets the Unmarshaller.Listener to be registered with the JAXB Unmarshaller.
+ */
public void setUnmarshallerListener(Unmarshaller.Listener unmarshallerListener) {
this.unmarshallerListener = unmarshallerListener;
}
@@ -170,27 +172,58 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
public boolean supports(Type type) {
if (type instanceof Class) {
return supportsInternal((Class) type, true);
- }
- else if (type instanceof ParameterizedType) {
+ } else if (type instanceof ParameterizedType) {
ParameterizedType parameterizedType = (ParameterizedType) type;
if (JAXBElement.class.equals(parameterizedType.getRawType())) {
- Type[] typeArguments = parameterizedType.getActualTypeArguments();
- for (int i = 0; i < typeArguments.length; i++) {
- if (typeArguments[i] instanceof Class) {
- if (!supportsInternal((Class) typeArguments[i], false)) {
- return false;
- }
- }
- else if (!supports(typeArguments[i])) {
+ Assert.isTrue(parameterizedType.getActualTypeArguments().length == 1,
+ "Invalid amount of parameterized types in JAXBElement");
+ Type typeArgument = parameterizedType.getActualTypeArguments()[0];
+ if (typeArgument instanceof Class) {
+ Class clazz = (Class) typeArgument;
+ if (!isPrimitiveType(clazz) && !isStandardType(clazz) && !supportsInternal(clazz, false)) {
return false;
}
}
+ else if (typeArgument instanceof GenericArrayType) {
+ GenericArrayType genericArrayType = (GenericArrayType) typeArgument;
+ return genericArrayType.getGenericComponentType().equals(Byte.TYPE);
+ } else if (!supports(typeArgument)) {
+ return false;
+ }
return true;
}
}
return false;
}
+ private boolean isPrimitiveType(Class clazz) {
+ return (Boolean.class.equals(clazz) ||
+ Byte.class.equals(clazz) ||
+ Short.class.equals(clazz) ||
+ Integer.class.equals(clazz) ||
+ Long.class.equals(clazz) ||
+ Float.class.equals(clazz) ||
+ Double.class.equals(clazz) ||
+ byte[].class.equals(clazz));
+ }
+
+ private boolean isStandardType(Class clazz) {
+ return (String.class.equals(clazz) ||
+ BigInteger.class.equals(clazz) ||
+ BigDecimal.class.equals(clazz) ||
+ Calendar.class.isAssignableFrom(clazz) ||
+ Date.class.isAssignableFrom(clazz) ||
+ QName.class.equals(clazz) ||
+ URI.class.equals(clazz) ||
+ XMLGregorianCalendar.class.isAssignableFrom(clazz) ||
+ Duration.class.isAssignableFrom(clazz) ||
+ Object.class.equals(clazz) ||
+ Image.class.isAssignableFrom(clazz) ||
+ DataHandler.class.equals(clazz) ||
+ Source.class.isAssignableFrom(clazz) ||
+ UUID.class.equals(clazz));
+ }
+
public boolean supports(Class clazz) {
return supportsInternal(clazz, true);
}
@@ -216,8 +249,7 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
}
}
return false;
- }
- else if (!ObjectUtils.isEmpty(classesToBeBound)) {
+ } else if (!ObjectUtils.isEmpty(classesToBeBound)) {
return Arrays.asList(classesToBeBound).contains(clazz);
}
return false;
@@ -244,11 +276,9 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
}
if (StringUtils.hasLength(getContextPath())) {
return createJaxbContextFromContextPath();
- }
- else if (!ObjectUtils.isEmpty(classesToBeBound)) {
+ } else if (!ObjectUtils.isEmpty(classesToBeBound)) {
return createJaxbContextFromClasses();
- }
- else {
+ } else {
throw new IllegalArgumentException("setting either contextPath or classesToBeBound is required");
}
}
@@ -260,8 +290,7 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
if (jaxbContextProperties != null) {
return JAXBContext
.newInstance(getContextPath(), ClassUtils.getDefaultClassLoader(), jaxbContextProperties);
- }
- else {
+ } else {
return JAXBContext.newInstance(getContextPath());
}
}
@@ -273,8 +302,7 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
}
if (jaxbContextProperties != null) {
return JAXBContext.newInstance(classesToBeBound, jaxbContextProperties);
- }
- else {
+ } else {
return JAXBContext.newInstance(classesToBeBound);
}
}
@@ -327,8 +355,7 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
}
if (result instanceof StaxResult) {
marshalStaxResult(marshaller, graph, (StaxResult) result);
- }
- else {
+ } else {
marshaller.marshal(graph, result);
}
}
@@ -341,11 +368,9 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
throws JAXBException {
if (staxResult.getXMLStreamWriter() != null) {
jaxbMarshaller.marshal(graph, staxResult.getXMLStreamWriter());
- }
- else if (staxResult.getXMLEventWriter() != null) {
+ } else if (staxResult.getXMLEventWriter() != null) {
jaxbMarshaller.marshal(graph, staxResult.getXMLEventWriter());
- }
- else {
+ } else {
throw new IllegalArgumentException("StaxResult contains neither XMLStreamWriter nor XMLEventConsumer");
}
}
@@ -366,8 +391,7 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
}
if (source instanceof StaxSource) {
return unmarshalStaxSource(unmarshaller, (StaxSource) source);
- }
- else {
+ } else {
return unmarshaller.unmarshal(source);
}
}
@@ -379,11 +403,9 @@ public class Jaxb2Marshaller extends AbstractJaxbMarshaller
private Object unmarshalStaxSource(Unmarshaller jaxbUnmarshaller, StaxSource staxSource) throws JAXBException {
if (staxSource.getXMLStreamReader() != null) {
return jaxbUnmarshaller.unmarshal(staxSource.getXMLStreamReader());
- }
- else if (staxSource.getXMLEventReader() != null) {
+ } else if (staxSource.getXMLEventReader() != null) {
return jaxbUnmarshaller.unmarshal(staxSource.getXMLEventReader());
- }
- else {
+ } else {
throw new IllegalArgumentException("StaxSource contains neither XMLStreamReader nor XMLEventReader");
}
}
diff --git a/oxm-tiger/src/test/java/org/springframework/oxm/jaxb/Jaxb2MarshallerTest.java b/oxm-tiger/src/test/java/org/springframework/oxm/jaxb/Jaxb2MarshallerTest.java
index 5560c86e..fdae544d 100644
--- a/oxm-tiger/src/test/java/org/springframework/oxm/jaxb/Jaxb2MarshallerTest.java
+++ b/oxm-tiger/src/test/java/org/springframework/oxm/jaxb/Jaxb2MarshallerTest.java
@@ -16,24 +16,6 @@
package org.springframework.oxm.jaxb;
-import java.io.ByteArrayOutputStream;
-import java.io.StringWriter;
-import java.lang.reflect.Method;
-import java.util.Collections;
-import javax.activation.DataHandler;
-import javax.activation.FileDataSource;
-import javax.xml.bind.JAXBElement;
-import javax.xml.namespace.QName;
-import javax.xml.parsers.DocumentBuilder;
-import javax.xml.parsers.DocumentBuilderFactory;
-import javax.xml.stream.XMLEventWriter;
-import javax.xml.stream.XMLOutputFactory;
-import javax.xml.stream.XMLStreamWriter;
-import javax.xml.transform.Result;
-import javax.xml.transform.dom.DOMResult;
-import javax.xml.transform.sax.SAXResult;
-import javax.xml.transform.stream.StreamResult;
-
import org.custommonkey.xmlunit.XMLTestCase;
import static org.easymock.EasyMock.*;
import org.springframework.core.io.ClassPathResource;
@@ -53,6 +35,36 @@ import org.xml.sax.Attributes;
import org.xml.sax.ContentHandler;
import org.xml.sax.Locator;
+import javax.activation.DataHandler;
+import javax.activation.FileDataSource;
+import javax.xml.bind.JAXBElement;
+import javax.xml.datatype.Duration;
+import javax.xml.datatype.XMLGregorianCalendar;
+import javax.xml.namespace.QName;
+import javax.xml.parsers.DocumentBuilder;
+import javax.xml.parsers.DocumentBuilderFactory;
+import javax.xml.stream.XMLEventWriter;
+import javax.xml.stream.XMLOutputFactory;
+import javax.xml.stream.XMLStreamWriter;
+import javax.xml.transform.Result;
+import javax.xml.transform.Source;
+import javax.xml.transform.dom.DOMResult;
+import javax.xml.transform.sax.SAXResult;
+import javax.xml.transform.stream.StreamResult;
+import java.awt.*;
+import java.io.ByteArrayOutputStream;
+import java.io.StringWriter;
+import java.lang.reflect.Method;
+import java.lang.reflect.ParameterizedType;
+import java.lang.reflect.Type;
+import java.math.BigDecimal;
+import java.math.BigInteger;
+import java.net.URI;
+import java.util.Calendar;
+import java.util.Collections;
+import java.util.Date;
+import java.util.UUID;
+
public class Jaxb2MarshallerTest extends XMLTestCase {
private static final String CONTEXT_PATH = "org.springframework.oxm.jaxb2";
@@ -223,6 +235,27 @@ public class Jaxb2MarshallerTest extends XMLTestCase {
assertFalse("Jaxb2Marshaller supports wrong JAXBElement", marshaller.supports(testElement.getClass()));
}
+ public void testSupportsPrimitives() throws Exception {
+ Method primitives = getClass().getDeclaredMethod("primitives", JAXBElement.class, JAXBElement.class, JAXBElement.class,
+ JAXBElement.class, JAXBElement.class, JAXBElement.class, JAXBElement.class, JAXBElement.class);
+ Type[] types = primitives.getGenericParameterTypes();
+ for (int i = 0; i < types.length; i++) {
+ ParameterizedType type = (ParameterizedType) types[i];
+ assertTrue("Jaxb2Marshaller does not support " + type, marshaller.supports(types[i]));
+ }
+ }
+
+ public void testSupportsStandards() throws Exception {
+ Method standards = getClass().getDeclaredMethod("standards", JAXBElement.class, JAXBElement.class, JAXBElement.class,
+ JAXBElement.class, JAXBElement.class, JAXBElement.class, JAXBElement.class, JAXBElement.class, JAXBElement.class, JAXBElement.class,
+ JAXBElement.class, JAXBElement.class, JAXBElement.class, JAXBElement.class);
+ Type[] types = standards.getGenericParameterTypes();
+ for (int i = 0; i < types.length; i++) {
+ ParameterizedType type = (ParameterizedType) types[i];
+ assertTrue("Jaxb2Marshaller does not support " + type, marshaller.supports(types[i]));
+ }
+ }
+
public void testMarshalAttachments() throws Exception {
marshaller = new Jaxb2Marshaller();
marshaller.setClassesToBeBound(new Class[]{BinaryObject.class});
@@ -245,4 +278,16 @@ public class Jaxb2MarshallerTest extends XMLTestCase {
verify(mimeContainer);
assertTrue("No XML written", result.toString().length() > 0);
}
+
+ private void primitives(JAXBElement