Main

RESTful services with jQuery and Java using JAX-RS and Jersey

NOTE: This is the Java version of this article and its companion app. A PHP version is available here.

This is a more in depth version of my previous post on the same topic. The previous article only covered the HTTP GET method for building RESTful services. This article (and its new companion app) provides an example of building a complete RESTful API using the different HTTP methods:

  • GET to retrieve and search data
  • POST to add data
  • PUT to update data
  • DELETE to delete data

The application used as an example for this article is a Wine Cellar app. You can search for wines, add a wine to your cellar, update and delete wines.


You can run the application here. The create/update/delete features are disabled in this online version. Use the link at the bottom of this post to download a fully enabled version.

The REST API consists of the following methods:

Method URL Action
GET /api/wines Retrieve all wines
GET /api/wines/search/Chateau Search for wines with ‘Chateau’ in their name
GET /api/wines/10 Retrieve wine with id == 10
POST /api/wines Add a new wine
PUT /api/wines/10 Update wine with id == 10
DELETE /api/wines/10 Delete wine with id == 10

 

Implementing the API using JAX-RS

JAX-RS makes it easy to implement this API in Java. You simply create a class defined as follows:

package org.coenraets.cellar;

@Path("/wines")
public class WineResource {

	WineDAO dao = new WineDAO();

	@GET
	@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
	public List<Wine> findAll() {
		return dao.findAll();
	}

	@GET @Path("search/{query}")
	@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
	public List<Wine> findByName(@PathParam("query") String query) {
		return dao.findByName(query);
	}

	@GET @Path("{id}")
	@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
	public Wine findById(@PathParam("id") String id) {
		return dao.findById(Integer.parseInt(id));
	}

	@POST
	@Consumes({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML})
	@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
	public Wine create(Wine wine) {
		return dao.create(wine);
	}

	@PUT @Path("{id}")
	@Consumes({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML})
	@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
	public Wine update(Wine wine) {
		return dao.update(wine);
	}

	@DELETE @Path("{id}")
	@Produces({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML })
	public void remove(@PathParam("id") int id) {
		dao.remove(id);
	}
}

Quick look at the JAX-RS annotations used in this class:

  • @GET, @POST, @PUT, @DELETE: HTTP method the class method responds to.
  • @Path: path the method responds to.
  • @Consumes: type of data the method can take as input. The data will automatically be deserialized into a method input parameter. For example, you can pass a wine object to the addWined() method either as JSON or XML. The JSON or XML representation of a new wine is automatically deserialized into the Wine object passed as an argument to the method.
  • @Produces: One or more response content type(s) the method can generate. The method’s return value will be automatically serialized using the content type requested by the client. If the client didn’t request a specific content type, the first content type listed in the @Produces annotation will be used. For example, if you access http://coenraets.org/rest/wines, you get a list of wines represented as JSON because it is the first content type listed in the @Produces annotation of the findAll() method.

The jQuery client below sends data to the server using JSON (addWine() and updateWine() methods).

The approach you use to actually retrieve the data is totally up to you. In this example, I use a simple DAO, but you can of course use your own data access solution.

Testing the API using cURL

If you want to test your API before using it in a client application, you can invoke your REST services straight from a browser address bar. For example, you could try:

You will only be able to test your GET services that way, and even then, it doesn’t give you full control to test all the content types your API can return.

A more versatile solution to test RESTful services is to use cURL, a command line utility for transferring data with URL syntax.

For example, using cURL, you can test the Wine Cellar API with the following commands:

  • Get all wines returned as default content type:
    curl -i -X GET http://localhost:8080/cellar/rest/wines
    
  • Get all wines returned as xml:
    curl -i -X GET http://localhost:8080/cellar/rest/wines -H 'Accept:application/xml'
    
  • Get all wines with ‘chateau’ in their name:
    curl -i -X GET http://localhost:8080/cellar/rest/wines/search/chateau
    
  • Get wine #5:
    curl -i -X GET http://localhost:8080/cellar/rest/wines/5
    
  • Delete wine #5:
    curl -i -X DELETE http://localhost:8080/cellar/rest/wines/5
    
  • Add a new wine:
    curl -i -X POST -H 'Content-Type: application/json' -d '{"name": "New Wine", "year": "2009"}' http://localhost:8080/cellar/rest/wines
    
  • Modify wine #27:
    curl -i -X PUT -H 'Content-Type: application/json' -d '{"id": "27", "name": "New Wine", "year": "2010"}' http://localhost:8080/cellar/rest/wines/27
    

The jQuery Client

