How to serialize Java Objects to XML and deserialize back from XML
By Partho, Gaea News NetworkFriday, October 23, 2009
XML has set ubiquitary standards for representing data. There are several XML technologies that can be used to serialize Java objects to XML. Some of the most commonly technologies used by Java developers include the Simple API for XML (SAX) and the Document Object Model (DOM) APIs. For a smooth control over parsing and serialization SAX, or Stax offers better performance. However, the programmers prefer to use technologies that can accomplish immediate tasks. However, we would provide you two simple and quick howto’s for serialization of Java Objects to XML and deserialize back to XML.
Java API for XML Binding (JAXB) provides a simple and quick Java-XML mapping or serialization. With JAXB you can performs a number of tasks that include binding of class data from XML schema, and serializing object data to and from XML. We would show you how to do simple Java-XML serialization with JAXB.
Again, Java has the inherent benefit of Library that enables almost everything. XStream is simple and easy to use library for serializing Java-Objects to XML and read them back. It converts the existing Java objects clean XML and restores them again without any modifications. XStream 2.1.0 is currentl.y available for the users. Here’s how to serialize Java Objects to XML and deserialize back from XML
Serialization of Java Objects to XML and deserialization with XStream
To understand the use of XStream library you can take this example.
Take the class below
package com.java_blog.xStreamTest;
public class Person {
private String firstName;
private String lastName;
public Person(String firstName, String lastName) {
super();
this.firstName = firstName;
this.lastName = lastName;
}
}
Use this Testcode
package com.java_blog.xStreamTest;
import com.thoughtworks.xstream.XStream;
public class Test {
public static void main(String[] args) {
Person Chancellor = new Person(”Angela”, “Merkel”);
Person President = new Person(”Barack”, “Obama”);
XStream xStream = new XStream();
xStream.alias(”Person”, Person.class);
StringBuilder sb = new StringBuilder();
sb.append(xStream.toXML(Chancellor));
sb.append(”\n”);
sb.append(xStream.toXML(President));
System.out.println(sb);
}
}
After compiling the output is
<Person>
<firstName>Angela</firstName>
<lastName>Merkel</lastName>
</Person>
<Person>
<firstName>Barack</firstName>
<lastName>Obama</lastName>
</Person>
Deserializing XML to Objects
Here’s an example how you can deserialize XML to an object
import com.thoughtworks.xstream.XStream;
class Date {
int year = 2009;
int month = 10;
int day = 20;
}
public class Deserialize {
public static void main(String[] args) {
XStream xstream = new XStream();
Date date = new Date();
xstream.alias(”date”, Date.class);
String xml = xstream.toXML(date);
System.out.print(xml);
Date newdate = (Date)xstream.fromXML(xml);
newdate.month = 12;
newdate.day = 2;
String newxml = xstream.toXML(newdate);
System.out.print(”\n\n” + newxml);
}
}
Observe the line
Date newdate = (Date)xstream.fromXML(xml);
Here a new object newdate is created using fromXML method to convert the string xml back to an object
After compiling the output is
Output
<date>
<year>2009<year>
<month>10<month>
<day>20<day>
<date>
<date>
<year>2009<year>
<month>12<month>
<day>2<day>
<date>
This is just a basic example of using XStream for serializing and deserializing Java objects to XML. In order to use XStream on a wider scale you need to know look for the tutorials in XStream.
Java-XML serialization using JAXB
Java-XML serialization with JAXB using POJO
Let’s take an item Java object. We would serialize an Item object to XML format. For this we will annotate this POJO with a few XML annotation from javax.xml.bind.annotation.
From the code
@XmlRootElement(name=”Item”) indicates that you want <Item> to be the root element.
@XmlType(propOrder = {”name”, “price”}) indicates the order you want the element to be arranged in XML output.
@XmlAttribute(name=”id”, …) indicates that id is an attribute to < Item> root element.
@XmlElement(….) indicates that you want price and name to be element within Item.
The Item.java is ready. Now create JAXB script for marshaling Item.
//creating Item data object
Item item = new Item();
item.setId(2);
item.setName("Foo");
item.setPrice(200);
.....
JAXBContext context = JAXBContext.newInstance(item.getClass());
Marshaller marshaller = context.createMarshaller();
marshaller.marshal(item, new FileWriter(”item.xml”)); //I want to save the output file to item.xml
The output code listing 3 item.xml file is created that appears like this
<?xml version=”1.0″ encoding=”UTF-8″ standalone=”yes”?>
<ns1:item ns1:id=”2″ xmlns:ns1=”https://blogs.sun.com/teera/ns/item”>
<ns1:itemName>Foo</ns1:itemName>
<ns1:price>200</ns1:price>
</ns1:item>
To channel the output XML as text String, Stream, Writer, ContentHandler, etc simply change the parameter of the marshal method as below
...
JAXBContext context = JAXBContext.newInstance(item.getClass());
Marshaller marshaller = context.createMarshaller();
marshaller.marshal(item, <java.io.OutputStream instance>); // save xml output to the OutputStream instance
…
JAXBContext context = JAXBContext.newInstance(item.getClass());
Marshaller marshaller = context.createMarshaller();
StringWriter sw = new StringWriter();
marshaller.marshal(item, sw); //save to StringWriter, you can then call sw.toString() to get java.lang.String
XML to POJO
This is just the reverse of the above process. Let’s say we have a XML string data and would like to turn it into Item.java.object XML data the code listing 3 is like this
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<ns1:item ns1:id="2" xmlns:ns1="https://blogs.sun.com/teera/ns/item">
<ns1:itemName>Bar</ns1:itemName>
<ns1:price>80</ns1:price>
</ns1:item>
To unmarshal this xml code to Java object do this
...
ByteArrayInputStream xmlContentBytes = new ByteArrayInputStream (xmlContent.getBytes());
JAXBContext context = JAXBContext.newInstance(Item.getClass());
Unmarshaller unmarshaller = context.createUnmarshaller();
//note: setting schema to null will turn validator off
unmarshaller.setSchema(null);
Object xmlObject = Item.getClass().cast(unmarshaller.unmarshal(xmlContentBytes));
return xmlObject;
...
The XML source might appear in several forms both from Stream and file. The only difference is method parameter
...
unmarshaller.unmarshal(new File("Item.xml"));
...
unmarshaller.unmarshal(inputStream); // inputStream is an instance of java.io.InputStream, reading from stream
Validation with XML Schema
Before unmarshalling to Java object you need to validate input XML with schema. Create an XML schema file called item.xsd.
Now register this schema for validation
...
Schema schema = SchemaFactory.newInstance(XMLConstants.W3C_XML_SCHEMA_NS_URI)
.newSchema(new File("Item.xsd"));
unmarshaller.setSchema(schema);
...
When you try to unmarshal XML data to POJO, if the input XML is not conformed to the schema, exception will be caught.
javax.xml.bind.UnmarshalException
- with linked exception:
javax.xml.bind.JAXBException caught: null
[org.xml.sax.SAXParseException: cvc-datatype-valid.1.2.1: 'item1' is not a valid value for 'integer'.]
In case the XML input is valid against the schema, the XML data will be unmarshalled to Item.java object successfully.