http://www.developer.com/

Back to article

Using JAXB in JDeveloper 10.1.3


January 17, 2008

If you have used Web Services, you should be familiar that SOAP/XML messages used in data exchange in a Web Service are based on an XML Schema. Or, if you have used J2EE applications, you would be familiar with creating XML deployment descriptors that are based on an XML Schema. But, how is an XML document instantiated from an XML Schema? Java Architecture for XML Binding (JAXB) provides a compiler to bind an XML Schema to its Java representation from which an XML document may be marshalled. Marshalling is the process of creating an XML document from a Java object. JAXB also provides an unmarshalling API to unmarshal an XML document to a Java object. Unmarshalling is the process of converting an XML document to its Java object representation and subsequently reading the element and attribute values in the XML document. Marshalling is used to create an XML document and unmarshalling is used to read an XML document. You will use Oracle JDeveloper for JAXB, because JDeveloper provides a built-in support for JAXB compiler.

Preliminary Setup

JDeveloper 10.1.3 has new feature, a JAX-B compiler. With the JAX-B compiler, an XML Schema may be compiled into its Java representation. You will need to install JDeveloper 10.1.3. In JDeveloper, create an application and a project. In the project, create an XML Schema with File>New>General>XML>XML Schema.



Click here for a larger image.

Figure 1: Creating an XML Schema

In the Create XML Schema window, specify a File Name, and click OK. An XML Schema gets added to the Applications-Navigator.

Figure 2: XML Schema in a JDeveloper Project

You need to add the Oracle XML Parser v2 library, which contains the Java API for XML Parsing (JAXP) and the XML parsers. Also, add the Xml.jar JAR file, which contains the javax.xml.bind package API. A library is added by selecting Tools>Project Properties>Libraries>Add Library.



Click here for a larger image.

Figure 3: Adding JAXB Libraries to JAXB Application

The JAXB compiler generates Java interfaces and classes corresponding to the top-level elements and top-level complexType elements. A schema element is represented with <xs:element/>, and a complexType is represented by <xs:complexType/>. The example schema that will be compiled in this article is listed below.

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
   <xsd:element name="Catalog" type="catalogType"/>
   <xsd:complexType name="catalogType">
      <xsd:sequence>
         <xsd:element name="journal" type="journalType"
                      minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
      <xsd:attribute name="title" type="xsd:string"/>
      <xsd:attribute name="publisher" type="xsd:string"/>
   </xsd:complexType>

   <xsd:complexType name="journalType">
      <xsd:sequence>
         <xsd:element name="article" type="articleType"
                      minOccurs="0" maxOccurs="unbounded"/>
      </xsd:sequence>
      <xsd:attribute name="date" type="xsd:string"/>
   </xsd:complexType>
   <xsd:complexType name="articleType">
      <xsd:sequence>
         <xsd:element name="title" type="xsd:string"/>
         <xsd:element name="author" type="xsd:string"/>
      </xsd:sequence>
      <xsd:attribute name="section" type="xsd:string"/>
   </xsd:complexType>
</xsd:schema>

In the next section, you will compile the example schema into Java classes and representation. Subsequently, you will construct and marshal a Java representation to an XML document. You also will unmarshal an XML document using the JAXB API.

Compiling an XML Schema

In this section, you will compile the example XML schema using the JAX-B compiler in JDeveloper 10.1.3. To compile the example XML schema, select the schema node in Applications-Navigator and select Tools>JAXB Compilation.



Click here for a larger image.

Figure 4: Compiling an XML Schema with the JAXB Compiler

In the JAXB Compilation window, specify a package name to which the schema is to be compiled and click OK.

The schema gets compiled and the Java classes get generated in the specified package. An interface and an implementation class get generated for each of the top level element and complexType definitions. Interface Catalog.java and implementation class CatalogImpl.java get generated, corresponding to top level element 'catalog'. Catalog.java is listed below.

package jaxb;
public interface Catalog extends jaxb.CatalogType,
   javax.xml.bind.Element
{
}

The Catalog.java interface extends the javax.xml.bind.Element interface. The CatalogImpl.java class is listed below.

package jaxb;

public class CatalogImpl extends jaxb.CatalogTypeImpl
   implements jaxb.Catalog
{
   public CatalogImpl(oracle.xml.parser.v2.XMLDocument ownerDoc)
   {
      super("Catalog", "", ownerDoc);
   }

   public CatalogImpl(java.lang.String name,
                      java.lang.String namespace,
                      oracle.xml.parser.v2.XMLDocument ownerDoc)
   {
      super(name, namespace, ownerDoc);
   }

   public CatalogImpl(oracle.xml.parser.v2.XMLElement node)
   {
      super(node);
   }

}