Accessing your API through cURL is cool, but there is nothing like a real application to put your API to the test. So the source code (available for download at the end of this post) includes a simple jQuery client to manage your wine cellar.

Here is the jQuery code involved in calling the services:

function findAll() {
	$.ajax({
		type: 'GET',
		url: rootURL,
		dataType: "json", // data type of response
		success: renderList
	});
}

function findByName(searchKey) {
	$.ajax({
		type: 'GET',
		url: rootURL + '/search/' + searchKey,
		dataType: "json",
		success: renderList
	});
}

function findById(id) {
	$.ajax({
		type: 'GET',
		url: rootURL + '/' + id,
		dataType: "json",
		success: function(data){
			$('#btnDelete').show();
			renderDetails(data);
		}
	});
}

function addWine() {
	console.log('addWine');
	$.ajax({
		type: 'POST',
		contentType: 'application/json',
		url: rootURL,
		dataType: "json",
		data: formToJSON(),
		success: function(data, textStatus, jqXHR){
			alert('Wine created successfully');
			$('#btnDelete').show();
			$('#wineId').val(data.id);
		},
		error: function(jqXHR, textStatus, errorThrown){
			alert('addWine error: ' + textStatus);
		}
	});
}

function updateWine() {
	$.ajax({
		type: 'PUT',
		contentType: 'application/json',
		url: rootURL + '/' + $('#wineId').val(),
		dataType: "json",
		data: formToJSON(),
		success: function(data, textStatus, jqXHR){
			alert('Wine updated successfully');
		},
		error: function(jqXHR, textStatus, errorThrown){
			alert('updateWine error: ' + textStatus);
		}
	});
}

function deleteWine() {
	console.log('deleteWine');
	$.ajax({
		type: 'DELETE',
		url: rootURL + '/' + $('#wineId').val(),
		success: function(data, textStatus, jqXHR){
			alert('Wine deleted successfully');
		},
		error: function(jqXHR, textStatus, errorThrown){
			alert('deleteWine error');
		}
	});
}

// Helper function to serialize all the form fields into a JSON string
function formToJSON() {
	return JSON.stringify({
		"id": $('#id').val(),
		"name": $('#name').val(),
		"grapes": $('#grapes').val(),
		"country": $('#country').val(),
		"region": $('#region').val(),
		"year": $('#year').val(),
		"description": $('#description').val()
		});
}

 

Download the Source Code

The source code for this application is hosted on GitHub here. And here is a quick link to the project download (Eclipse Dynamic Web Project). It includes both the Java and jQuery code for the application.

UPDATE (1/11/2012): A version of this application using Backbone.js at the client-side is also available on GitHub here. You can find more information on the Backbone.js of this application here.

I’m interested in your feedback. Let me know what you think and what your experience has been building RESTful-based applications using Java and jQuery.

Share this Article:

