Generating an XML Document with JAXB
by Deepak Vohra
12/15/2004
An XML Schema represents the structure of an XML document in XML syntax. J2EE developers may require an XML document to conform to an XML Schema. The Java Architecture for XML Binding (JAXB) provides a binding compiler, xjc
, to generate Java classes from an XML Schema. The Java classes generated with the JAXB xjc
utility represent the different elements and complexType
s in an XML Schema. (A complexType
provides for constraining an element by specifying the attributes and elements in an element.) An XML document that conforms to the XML Schema may be constructed from the Java classes.
In this tutorial, JAXB is used to generate Java classes from an XML Schema. An example XML document shall be created from the Java classes. This article is structured into the
following sections.
- Preliminary Setup
- Overview
- Generating Java Classes from XML Schema
- Creating an XML Document from Java Classes
Preliminary Setup
To generate Java classes from an XML Schema with the JAXB
, the JAXB API
classes and the xjc
utility are required in the CLASSPATH
variable. Install the Java Web Service Developer Pack (JWSDP) 1.5 to a installation directory. Add the following .jar files to the CLASSPATH
variable.
/jaxb/lib/jaxb-api.jar /jaxb/lib/jaxb-impl.jar /jaxb/lib/jaxb-libs.jar /jaxb/lib/jaxb-xjc.jar /jwsdp-shared/lib/namespace.jar /jwsdp-shared/lib/jax-qname.jar /jwsdp-shared/lib/relaxngDatatype.jar
is the directory in which Java Web Service Developer Pack 1.5 is installed. Add
to the PATH
variable. The
directory contains the xjc
compiler. Add the
directory to the PATH
variable. The
directory contains the setenv
batch file to set the environment variables JAVA_HOME
, ANT_HOME
, and JWSDP_HOME
.
Overview
JAXB generates Java classes and interfaces corresponding to the top-level elements and top-level complexType
elements. In a XML Schema, an element is represented with
, and a complexType
is represented with
. In this tutorial, an example schema that represents articles published in a scientific journal is compiled with the JAXB
binding compiler. This schema has top-level element and complexType
declarations. The example XML Schema, catalog.xsd, is below.
Some of the XML Schema constructs are not supported by JAXB. If such unsupported constructs are included in a schema, an error will be generated when you try to generate Java classes from them with xjc
. The following schema elements are not supported: xs:any
, xs:anyAttribute
, xs:notation
, xs:redefine
, xs:key
, xs:keyref
, and xs:unique
. The following schema attributes are not supported: complexType.abstract
, element.abstract
, element.substitutionGroup
, xsi:type
, complexType.block
, complexType.final
, element.block
, element.final
, schema.blockDefault
, and schema.finalDefault
.
Generating Java Classes
The xjc
utility is run on the schema to bind a schema to Java classes. Run the xjc
utility on the example schema with the command:
>xjc catalog.xsd
Some of the options for the xjc
command-line interface are listed in the table:
-nv | Strict validation of the input schema(s) is not performed. |
-b | Specifies the external binding file. |
-d | Specifies the directory for generated files. |
-p | Specifies the target package. |
-classpath | Specifies classpath. |
-use-runtime | The impl.runtime package does not get generated. |
-xmlschema | The input schema is a W3C XML Schema (default). |
For the example schema catalog.xsd, xjc
generates 45 classes, as shown by xjc
's output below:
parsing a schema...
compiling a schema...
generated\impl\runtime\ErrorHandlerAdaptor.java
generated\impl\runtime\MSVValidator.java
generated\impl\runtime\NamespaceContext2.java
generated\impl\runtime\UnmarshallableObject.java
generated\impl\runtime\MarshallerImpl.java
generated\impl\runtime\ValidationContext.java
generated\impl\runtime\UnmarshallerImpl.java
generated\impl\runtime\DefaultJAXBContextImpl.java
generated\impl\runtime\ContentHandlerAdaptor.java
generated\impl\runtime\GrammarInfoFacade.java
generated\impl\runtime\UnmarshallingContext.java
generated\impl\runtime\UnmarshallingEventHandlerAdaptor.java
generated\impl\runtime\XMLSerializable.java
generated\impl\runtime\Discarder.java
generated\impl\runtime\PrefixCallback.java
generated\impl\runtime\SAXMarshaller.java
generated\impl\runtime\NamespaceContextImpl.java
generated\impl\runtime\UnmarshallingEventHandler.java
generated\impl\runtime\GrammarInfo.java
generated\impl\runtime\InterningUnmarshallerHandler.java
generated\impl\runtime\ValidatableObject.java
generated\impl\runtime\GrammarInfoImpl.java
generated\impl\runtime\ValidatingUnmarshaller.java
generated\impl\runtime\ValidatorImpl.java
generated\impl\runtime\SAXUnmarshallerHandlerImpl.java
generated\impl\runtime\XMLSerializer.java
generated\impl\runtime\Util.java
generated\impl\runtime\SAXUnmarshallerHandler.java
generated\impl\runtime\AbstractUnmarshallingEventHandlerImpl.java
generated\impl\ArticleImpl.java
generated\impl\ArticleTypeImpl.java
generated\impl\CatalogImpl.java
generated\impl\CatalogTypeImpl.java
generated\impl\JAXBVersion.java
generated\impl\JournalImpl.java
generated\impl\JournalTypeImpl.java
generated\Article.java
generated\ArticleType.java
generated\Catalog.java
generated\CatalogType.java
generated\Journal.java
generated\JournalType.java
generated\ObjectFactory.java
generated\bgm.ser
generated\jaxb.properties
A Java interface and a Java class are generated corresponding to each top-level xs:element
and top-level xs:complexType
in the example XML Schema. A factory class (ObjectFactory.java
), consisting of methods to create interface objects, also gets generated.
The ObjectFactory.java
class is in this article's sample code file,
jaxb-java-resources.zip.
Catalog.java
is the interface generated corresponding to the top-level element catalog
. An interface generated from a schema element extends the javax.xml.bind.Element
class. Catalog.java
is illustrated in the listing below.
package generated;
public interface Catalog
extends javax.xml.bind.Element, generated.CatalogType
{
}
CatalogType.java
is the generated interface corresponding to the top-level complexType
catalogType
. The CatalogType
interface consists of the getter and setter methods for each of the attributes of the catalog
element, and a getter method for the journal
elements in the catalog
element. CatalogType.java
is illustrated in the following listing.
package generated;
public interface CatalogType {
java.lang.String getSection();
void setSection(java.lang.String value);
java.util.List getJournal();
java.lang.String getPublisher();
void setPublisher(java.lang.String value);
}
CatalogImpl.java
and CatalogTypeImpl.java
are the Java classes generated for the Catalog.java
and CatalogType.java
interfaces, respectively.
Creating an XML Document from the Java Classes
In this section, an example XML document shall be created from the Java classes generated with JAXB. The example XML document, catalog.xml, is illustrated in the following listing.
section="Java Technology"
publisher="IBM developerWorks">
Service Oriented Architecture Frameworks
Naveen Balani
Advance DAO Programming
Sean Sullivan
Best Practices in EJB Exception Handling
Srikanth Shenoy
Create a CatalogImpl
class object from the Java classes and marshal the CatalogImpl
class object with a Marshaller
to construct an XML document.
Creating the Marshaller
First, import the javax.xml.bind
package, which consists of the Marshaller
, UnMarshaller
, and JAXBContext
classes. The Marshaller
class is used to convert a Java object into XML data. The UnMarshaller
class converts an XML document to a Java object.
import javax.xml.bind.*;
Create a JAXBContext
. A JAXBContext
object is required to implement the JAXB binding framework operations marshal
, unmarshal
, and validate
. An application creates a new instance (object) of the JAXBContext
class with the static method newInstance(String contextPath)
. The contextPath
specifies a list of Java package names for the schema-derived interfaces.
JAXBContext jaxbContext=JAXBContext.newInstance("generated");
The directory generated contains the JAXB-generated classes and interfaces.
Create a Marshaller
with the createMarshaller
method. The Marshaller
class has overloaded marshal
methods to marshal (that is, convert a Java object to XML data) into SAX2 events, a Document Object Model (DOM) structure, an OutputStream
, a javax.xml.transform.Result
, or a java.io.Writer
object.
Marshaller marshaller=jaxbContext.createMarshaller();
Creating a Java Object for an XML Document: CatalogImpl
To create a Java object, first create an ObjectFactory
. An implementation class instance is
created with the ObjectFactory
. For each of the schema-derived Java classes, a static factory method to produce an object of the class is defined in the ObjectFactory
.
ObjectFactory factory=new ObjectFactory();
Create a catalog
element with the createCatalog
method of the ObjectFactory
class. CatalogImpl
is the implementation class for the interface Catalog
.
CatalogImpl catalog=(CatalogImpl)(factory.createCatalog());
Set the section
attribute of the catalog
element with the setSection
method in the CatalogImpl
class.
catalog.setSection("Java Technology");
Set the publisher
attribute of the catalog
element with the setPublisher
method.
catalog.setPublisher("IBM developerWorks");
Creating a Java Object for an XML Document: JournalImpl
and ArticleImpl
Create a journal
element with the createJournal
method of the ObjectFactory
class. JournalImpl
is the implementation class for the interface Journal
.
JournalImpl journal=(JournalImpl)(factory.createJournal());
Add the journal
element to the catalog
element. Obtain a java.util.List
of JournalImpl
for a CatalogImpl
and add the journal
element to the List
.
java.util.List journalList=catalog.getJournal();
journalList.add(journal);
Create the article
element in the journal
element with the createArticle
method of the ObjectFactory
class. ArticleImpl
is the implementation class for the Article
interface.
ArticleImpl article=(ArticleImpl)(factory.createArticle());
Set the level
attribute of the article
element with the setLevel
method in the ArticleImpl
class.
article.setLevel("Intermediate");
Set the date
attribute of the article
element with the setDate
method.
article.setDate("January-2004");
Create the title
element in the article
element with the setTitle
method.
article.setTitle("Service Oriented Architecture Frameworks");
Create the author
element of the article
element with the setAuthor
method.
article.setAuthor("Naveen Balani");
Add the article
element to the journal
element. Obtain a java.util.List
of ArticleImpl
for a JournalImpl
and add the article element to the List
.
java.util.List articleList=journal.getArticle();
articleList.add(article);
Similar to the article
element created with the procedure explained, add the other article
elements to create the example XML document catalog.xml.
Marshalling the Java Object to an XML Document
Marshal the CatalogImpl
object to an XML document with the marshal
method of the class Marshaller
. The CatalogImpl
object is marshalled to an OutputStream
.
marshaller.marshal(catalog, new FileOutputStream(xmlDocument));
xmlDocument
is the output XML java.io.File
object, representing the XML document shown at the beginning of this section.
JAXBConstructor.java
, the program used to create an XML document from the Java classes, is in this article's sample code file,
jaxb-java-resources.zip.
Conclusion
JAXB
provides a xjc
binding compiler to generate Java objects from a schema, which may be subsequently marshalled to an XML document. However, JAXB has a limitation: it does not support all of the XML schema constructs.
Resources
" Java Architecture for XML Binding"
"XML Schema Structures"
Java Web Services Developer Pack 1.5
Example code for this article: jaxb-java-resources.zip
Deepak Vohra
is a NuBean consultant and a web developer.