The implementation class provides three constructors. One of the constructors takes a oracle.xml.parser.v2.XMLDocument class object as an argument. Another constructor takes an oracle.xml.parser.v2.XMLElement node as an argument. A third constructor takes a String element tag name, a String element namespace, and an XMLDocument object as arguments.

An interface, CatalogType.java, also gets generated for top level complexType catalogType. The CatalogType.java interface consists of getter and setter methods for the title and publisher attributes. CatalogType.java also includes a getter method for the journal node. The getJournal() method returns a List. CatalogType.java is listed below.

package jaxb;
public interface CatalogType
   public void setTitle(java.lang.String value);
   public java.lang.String getTitle();
   public void setPublisher(java.lang.String value);
   public java.lang.String getPublisher();
   public java.util.List getJournal();
}

Similarly,the JournalType.java and ArticleType.java interfaces get generated corresponding to journalType and articleType complexTypes. Corresponding to these interfaces, implementation classes CatalogTypeImpl.java, JournalTypeImpl.java, and ArticleTypeImpl.java get generated.

An ObjectFactory.java factory class also gets generated. The factory class consists of create methods to create instances of interfaces corresponding to complexType and element definitions. ObjectFactory.java class also consists of an unmarshal (Node) method to unmarshal an XML document node to an object of type Catalog. ObjectFactory.java class is listed below.

package jaxb;
public class ObjectFactory
{
   public jaxb.Catalog createCatalog()
   {
      jaxb.Catalog elem = new jaxb.CatalogImpl(ownerDocument);
      return elem;
   }
   public jaxb.JournalType createJournalType()
   {
      jaxb.JournalType elem =
         new jaxb.JournalTypeImpl(ownerDocument);
      return elem;
   }
   public jaxb.CatalogType createCatalogType()
   {
      jaxb.CatalogType elem =
         new jaxb.CatalogTypeImpl(ownerDocument);
      return elem;
   }

   public jaxb.ArticleType createArticleType()
   {
      jaxb.ArticleType elem =
         new jaxb.ArticleTypeImpl(ownerDocument);
      return elem;
   }
   public Object newInstance (Class javaContentInterface)
      throws javax.xml.bind.JAXBException
   {
      Object newInstance = null;
      java.lang.String elemName = javaContentInterface.getName();
      try
      {
         if (elemName.equals("jaxb.Catalog"))
         {
            newInstance = new jaxb.CatalogImpl(ownerDocument);
            return newInstance;
         }
      }
      catch (Exception e)
      {
         throw new javax.xml.bind.JAXBException(e.toString());
      }
      return null;
   }
   public Object getProperty(String name)
   {
      return null;
   }
   public void setProperty(String name, Object value)
   {
   }
   public Object unmarshal(org.w3c.dom.Node node)
      throws javax.xml.bind.UnmarshalException
   {
      java.lang.String elemName = node.getLocalName();
      try
      {
         if (elemName.equals("Catalog"))
         {
            jaxb.Catalog unode =
               new jaxb.CatalogImpl((oracle.xml.parser.v2.
                                     XMLElement)node);
            return unode;
         }
      }
      catch (Exception e)
      {
         throw new javax.xml.bind.
            UnmarshalException(e.toString());
      }
      return null;
   }
   public Object getSchemaLocation() throws Exception
   {
      return new java.io.File("null").toURL();
   }
   private oracle.xml.parser.v2.XMLDocument ownerDocument =
      new oracle.xml.parser.v2.XMLDocument();
}

The interfaces, implementation classes, and ObjectFactory.java class generated from compiling an XML schema are shown in the Applications-Navigator.

Figure 5: Java Classes Generated with the JAXB Compiler

Marshalling an XML Document

Marshalling is the construction of an XML document from a Java representation of the document. In this section, you will marshal an XML document. The XML document that will be marshaled is listed below.

<?xml version="1.0" encoding = 'UTF-8'?>
<catalog title="Oracle Magazine"
         publisher="Oracle Publishing">
   <journal date="July-August 2005">
      <article section="TECHNOLOGY">
         <title>Tuning Undo Tablespace</title>
         <author>Kimberly Floss</author>
      </article>
   </journal>

   <journal date="July-August 2005">
      <article section="TECHNOLOGY">
         <title>Using PHP 5 with Oracle XML DB</title>
         <author>Yuli Vasiliev</author>
      </article>
   </journal>