56 Responses to RESTful services with jQuery and Java using JAX-RS and Jersey

  1. Gerd January 5, 2012 at 2:06 pm #

    The best Jersey Rest + JQuery example i´ve seen so far… still searching for an easy solution to solve the “cross-site” – problem… some of yours have any idea what to change on server-side in case of running the JQuery – Client on a different webserver? (eg. webservice is running on http://10.10.10.1:8080/cellar, JQuery – client is running on http://10.10.20.1:8080/index.html)

    • Kenny May 24, 2012 at 9:33 am #

      Hi Gerd
      I’ve been running into the cross-site problem aswel and after a lot of research found a few solutions:

      - JSON-P can be used for GET requests ONLY. Also note that it is not very secure.
      - CORS is probably the best way other then using a proxy. (Basically you add the correct headers to your requests and replies.)

      Hope this helps.
      Cheers
      Kenny

    • Alex August 13, 2012 at 1:32 pm #

      Hi,

      “(Basically you add the correct headers to your requests and replies.)”
      below is an example how to add the header to your response:

      @GET
      @Produces(MediaType.APPLICATION_JSON)
      public Response getFooBar() {
      String json = “”{foo: \”bar\”}”;
      return Response.ok(json).header(“Access-Control-Allow-Origin”, “*”).build();
      }

      • ThonyFD November 14, 2012 at 5:51 pm #

        Hi Alex, I’have a problem Access-Control-Allow-Origin, and your comment was very ussefull for me!

        Regards

        Note: sorry for my english

  2. Carlos Martins February 16, 2012 at 10:14 am #

    Hi Christophe. As always, a great sample! How would you work the authentication and the security layer on the REST?
    How would you work the login in html, and assure that all REST invocations are validated and are secure?
    Regards

  3. MeanHouse March 7, 2012 at 9:01 am #

    Hi,

    At first let me thank you for putting the nicest example of Webservice that is done using REST/Jersey.
    However, my question is not regarding the service, but in database connectivity. You have used mysql as your database and so on, I would like to use Oracle, but the problem with the connection string,
    my database name is, Orcl, name: system and password: sa1234, but don’t what would be the syntax for putting the data.

  4. MeanHouse March 7, 2012 at 9:01 am #

    Hi,

    At first let me thank you for putting the nicest example of Webservice that is done using REST/Jersey.
    However, my question is not regarding the service, but in database connectivity. You have used mysql as your database and so on, I would like to use Oracle, but the problem with the connection string,
    my database name is, Orcl, name: system and password: sa1234, but don’t what would be the syntax for putting the data. Can you please share your thoughts, how i can use Oracle database connectivity in your code.

  5. DS March 28, 2012 at 8:40 pm #

    Awesome Example !!!!!! Helped me a lot … Thanks,Thanks,Thanks,Thanks. :-)

  6. Tamil April 9, 2012 at 12:44 pm #

    Hi,
    Thanks for a simple and elegant example for RESTful service. I have one question,
    what if the ‘Wine’ object is modified later and a group of people need the initial version of ‘Wine’ and a different group need the newer version of ‘Wine’?
    Bottomline, how to deal with versions of ‘Wine’ object? I hate to use query params, that may not be valid for POST, I might use PUT instead, still not an elegant solution.
    Your advise please.

    Thanks much,
    Tamil

  7. Shailendra kumar May 17, 2012 at 12:49 pm #

    Really good article. Thanks for this article and the source code. The example application worked like a charm.

  8. Ashu sharma May 25, 2012 at 9:34 pm #

    I can’t make this example run beyond the static index.html and main.js. I tried in Eclipse and then in NetBeans with both Tomcat and Glassfish. There seems to some errors in terms of URIs for the RESTFul Webservices. Context was not setup in Glassfish and Tomcat is also not going any further.
    I like the example and there is no compilation errors but some how it needs a lot of work around to make it run end to end.

  9. Larry June 3, 2012 at 7:40 pm #

    I deployed to tomcat, and no data populated the web page.

    Did I dod something wrong?

  10. nick June 29, 2012 at 11:09 am #

    Bit of a simple question, but how do you open the java project in eclipse (do I need to create a project and import the files)

    thanks
    Nick

  11. javascript forum August 7, 2012 at 9:17 am #

    Ahaa, its nice discussion on the topic of this piece of writing at this place at this blog,
    I have read all that, so now me also commenting at this place.

  12. Mahboob Ur Rasheed August 9, 2012 at 5:37 pm #

    Good Job Christophe :)… I am waiting Your article about security concerns about REST/JSON

  13. Maran August 10, 2012 at 12:20 pm #

    Hi,
    I am a newbie to jquery and I tried the eclipse project and configure my database as defined in the readme file.
    But while creating a ‘New Wine’ i got this error “addWine error: error”. Need help…

  14. Tim August 16, 2012 at 9:21 pm #

    Awesome tutorial, thank you!

  15. Mahadevan August 19, 2012 at 10:55 am #

    Thanks for providing this example and the example looks nice. But I am able to get the proper output when I use get or delete. But for post or put I am getting problem. When I send the json form using, json.stringify(), the service is not taking up the json, I am sending and I am getting an error message. Can someone who has run this successfully help me send me the code with which he is successful? Thanks in advance,

  16. Mahadevan August 20, 2012 at 2:15 pm #

    I have managed to workout the needful to get the example working. But I needed to make some modifications. Thanks for providing this example.

  17. kaneyip September 6, 2012 at 9:50 am #

    really appreciate the code especially for new beginner like me…thanks alot

  18. Gian October 31, 2012 at 11:05 am #

    Hi,
    I have a problem with fields on the DB that contain the underscore “_” character in the field name.
    Jersey seems to ignore those fields and no data is stored on the DB …
    Any suggestion ?

  19. al November 14, 2012 at 4:33 pm #

    Hi Christophe, the code highlighter doesn’t work properly on the entire website including all ther posts, wanted to let you know.

  20. N White November 15, 2012 at 8:00 pm #

    Nice post.

    If you wanted to have a slightly more ‘RESTful’ API you could implement the search functionality with query params on the Wine resource like so:

    /api/wines?name=*Chateau*

    Style wise /api/wines/search is more of an RPC approach then a RESTful one.

    • Mars009 December 17, 2012 at 7:08 am #

      Thanks for the great tutorial! I have a quick question though, how are the js files and html files being loaded into the browser? Setting the src of the is caught by the servlet and prepends the request for the resources.

  21. Jack Rooney December 27, 2012 at 12:52 am #

    Hi Christophe ,

    Thanks a lot for the wonderful article. However, i have a question. when I issue a POST using the curl command that you have listed, it gives me a HTTP 1.1 404 Not Found error. Can you kindly have a look into this and let me know.

    Thanks again for this wonderful tutorial.

    Regards,
    Jack

  22. Avivkri December 30, 2012 at 5:14 pm #

    Great example. Helped me a lot in doing a restful service application

  23. Luis January 10, 2013 at 1:41 pm #

    It works! Simple and clear!

    Thanks!

  24. Gopal January 25, 2013 at 12:30 pm #

    is it possible to send custom object as a @Pathparam using get method and i need json as output using RESTFUL.

    I mean instead of sending all the parameters URI like —-> custom/1/aaa/addr shall we custom/pojo

    Client Side:

    class Pojo{
    int id=1;
    String name=”aaa”;
    String addr=”addr”;
    //setter & getters

    }

    Main class:

    public static void main(String… a)
    {
    Pojo pojo = new Pojo();

    System.out.println(service.path(“rest”).path(“custom/pojo”).accept(MediaType.APPLICATION_JSON).get(String.class));
    }

    server side:

    @Path(“/custom”)
    class Custom
    {
    @GET
    @Produces({ MediaType.APPLICATION_XML, MediaType.APPLICATION_JSON })
    @Path(“{pojo}”)
    public Pojo getJsonOutput(@PathParam(“pojo”) Pojo p) {
    if(1==p.getId() && “aaa”.equals(p.getName()) && “addr”.equals(p.getAddr())

    return new Pojo();

    else

    return null;
    }
    }

    class Pojo{
    int id=1;
    String name=”aaa”;
    String addr=”addr”;
    String firstName=”aaa”;
    String lastName=”bbb”;
    String firstAddr=”ccc”;
    String lastAddr=”ddd”;
    String mobnumber=”123457896″;

    //Setters & Getters

    }

  25. Raju January 26, 2013 at 6:34 pm #

    Hi, nice t utorial. But my request is can u provide this example using spring3. I am gladful if u give me spring 3 hibernate mysql restful webservices (jquery and javascript not necessary)

  26. Zim February 12, 2013 at 9:34 pm #

    Excellent tutorial, really good for those who have everything in place but need an example that plugs it all together

  27. Escort in Thailand February 13, 2013 at 9:42 am #

    I got this web site from my pal who told me about this site and at the moment this
    time I am browsing this site and reading very informative articles here.

  28. article February 13, 2013 at 5:14 pm #

    Hello mates, nice post and fastidious urging commented here, I am actually enjoying by these.

  29. Santiago H February 13, 2013 at 5:47 pm #

    Hi im not sure but how can I implement MVC with rest? can I use push or pull?

    Thanks in advance

  30. imomi February 14, 2013 at 2:19 pm #

    Can I perform partial updates to the Wine object?

    For example: return JSON.stringify({
    “id”: $(‘#id’).val(),
    “name”: $(‘#name’).val(),
    “grapes”: $(‘#grapes’).val()
    });

  31. shakthydoss February 17, 2013 at 6:43 am #

    Hi All ,
    Is there any way to pass multiple json objects from jquery to call a rest service method that has multiple parameter.

    eg :
    @Consumes({ MediaType.APPLICATION_JSON, MediaType.APPLICATION_XML})
    public Wine compareWine(Wine wine1 , Wine wine2) {
    return dao.create(wine1);
    }

  32. regow February 28, 2013 at 9:32 pm #

    Thank you, for your tutorial. I am using jquery dataTables, how can I persuade Jersey to provide data in a format like this:
    { “aaData”: [
    [ "A", "Internet Explorer 4.0", "Win 95+", 4, "X" ],
    [ "B", "Internet Explorer 5.0", "Win 95+", 5, "C" ] ] }
    which is the format that dataTables requires.

  33. louis armstrong March 2, 2013 at 4:15 pm #

    It’s impressive that you are getting ideas from this article as well as from our dialogue made at this place.

  34. michael kors mens watches March 8, 2013 at 6:53 am #

    It’s really a nice and useful piece of info. I’m
    glad that you simply shared this useful information with us.
    Please keep us up to date like this. Thanks for sharing.

  35. endocrine disruption research March 13, 2013 at 9:59 am #

    I don’t know if it’s just me or if perhaps everybody else experiencing issues with your blog.
    It appears like some of the text on your posts are running off the screen.
    Can somebody else please provide feedback and let me know if this is
    happening to them as well? This could be a problem with
    my browser because I’ve had this happen before. Appreciate it

  36. tv shows March 16, 2013 at 3:37 am #

    Fantastic blog! Do you have any suggestions for aspiring writers?
    I’m planning to start my own blog soon but I’m a little lost on
    everything. Would you advise starting with a free platform
    like WordPress or go for a paid option? There are so many choices out there that I’m totally confused .. Any recommendations? Many thanks!

  37. Annett March 19, 2013 at 2:01 pm #

    My relatives always say that I am wasting my time here at
    net, except I know I am getting familiarity everyday by reading
    such good content.

  38. london escorts March 25, 2013 at 5:36 am #

    Hello, just wanted to mention, I enjoyed this article.
    It was inspiring. Keep on posting!

  39. Ahmad April 10, 2013 at 2:28 pm #

    Can you please guide me how can I place the Jersey implementation JAR’s out of the project? I mean can I place these jars on a common path for all the JAX-RS web services I have?

  40. Xplorer April 27, 2013 at 8:21 am #

    its a beautiful example ….. tests r running great but i m unable 2 run the Jquery client … is there any errors… i m not geting the list of wines … help wud b apppreciable

  41. www.4view.me May 14, 2013 at 4:36 pm #

    Truly no matter if someone doesn’t know afterward its up to other viewers that they will assist, so here it occurs.

Trackbacks/Pingbacks

  1. RESTful services with jQuery and Java using JAX-RS and Jersey - hostinghanger.in | hostinghanger.in - December 1, 2011

    [...] Follow this link: RESTful services with jQuery and Java using JAX-RS and Jersey [...]

  2. Backbone.js Wine Cellar Tutorial — Part 2: CRUD - December 7, 2011

    [...] A PHP version of these services (using the Slim framework) is available as part of the download. A similar Java version of the API (using JAX-RS) is available as part of this post. [...]

  3. Backbone.js Wine Cellar Tutorial — Part 1: Getting Started - December 7, 2011

    [...] I also blogged a non-Backbone version of the application here (Java back-end) and here (PHP back-end), which you can look at for [...]

  4. Using Backbone.js with a RESTful Java Back-End - January 10, 2012

    [...] a previous post, RESTful services with jQuery and Java using JAX-RS and Jersey, I demonstrated how to build a RESTful API using JAX-RS and Jersey, and how to build a jQuery [...]

  5. Confluence: Mobile Devices Development - January 15, 2012

    PHP…

    Yii framework…

  6. The LiveCycle Post | Using Backbone.js with a RESTful Java Back-End - January 17, 2012

    [...] a previous post, RESTful services with jQuery and Java using JAX-RS and Jersey, I demonstrated how to build a RESTful API using JAX-RS and Jersey, and how to build a jQuery [...]

  7. One Java Service POJO for AMF/XML/JSON with Spring BlazeDS & Jersey JAX-RS | Web App Solution Blog - March 23, 2012

    [...] was reading Christophe Coenraets’ blog post on RESTful services with jQuery and Java using JAX-RS and Jersey and it got me thinking…in order to serve technology agnostic Java Service POJOs to [...]

  8. Rest webservice Jersey Backbone jquery « Life in USA - August 5, 2012

    [...] RESTful services with jQuery and Java using JAX-RS and Jersey Like this:LikeBe the first to like this. [...]

  9. Backbone.js and Twitter Bootstrap tutorials - Adriel Blog | Adriel Blog - August 6, 2012

    [...] http://coenraets.org/blog/2011/12/restful-services-with-jquery-and-java-using-jax-rs-and-jersey/ Client: [...]

  10. Creating a REST API using Node.js, Express, and MongoDB - October 2, 2012

    [...] Express, and MongoDB to rewrite a RESTful API I had previously written in Java and PHP with MySQL (Java version, PHP version), and I thought I’d share the [...]

  11. JAX-RS Form Validation -Highlight input text field and display validation message | BlogoSfera - April 7, 2013

    [...] I have a sample CRUD application, The application used is a Wine Cellar app. You can search for wines, add a wine to your cellar, update and delete wines. I got it from RESTful services with jQuery and Java using JAX-RS and Jersey. [...]

Leave a Reply


4 + = 7

Powered by WordPress. Designed by Woo Themes