<div dir="ltr" style="text-align: justify;">Java Architecture for <b>XML Binding (JAXB)</b> is an <b>XML-to-Java binding</b> technology that simplifies the development of web services by enabling transformations between schema and Java objects and between XML instance documents and Java object instances. An XML schema defines the data elements and structure of an XML document. You can use <b>JAXB APIs</b> and tools to establish mappings between Java classes and XML schema. <b>JAXB </b>technology provides the tools that enable you to convert your XML documents to and from Java objects.There are many tutorials and examples of using<b> JAX-RS</b> to create <b>RESTful web services,</b> but most fall short of explaining how to produce and consume complex object graphs using <b>XML </b>and <b>JAXB</b>. This article will show how easy it can be, several approaches to where you place the annotations, and how you can configure them.</p>
<p>Lets start with the root XML element. I chose to call mine <i><b>GetBooksResponse</b></i>, and use it as a container for a collection of Book objects and a Student object. You don&#8217;t need to follow this convention.<br />
<b>GetBooksResponse.java</b></p>
<pre class="highlight">package com.dineshonjava.ws.rest; 
 
import java.util.ArrayList; 
import java.util.List; 
 
import javax.xml.bind.annotation.XmlElement; 
import javax.xml.bind.annotation.XmlElementWrapper; 
import javax.xml.bind.annotation.XmlRootElement; 
 
import com.dineshonjava.ws.xml.Book; 
import com.dineshonjava.ws.xml.Student; 
 
/** 
 * @author Dinesh Rajput 
 * 
 */ 
@XmlRootElement 
public class GetBooksResponse { 
 private Student student; 
 private List<;Book>; books = new ArrayList<;Book>;(); 
 
 @XmlElement 
 public Student getStudent() { 
 return student; 
 } 
 public void setStudent(Student student) { 
 this.student = student; 
 } 
 
 @XmlElement 
 @XmlElementWrapper(name = "books") 
 public List<;Book>; getBooks() { 
 return books; 
 } 
 public void setBooks(List<;Book>; books) { 
 this.books = books; 
 } 
 
} 
 
</pre>
<div id="ads-id" align="center"></div>
<p><b>JAXB&#8217;s</b> default naming convention is to use your class or bean getter name as-is, but starting with a lower case letter. In this example, once marshaled to XML the element names will be <b>getBooksResponse</b>, <b>student</b>, and <b>books</b>. I will show an example of how to override the default naming later in this article.</p>
<p>Also notice that I placed the <b>@XmlElement</b> annotations on the getter methods instead of on the private fields. When placed on the private fields, <b>JAXB </b>will give you an error unless you add <b>@XmlAccessorType(XmlAccessType.FIELD) </b>at the class level.</p>
<p>Finally, notice the <b>@XmlElementWrapper</b> annotation on the List collection. This makes <b>JAXB </b>wrap all of the order XML elements inside of an orders XML element. This annotation can be used with an array instead of a List too.<br />
<b>Student.java</b></p>
<pre class="highlight">package com.dineshonjava.ws.xml; 
 
import javax.xml.bind.annotation.XmlElement; 
import javax.xml.bind.annotation.XmlType; 
 
/** 
 * @author Dinesh Rajput 
 * 
 */ 
@XmlType(name="students") 
public class Student { 
 private long rollNumber; 
 private String name; 
 private String course; 
 
 @XmlElement(name="rollNumber") 
 public long getRollNumber() { 
 return rollNumber; 
 } 
 public void setRollNumber(long rollNumber) { 
 this.rollNumber = rollNumber; 
 } 
 @XmlElement(name="name") 
 public String getName() { 
 return name; 
 } 
 public void setName(String name) { 
 this.name = name; 
 } 
 @XmlElement(name="course") 
 public String getCourse() { 
 return course; 
 } 
 public void setCourse(String course) { 
 this.course = course; 
 } 
} 
 