</catalog>

You need to create a Java application to marshal an XML document. Select File>New>General>Java Class to add a Java class. In the Create Java class frame, specify class name (JAXBMarshaller) and package name (jaxb) and click OK. Java class JAXBMarshaller.java gets added to package jaxb. In the marshaller application, import the JAXB API package.

import javax.xml.bind.*;

Create an instance of JaxbContextImpl.

JaxbContextImpl jaxbContext=new JaxbContextImpl();

Create a Marshaller object from the JaxbContextImpl object. The Marshaller interface is used to marshal a Java object to an XML document.

Marshaller marshaller=jaxbContext.createMarshaller();

Create an ObjectFactory object, which is used to create instances of Java representations of XML Schema elements and complexTypes. Create an object of type Catalog using createCatalog() method.

ObjectFactory factory=new ObjectFactory();
Catalog catalog=factory.createCatalog();

Set 'title' and 'publisher' attributes using setter methods for these attributes.

catalog.setTitle("Oracle Magazine");
catalog.setPublisher("Oracle Publishing");

Create an object of type JournalType, which corresponds to journalType complexType in example XML schema. Set 'date' attribute of JournalType object.

JournalType journal=factory.createJournalType();
journal.setDate("July-August 2005");

Create an ArticleType object and set the 'section' attribute and 'title' and 'author' elements.

ArticleType article=factory.createArticleType();
   article.setSection("Technology");
   article.setTitle("Tuning Undo Tablespace");
   article.setAuthor("Kimberly Floss");

Obtain a ArticleType List from the JournalType object and add the ArticleType object created to the JournalType object.

java.util.List articleList=journal.getArticle();
articleList.add(article);

Obtain a JournalType List from Catalog object and add the JournalType object created to the Catalog object.

java.util.List journalList=catalog.getJournal();
journalList.add(journal);

Similarly, add another JournalType object. The Marshaller interface provides overloaded marshal() methods to marshal a Java object to either a ContentHandler object, a Node, an OutputStream, a Result object, or a Writer object. In the example application, the Java object is marshaled to an XML document using an OutputStream.

marshaller.marshal(catalog, new FileOutputStream(xmlDocument));

JAXBMarshaller.java is listed below.

package jaxb;
import java.io.*;
import javax.xml.bind.*;
import oracle.xml.jaxb.JaxbContextImpl;
public class JAXBMarshaller
{
   public void createXMLDocument(File xmlDocument){
      try
      {

         JaxbContextImpl jaxbContext=new JaxbContextImpl();
         Marshaller marshaller=jaxbContext.createMarshaller();

         ObjectFactory factory=new ObjectFactory();
         Catalog catalog=factory.createCatalog();
         catalog.setTitle("Oracle Magazine");
         catalog.setPublisher("Oracle Publishing");

         JournalType journal=factory.createJournalType();
         journal.setDate("July-August 2005");

         ArticleType article=factory.createArticleType();
         article.setSection("Technology");
         article.setTitle("Tuning Undo Tablespace");
         article.setAuthor("Kimberly Floss");

         java.util.List articleList=journal.getArticle();
         articleList.add(article);

         java.util.List journalList=catalog.getJournal();
         journalList.add(journal);

         journal=factory.createJournalType();
         journal.setDate("July-August 2005");

         article=factory.createArticleType();
         article.setSection("Technology");
         article.setTitle("Using PHP 5 with Oracle XML DB");
         article.setAuthor("Yuli Vasiliev");

         articleList=journal.getArticle();
         articleList.add(article);

         journalList=catalog.getJournal();
         journalList.add(journal);

         marshaller.marshal(catalog, new
            FileOutputStream(xmlDocument));

      }catch (IOException e)
      {
         System.out.println(e.toString());

      }
      catch (JAXBException e)
      {
         System.out.println(e.toString());

      }

   }
   public static void main (String[] argv)
   {
      JAXBMarshaller marshaller=new JAXBMarshaller();
      marshaller.createXMLDocument(new File("catalog.xml"));
   }
}

To run the JAXBMarshaller application, right-click JAXBMarshaller.java in Applications Navigator and select Run.



Click here for a larger image.

Figure 6: Running JAXB Application

The Java object constructed gets marshaled to an XML document, as shown below.



Click here for a larger image.

Figure 7: XML Document Marshalled using JAXB

UnMarshalling an XML Document

