I'm using JAXB with Scala, my marshalling code looks like this:
def marshalToXml(): String = {
val context = JAXBContext.newInstance(this.getClass())
val writer = new StringWriter
context.createMarshaller.marshal(this, writer)
writer.toString()
}
Then for my nullable elements I'm using the annotation @XmlElement(nillable = true)
as per JAXB Marshalling with null fields. This gives me XML output like so:
<name>Alex Dean</name>
<customerReference xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:nil="true"/>
<quantity>1</quantity>
<createdAt>2011-05-14T00:00:00+03:00</createdAt>
This is a good start but what I'd really like to marshal for these fields is:
<name>Alex Dean</name>
<customerReference nil="true"/>
<quantity type="integer">1</quantity>
<createdAt type="datetime">2011-05-14T00:00:00+03:00</createdAt>
In other words, I would like to remove the namespace attributes and prefixes, and add in explicit XML datatype attributes for all but strings. It's probably quite simple to do but I can't seem to find how in the JAXB documentation.
Any help gratefully received!
You could use JAXB with a StAX parser and do the following:
Customer
Each property in your domain model will be mapped with
@XmlElement(nillable=true, type=Object.class)
. Setting thetype=Object.class
will force anxsi:type
attribute to be written out.XMLStreamWriterWrapper
We will write a create a wrapper for an
XMLStreamWriter
that strips off all the information we do not want written to XML.XMLStreamReaderWrapper
We need to create a wrapper for
XMLStreamReader
that adds everything that we stripped off on theXMLStreamWriter
. This is easier to do forXMLStreamReader
since we can extendStreamReaderDelegate
.Demo
The following demonstrates how everything comes together:
Output