</pre>
<p>In the example above, we use <b>@XmlType</b> at the class level instead of <b>@XmlRootElement</b> because it is not the root element. Also notice the name parameter in each of the annotations. This is how you override JAXB&#8217;s default element naming.</p>
<p><b>Book.java</b></p>
<pre class="highlight">package com.dineshonjava.ws.xml; 
 
import java.util.Date; 
 
import javax.xml.bind.annotation.XmlAccessType; 
import javax.xml.bind.annotation.XmlAccessorType; 
import javax.xml.bind.annotation.XmlElement; 
import javax.xml.bind.annotation.XmlElementWrapper; 
import javax.xml.bind.annotation.XmlType; 
 
/** 
 * @author Dinesh Rajput 
 * 
 */ 
@XmlType(propOrder = { "publishDate", "publishNumber", "publishedBooks", "bookName" } ) 
@XmlAccessorType(XmlAccessType.FIELD) 
public class Book { 
 @XmlElement 
 public Date publishDate; 
 
 @XmlElement 
 public long publishNumber; 
 
 @XmlElement 
 public String bookName; 
 
 @XmlElement 
 @XmlElementWrapper(name = "publishedBooks") 
 public PublishedBooks[] publishedBooks; 
 
 public Date getPublishDate() { 
 return publishDate; 
 } 
 
 public void setPublishDate(Date publishDate) { 
 this.publishDate = publishDate; 
 } 
 
 public long getPublishNumber() { 
 return publishNumber; 
 } 
 
 public void setPublishNumber(long publishNumber) { 
 this.publishNumber = publishNumber; 
 } 
 
 public String getBookName() { 
 return bookName; 
 } 
 
 public PublishedBooks[] getPublishedBooks() { 
 return publishedBooks; 
 } 
 
 public void setPublishedBooks(PublishedBooks[] publishedBooks) { 
 this.publishedBooks = publishedBooks; 
 } 
 
 public void setBookName(String bookName) { 
 this.bookName = bookName; 
 } 
 
} 
 