In this section, you will unmarshal an XML document using the JAXB API and the Java classes generated by compiling the example XML schema. A prerequisite for unmarshalling is that the XML document should conform to the XML Schema from which the binding classes are generated. The XML document that you will unmarshal is the same that is marshalled in the previous section. Create a Java application, JAXBUnMarshaller.java, in JDeveloper project JAXB with File>New>General>Java Class. Import the JAXB API. Because JAXBUnMarshaller.java is created in the same package as the binding classes, the binding classes are not required to be imported. If the unmarshalling application is in a different package, import the package containing the binding classes.

Create a JAXBContext object using the static method newInstance(String contextPath). ContextPath is a list of packages that contain the schema derived binding classes.

JAXBContext jaxbContext=JAXBContext.newInstance("jaxb");

Create an Unmarshaller object from the JAXBContext object.

Unmarshaller unmarshaller=jaxbContext.createUnmarshaller();

The Unmarshaller interface provides overloaded unmarshal methods to unmarshal an XML document from a File, InputSource, InputStream, Node Source, or URL object. In the example application, unmarshal from a File object.

CatalogType catalog =
   (CatalogType)unmarshaller.unmarshal(xmlDocument);

Output the 'title' and 'publisher' attributes using getter methods for these attributes.

System.out.println("Title: "+catalog.getTitle());
System.out.println("Publisher: "+catalog.getPublisher());

Obtain a List of JournalType objects, corresponding to 'journal' nodes in the XML document, using the getJournal() method.

java.util.List journalList=catalog.getJournal();
Iterator iterator=journalList.iterator();

Iterate over the List and obtain the JournalType nodes.

while(iterator.hasNext()){
   JournalType journal=(JournalType)iterator.next();
}

Output the 'date' attribute of the 'journal' element using the getDate() method.

System.out.println("Date: "+journal.getDate());

Obtain a List of ArticleType objects for each of JournalType nodes and create an Iterator for the List.

java.util.List articleList=journal.getArticle();
Iterator iter=articleList.iterator();

Iterate over a ArticleType List and output the values of the 'section' attribute and the 'title' and 'author' elements.

while(iter.hasNext()){
   ArticleType article=(ArticleType)iter.next();
   System.out.println("Section: "+article.getSection());
   System.out.println("Title:   "+article.getTitle());
   System.out.println("Author:  "+article.getAuthor());
}

JAXBUnMarshaller.java is listed below.

package jaxb;

import java.io.*;

import java.util.Iterator;
import javax.xml.bind.*;


public class JAXBUnMarshaller
{
   public void unmarshalXMLDocument(File xmlDocument){
      try
      {

         JAXBContext jaxbContext =
            JAXBContext.newInstance("jaxb");

         Unmarshaller unmarshaller =
            jaxbContext.createUnmarshaller();

         CatalogType catalog =
            (CatalogType)unmarshaller.unmarshal(xmlDocument);
         System.out.println("Title:     "+catalog.getTitle());
         System.out.println("Publisher: "+catalog.getPublisher());

         java.util.List journalList=catalog.getJournal();
         Iterator iterator=journalList.iterator();

         while(iterator.hasNext()){
            JournalType journal=(JournalType)iterator.next();
            System.out.println("Date: "+journal.getDate());

            java.util.List articleList=journal.getArticle();
            Iterator iter=articleList.iterator();

            while(iter.hasNext()){
               ArticleType article=(ArticleType)iter.next();
               System.out.println("Section: "+article.getSection());
               System.out.println("Title:   "+article.getTitle());
               System.out.println("Author:  "+article.getAuthor());
            }

         }
      }
      catch (JAXBException e)
      {
         System.out.println(e.toString());
      }
   }
   public static void main (String[] argv)
   {
      JAXBUnMarshaller jaxbUnmarshaller = new JAXBUnMarshaller();
      jaxbUnmarshaller.unmarshalXMLDocument
         (new File("catalog.xml"));
   }
}

To unmarshal the example XML document, right-click JAXBUnMarshaller.java and select Run.



Click here for a larger image.

Figure 8: Running Unmarshalling JAXB Application

The output from JAXBUnMarshaller.java lists the values of the different attributes and elements in the example XML document.



Click here for a larger image.

Figure 9:Unmarshalled XML Document using JAXB

Conclusion

JDeveloper 10.1.3 provides a JAX-B compiler with which an XML schema may be compiled to its Java representation. Subsequently, the Java classes may be used to create an XML document and read an XML document.

Sitemap | Contact Us

Thanks for your registration, follow us on our social networks to keep up-to-date