</pre>
<p>In the example above I used the <b>@XmlAccessorType(XmlAccessType.FIELD)</b> to allow me to place the <b>@XmlElement</b> annotations on the private fields instead of on the getter methods.</p>
<p>Also notice the <b>propOrder </b>parameter of the <b>@XmlType</b> annotation. By default <b>JAXB </b>will <b>book </b>the elements alphabetically. Use the <b>propOrder </b>parameter to specify the order when marshaling to <b>XML</b>. The values are the bean names, not the overridden names in the <b>@XmlElement(name = &#8220;overridenName&#8221;)</b> annotation.</p>
<p>Finally, notice the <b>@XmlElementWrapper</b> used on a <b>PublishedBooks[]</b> array. It works with arrays and Lists.</p>
<p><b>PublishedBooks.java</b></p>
<pre class="highlight">package com.dineshonjava.ws.xml; 
 
import javax.xml.bind.annotation.XmlElement; 
import javax.xml.bind.annotation.XmlType; 
 
/** 
 * @author Dinesh Rajput 
 * 
 */ 
@XmlType(propOrder = { "bookId", "description", "quantity", "unitPrice", 
 "subTotal", "tax", "total" } ) 
public class PublishedBooks { 
 
 private long bookId; 
 private String description; 
 private short quantity; 
 private double unitPrice; 
 
 @XmlElement 
 public long getBookId() { 
 return bookId; 
 } 
 public void setBookId(long bookId) { 
 this.bookId = bookId; 
 } 
 @XmlElement 
 public String getDescription() { 
 return description; 
 } 
 public void setDescription(String description) { 
 this.description = description; 
 } 
 @XmlElement 
 public short getQuantity() { 
 return quantity; 
 } 
 public void setQuantity(short quantity) { 
 this.quantity = quantity; 
 } 
 @XmlElement 
 public double getUnitPrice() { 
 return unitPrice; 
 } 
 public void setUnitPrice(double unitPrice) { 
 this.unitPrice = unitPrice; 
 } 
 
 @XmlElement 
 public double getSubTotal() { 
 return unitPrice * quantity; 
 } 
 
 @XmlElement 
 public double getTax() { 
 return getSubTotal() * 0.15F; 
 } 
 
 @XmlElement 
 public double getTotal() { 
 return getSubTotal() + getTax(); 
 } 
} 
 
</pre>
<p>In the example above there are no setter methods that correspond to <b>getSubTotal</b>, <b>getTax </b>and <b>getTotal</b>. Now lets create a<b> JAX-RS RESTful </b>web service that can return this object graph in the response.<br />
<b>BookResource.java</b></p>
<pre class="highlight">package com.dineshonjava.ws.order; 
 
import java.util.Date; 
 
import javax.ws.rs.GET; 
import javax.ws.rs.PUT; 
import javax.ws.rs.Path; 
import javax.ws.rs.PathParam; 
import javax.ws.rs.Produces; 
import javax.ws.rs.core.MediaType; 
import javax.ws.rs.core.Response; 
import javax.ws.rs.core.Response.ResponseBuilder; 
 
import com.dineshonjava.ws.error.BookNotFoundException; 
import com.dineshonjava.ws.rest.GetBooksResponse; 
import com.dineshonjava.ws.xml.Book; 
import com.dineshonjava.ws.xml.PublishedBooks; 
import com.dineshonjava.ws.xml.Student; 
 
/** 
 * @author Dinesh Rajput 
 * 
 */ 
@Path("/order/books") 
public class BookResource { 
 @GET 
 @Produces("text/xml") 
 public GetBooksResponse getBooks() { 
 
 GetBooksResponse response = new GetBooksResponse(); 
 Student student = new Student(); 
 PublishedBooks publishedBooks1; 
 PublishedBooks publishedBooks2; 
 
 // student 
 student.setRollNumber(12345); 
 student.setName("Dinesh Rajput"); 
 student.setCourse("Computer Science"); 
 response.setStudent(student); 
 
 // first book 
 Book book1 = new Book(); 
 book1.setPublishNumber(54321); 
 book1.setPublishDate(new Date()); 
 book1.setBookName("Java"); 
 
 publishedBooks1 = new PublishedBooks(); 
 publishedBooks1.setBookId(77777); 
 publishedBooks1.setDescription("winning lottery ticket"); 
 publishedBooks1.setQuantity((short) 10); 
 publishedBooks1.setUnitPrice(5.00F); 
 
 publishedBooks2 = new PublishedBooks(); 
 publishedBooks2.setBookId(12121212); 
 publishedBooks2.setDescription("Real World Java EE Patterns Rethinking Best Practices"); 
 publishedBooks2.setQuantity((short) 1); 
 publishedBooks2.setUnitPrice(40.40F); 
 
 book1.setPublishedBooks(new PublishedBooks[] { publishedBooks1, publishedBooks2 } ); 
 response.getBooks().add(book1); 
 
 // second book 
 Book book2 = new Book(); 
 book2.setPublishNumber(12345); 
 book2.setPublishDate(new Date()); 
 
 publishedBooks1 = new PublishedBooks(); 
 publishedBooks1.setBookId(787878); 
 publishedBooks1.setDescription("JavaServer Faces 2.0, The Complete Reference"); 
 publishedBooks1.setQuantity((short) 10); 
 publishedBooks1.setUnitPrice(31.49F); 
 
 publishedBooks2 = new PublishedBooks(); 
 publishedBooks2.setBookId(1111111); 
 publishedBooks2.setDescription("Beginning Java EE 6 with GlassFish 3, Second Edition"); 
 publishedBooks2.setQuantity((short) 1); 
 publishedBooks2.setUnitPrice(41.73F); 
 
 book2.setPublishedBooks(new PublishedBooks[] { publishedBooks1, publishedBooks1 } ); 
 response.getBooks().add(book2); 
 
 return response; 
 } 
 
 @GET 
 @Path("{publishNumber}") 
 @Produces(MediaType.TEXT_PLAIN) 
 public Response updateOrder(@PathParam("publishNumber") String publishNumber) throws BookNotFoundException { 
 
 ResponseBuilder response; 
 
 if ("12345".equals(publishNumber)) { 
 response = Response.status(Response.Status.ACCEPTED).entity( "Saved changes to book '" +publishNumber+ "'."); 
 } else { 
 throw new BookNotFoundException("Publisher number '" + publishNumber + 
 "' does not exist."); 
 } 
 return response.build(); 
 } 
 
} 
 
</pre>
<p>Notice the<b> @Produces(&#8220;text/xml&#8221;)</b> annotation, and that the method returns a <b>GetBooksResponse </b>object. Since the <b>GetBooksResponse </b>is annotated with <b>JAXB </b>annotations, <b>JAX-RS </b>will automatically marshal the response to XML.</p>
<p>Next lets add a method that takes part of the object graph as a request parameter. We&#8217;ll start by creating an object to represent the XML root element:<br />
<b>UpdateBookRequest.java</b></p>
<pre class="highlight">package com.dineshonjava.ws.order; 
 
import javax.xml.bind.annotation.XmlElement; 
import javax.xml.bind.annotation.XmlRootElement; 
 
import com.dineshonjava.ws.xml.Book; 
 
/** 
 * @author Dinesh Rajput 
 * 
 */ 
@XmlRootElement 
public class UpdateBookRequest { 
 private Book book; 
 
 @XmlElement 
 public Book getBook() { 
 return book; 
 } 
 
 public void setBook(Book book) { 
 this.book = book; 
 } 
 
} 
 
</pre>
<p>Now lets use this object in a PUT request:</p>
<pre class="highlight">@PUT 
 @Path("{publishNumber}.xml") 
 @Produces(MediaType.TEXT_PLAIN) 
 public Response updateOrder(@PathParam("publishNumber") String publishNumber) throws BookNotFoundException { 
 
 ResponseBuilder response; 
 
 if ("12345".equals(publishNumber)) { 
 response = Response.status(Response.Status.ACCEPTED).entity( "Saved changes to book '" +publishNumber+ "'."); 
 } else { 
 throw new BookNotFoundException("Publisher number '" + publishNumber + 
 "' does not exist."); 
 } 
 return response.build(); 
 } 
</pre>
<p>Since the <b>UpdateBookRequest </b>is annotated with <b>JAXB </b>annotations, <b>JAX-RS</b> will automatically unmarshal it from XML.</p>
<p>This example returns a<i><b> javax.ws.rs.core.Response</b></i> built using <b><i>javax.ws.rs.core.ResponseBuilder.</i></b> You can use <b>ResponseBuilder </b>to set response headers, the status code, and many other things. The response body is called the entity, and you can place anything in it. For example, a String, or a <b>JAXB </b>annotated object graph.</p>
<p>This example also throws an <b>BookNotFoundException</b>:<br />
<b>BookNotFoundException.java</b></p>
<pre class="highlight">package com.dineshonjava.ws.error; 
 
import javax.ws.rs.WebApplicationException; 
import javax.ws.rs.core.MediaType; 
import javax.ws.rs.core.Response; 
import javax.ws.rs.core.Response.Status; 
 
/** 
 * @author Dinesh Rajput 
 * 
 */ 
public class BookNotFoundException extends WebApplicationException { 
 /** 
 * version 
 */ 
 private static final long serialVersionUID = 1L; 
 
 public BookNotFoundException(String message) { 
 super(Response.status(Status.NOT_FOUND).entity(message).type( 
 MediaType.TEXT_PLAIN).build()); 
 } 
} 
 
</pre>
<p>The custom exception extends the <b>WebApplicationException </b>in <b>JAX-RS</b>. There are many constructors in <b>WebApplicationException</b>. I chose to use the one that lets me provide the complete response data.<br />
<i><b>web.xml</b></i></p>
<pre class="highlight"><;?xml version="1.0" encoding="UTF-8"?>; 
<;web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" id="WebApp_ID" version="3.0">; 
 <;display-name>;JaxRSJaxBApps<;/display-name>; 
 <;servlet>; 
 <;servlet-name>;jersey-serlvet<;/servlet-name>; 
 <;servlet-class>; 
 com.sun.jersey.spi.container.servlet.ServletContainer 
 <;/servlet-class>; 
 <;load-on-startup>;1<;/load-on-startup>; 
 <;/servlet>; 
 
 <;servlet-mapping>; 
 <;servlet-name>;jersey-serlvet<;/servlet-name>; 
 <;url-pattern>;/*<;/url-pattern>; 
 <;/servlet-mapping>; 
<;/web-app>; 
</pre>
<p><b>Directory structure for this web application</b>.</p>
<div class="separator" style="clear: both; text-align: center;"><img src="https://dineshonjava.com/wp-content/uploads/2013/06/jaxrsdir.png" border="0" /></div>
<p><b>Now deploy this application to the tomcat server and hit the following urls.</b><br />
<b><br />
</b> <i><b>http://localhost:8181/doj/order/books</b></i></p>
<div class="separator" style="clear: both; text-align: center;"><img src="https://dineshonjava.com/wp-content/uploads/2013/06/out1jaxrs-488x1024.png" border="0" /></div>
<p><i><b>http://localhost:8181/doj/order/books/12345</b></i></p>
<div class="separator" style="clear: both; text-align: center;"><img src="https://dineshonjava.com/wp-content/uploads/2013/06/out2jaxrs.png" border="0" /></div>
<p><b>Download SourceCode and Libs</b><br />
<b><a href="https://sites.google.com/a/dineshonjava.com/dineshonjava/dineshonjava/JaxRSJaxBApps.zip?attredirects=0&;d=1" target="_blank" rel="noopener">JaxRSJaxBApps.zip</a></b></p>
<p><i><b>References</b></i><br />
1.<b> <i><a href="http://docs.oracle.com/javaee/6/tutorial/doc/giepu.html" target="_blank" rel="noopener">JAVA REST Web Services</a></i></b><br />
2. <i><b><a href="http://en.wikipedia.org/wiki/Web_service" target="_blank" rel="noopener">Wikipedia for REST Web Service</a></b></i></p>
<p> ;</p>
<div style="background-color: pink; border-width: thin; text-align: center;"><b><;<;<a href="https://dineshonjava.com/annotations-for-field-and-bean/">Previous </a><;<; || <a href="https://dineshonjava.com/jax-rs-web-service-tutorial/">Index </a>|| >;>;<a href="https://dineshonjava.com/jax-rs-path-uri-matching-example/">Next</a> >;>;</b></div>
<p> ;</p>
</div>
<div class="wp-post-navigation"> 
									 <div class="wp-post-navigation-pre"> 
									 <a href="https://dineshonjava.com/annotations-for-field-and-bean/">Previous</a> 
									 </div> 
									 <div class="wp-post-navigation-next"> 
									 <a href="https://dineshonjava.com/jax-rs-path-uri-matching-example/">Next</a> 
									 </div> 
									</div>
<script type="text/javascript">
jQuery(document).ready(function($) {
 $.post('https://dineshonjava.com/wp-admin/admin-ajax.php', {action: 'mts_view_count', id: '425'});
});
</script>
Strategy Design Patterns We can easily create a strategy design pattern using lambda. To implement…
Decorator Pattern A decorator pattern allows a user to add new functionality to an existing…
Delegating pattern In software engineering, the delegation pattern is an object-oriented design pattern that allows…
Technology has emerged a lot in the last decade, and now we have artificial intelligence;…
Managing a database is becoming increasingly complex now due to the vast amount of data…
Overview In this article, we will explore Spring Scheduler how we could use it by…