ETag Easy With RESTEasy

  •        0
  

We aggregate and tag open source projects. We have collections of more than one million projects. Check out the projects section.



RESTEasy is a JBoss project that provides various frameworks to help you build RESTful Web Services and RESTful Java applications. It comprises of frameworks for mock, embeddable server, rest client, proxy servers, logging and so on. In this article, we will walk-through ETag implementation and show the behaviour related to ETag done by rest easy framework. Example is developed using RESTEasy 3.7 and deployed in tomcat as RESTEasy framework is portable.

This article is a continuation of previous article

RESTEasy - A guide to implement CRUD Rest API

RESTEasy Advanced Guide - Filters and Interceptors

ETag:

ETag is an identifier passed in HTTP header for web cache validation and conditional requests for GET and PUT. There are two HTTP request header parameters like If-Match and If-None-Match to accomplish the functionalities of ETag. Read wiki for more info about ETag.

  • If-Match header ETag value matches in GET/PUT request it will produce/update the response otherwise preconditions failed message with status code 412
  • If-None-Match header ETag value doesn't match in GET/PUT request, it produces/update the response otherwise it returns the 304(Not modified)

Maven Dependency:

Start a maven web application project and add the following dependencies for rest easy framework:

<properties>
    <resteasy-version>3.7<resteasy-version>
</properties>

<dependency>
    <groupId>org.jboss.resteasy</groupId>
    <artifactId>resteasy-jaxrs</artifactId>
    <version>${resteasy-version}</version>
</dependency>
<dependency>
    <groupId>org.jboss.resteasy</groupId>
    <artifactId>resteasy-servlet-initializer</artifactId>
    <version>${resteasy-version}</version>
</dependency>

To marshall and unmarshall Java entity, jettison provider need to be include in the dependency list.

<dependency>
   <groupId>org.jboss.resteasy</groupId>
   <artifactId>resteasy-jettison-provider</artifactId>
   <version>${resteasy-version}</version>
</dependency>

 

Create Service:

Let's create a employee model and rest service for create and update and see how it works.

  @XmlRootElement
  public class Employee {

      private int employeeId;
      private String employeeName;
      private long mobileNumber;
      private Date lastModifiedDate;

      public Employee() {
         this.lastModifiedDate = new Date();
      }

      public Employee(int employeeId, String employeeName, Long mobileNumber) {
         this.employeeId = employeeId;
         this.employeeName = employeeName;
         this.mobileNumber = mobileNumber;
         this.lastModifiedDate = new Date();
     }

      public int getEmployeeId() {
         return employeeId;
      }

      public void setEmployeeId(int employeeId) {
          this.employeeId = employeeId;
      }

      public String getEmployeeName() {
         return employeeName;
      }

      public void setEmployeeName(String employeeName) {
          this.employeeName = employeeName;
      }

      public long getMobileNumber() {
         return mobileNumber;
      }

      public void setMobileNumber(long mobileNumber) {
         this.mobileNumber = mobileNumber;
      }

      public Date getLastModifiedDate() {
         return this.lastModifiedDate;
      }

      public void updateDate() {
         this.lastModifiedDate = new Date();
      }
}

Employee rest service to get employee by id and patch request to update the mobile number for the employee. ETag has been generated using modified date field in employee model and evaluatePreconditions will do the magic of ETag validation. Add this EmployeeService class also singletons in ApplicationMain class.

 @Path("employees")
 public class EmployeeService {
 private static Map<Integer, Employee> employees = new HashMap<Integer, Employee>();
 static {
   employees.put(1, new Employee(1, "Nagappan", 9600030004));
 }

 @GET
 @Path("/{id}")
 @Produces({MediaType.APPLICATION_JSON})
 public Response getUserById(@PathParam("id") int id, @Context Request req) {
      CacheControl cc = new CacheControl();
      cc.setMaxAge(10);
      System.out.println(employees.get(id).getLastModifiedDate());

      EntityTag etag = new EntityTag(employees.get(id).getLastModifiedDate().hashCode()+"");
      Response.ResponseBuilder resp = req.evaluatePreconditions(etag);
      if (resp != null) {
           /* response code 412 for precondition failed.. */
           return resp.cacheControl(cc).tag(etag).build();
      } else {
         System.out.println("Pre-conditon matched");
      }

      System.out.println("generating response");
      return Response.status(200).entity(employees.get(id)).cacheControl(cc).tag(etag).build();
 }

 @PATCH
 @Path("/{id}/mobilenumber/{mobilenumber}")
 @Produces({MediaType.APPLICATION_JSON})
 public Response updateUserById(@PathParam("id") int id, @PathParam("mobilenumber") String mobilenumber, @Context Request req) {
       CacheControl cc = new CacheControl();
       cc.setMaxAge(1000);
       cc.setMustRevalidate(true);
       EntityTag etag = new EntityTag(employees.get(id).getLastModifiedDate().hashCode()+"");
       Response.ResponseBuilder resp = req.evaluatePreconditions(etag);
       if (resp!=null) {
           return resp.tag(etag).build();
       }
       employees.get(id).setMobileNumber(Long.parseLong(mobilenumber));
       employees.get(id).updateDate();
       return Response.status(200).entity("mobile number updated successfully").cacheControl(cc).build();
 }
}

Register service

Rest service registered to standalone Servlet container 3.0 ServletContainerInitializer by extending jax-rs Application class. ServletContainerInitializer is a programmatic way of registering servlets and services at the startup phase of webapplication

  @ApplicationPath("/rest")
  public class ApplicationMain extends Application {
  private Set<Object> singletons = new HashSet<>();

  public ApplicationMain() {
      singletons.add(new EmployeeService());
  }

  @Override
  public Set<Object> getSingletons() {
     return singletons;
   }
}

Now when we hit the employee get request, it responds with ETag value.

curl -i -X GET http://localhost:8080/resteasyexamples/rest/employees/1
HTTP/1.1 200
Cache-Control: no-transform, max-age=10
ETag: "-396822946"
Content-Type: application/json
Transfer-Encoding: chunked
Date: Fri, 24 May 2019 05:38:50 GMT

{"employee":{"employeeId":1,"employeeName":"Nagappan","mobileNumber":9600030004}}

 

Update the employee record only if it matches the ETag value

curl --header 'If-Match: -396822946' -i -X PATCH http://localhost:8080/resteasyexamples/rest/employees/1/mobilenumber/9000050002
HTTP/1.1 200
Content-Type: application/json
Content-Length: 34
Date: Fri, 24 May 2019 05:43:37 GMT

mobile number updated successfully

Then get the employee record to see the change has been affected. Here If-None-Match header has been used because previous update request would have changed the ETag so it should not be that value. Returned response has the change in Mobile number.

curl --header 'If-None-Match: -396822946' -i -X GET http://localhost:8080/resteasyexamples/rest/employees/1
HTTP/1.1 200
Cache-Control: no-transform, max-age=10
ETag: "-396510836"
Content-Type: application/json
Transfer-Encoding: chunked
Date: Fri, 24 May 2019 05:44:46 GMT

{"employee":{"employeeId":1,"employeeName":"Nagappan","mobileNumber":9000050002}}

If we give the above returned tag with header tag, if none match value, for get request we will get status code 304 resource not modified.

curl --header 'If-None-Match: -396510836' -i -X GET http://localhost:8080/resteasyexamples/rest/employees/1
HTTP/1.1 304
Cache-Control: no-transform, max-age=10
ETag: "-396510836"
Date: Fri, 24 May 2019 05:46:17 GMT

Likewise incorrect resource ETag given in if-match header, it will return precondition failed saying the resource with that ETag is not available.

curl --header 'If-Match: -396510835' -i -X GET http://localhost:8080/resteasyexamples/rest/employees/1
HTTP/1.1 412
Cache-Control: no-transform, max-age=10
ETag: "-396510836"
Content-Length: 0
Date: Fri, 24 May 2019 05:49:48 GMT

 

Reference:

RESTEasy Framework - https://resteasy.github.io/index.html

Code samples - https://github.com/nagappan080810/resteasy_workbook

 


Sponsored:
To find embedded technology information about MCU, IoT, AI etc Check out embedkari.com.


   

Nagappan is a techie-geek and a full-stack senior developer having 10+ years of experience in both front-end and back-end. He has experience on front-end web technologies like HTML, CSS, JAVASCRIPT, Angular and expert in Java and related frameworks like Spring, Struts, EJB and RESTEasy framework. He hold bachelors degree in computer science and he is very passionate in learning new technologies.

Subscribe to our newsletter.

We will send mail once in a week about latest updates on open source tools and technologies. subscribe our newsletter



Related Articles

RESTEasy Advanced Guide - Filters and Interceptors

  • resteasy rest-api filters interceptors java

RESTEasy is JAX-RS 2.1 compliant framework for developing rest applications. It is a JBoss project that provides various frameworks to help you build RESTful Web Services and RESTful Java applications. It is a fully certified and portable implementation of the JAX-RS 2.1 specification, a JCP specification that provides a Java API for RESTful Web Services over the HTTP protocol.

Read More


RESTEasy - A guide to implement CRUD Rest API

  • resteasy rest-api java framework

RESTEasy is a JBoss project that provides various frameworks to help you build RESTful Web Services and RESTful Java applications. It is a fully certified and portable implementation of the JAX-RS 2.1 specification, a JCP specification that provides a Java API for RESTful Web Services over the HTTP protocol. It is licensed under the Apache 2.0 license.

Read More


RESTEasy Advanced guide - File Upload

  • resteasy rest-api file-upload java

RESTEasy is a JBoss project that provides various frameworks to help you build RESTful Web Services and RESTful Java applications. It is a fully certified and portable implementation of the JAX-RS 2.1 specification, a JCP specification that provides a Java API for RESTful Web Services over the HTTP protocol. It is licensed under the ASL 2.0.

Read More


Introduction to Light 4J Microservices Framework

  • light4j microservice java programming framework

Light 4j is fast, lightweight, secure and cloud native microservices platform written in Java 8. It is based on pure HTTP server without Java EE platform. It is hosted by server UnderTow. Light-4j and related frameworks are released under the Apache 2.0 license.

Read More


JWT Authentication using Auth0 Library

  • java jwt authentication security

Json Web Token shortly called as JWT becomes defacto standard for authenticating REST API. In a traditional web application, once the user login credentials are validated, loggedin user object will be stored in session. Till user logs out, session will remain and user can work on the web application without any issues. Rest world is stateless, it is difficult to identify whether the user is already authenticated. One way is to use authenticate every API but that would be too expensive task as the client has to provide credentials in every API. Another approach is to use token.

Read More



Angular Service Workers Usage Guide

  • angular service-worker offline-app

Web developers come across scenarios like web application completely breaks when workstation goes offline. Likewise to get into our application, every time we need to open a browser and then access it. Instead if it is in app, it will be easy to access for end-user. Push notifications similar to email client need to be done through web application. All these are addressed by a magic called service worker.

Read More


An introduction to web cache proxy server - nuster

  • web-cache proxy-server load-balancer

Nuster is a simple yet powerful web caching proxy server based on HAProxy. It is 100% compatible with HAProxy, and takes full advantage of the ACL functionality of HAProxy to provide fine-grained caching policy based on the content of request, response or server status. This article gives an overview of nuster - web cache proxy server, its installation and few examples of how to use it.

Read More


Light4j Cookbook - Rest API, CORS and RDBMS

  • light4j sql cors rest-api

Light 4j is a fast, lightweight and cloud-native microservices framework. In this article, we will see what and how hybrid framework works and integrate with RDMS databases like MySQL, also built in option of CORS handler for in-flight request.

Read More


AbanteCart - Easy to use open source e-commerce platform, helps selling online

  • e-commerce ecommerce cart

AbanteCart is a free, open source shopping cart that was built by developers with a passion for free and accessible software. Founded in 2010 (launched in 2011), the platform is coded in PHP and supports MySQL. AbanteCart’s easy to use admin and basic layout management tool make this open source solution both easy to use and customizable, depending on the skills of the user. AbanteCart is very user-friendly, it is entirely possible for a user with little to no coding experience to set up and use this cart. If the user would be limited to the themes and features available in base AbanteCart, there is a marketplace where third-party extensions or plugins come to the rescue.

Read More


Getting Started on Undertow Server

  • java web-server undertow rest

Undertow is a high performing web server which can be used for both blocking and non-blocking tasks. It is extermely flexible as application can assemble the parts in whatever way it would make sense. It also supports Servlet 4.0, JSR-356 compliant web socket implementation. Undertow is licensed under Apache License, Version 2.0.

Read More


Solr vs Elastic Search

  • full-text-search search-engine lucene solr elastic-search

Solr and Elastic Search are built on top of Lucene. Both are open source and both have extra features which makes programmer life easy. This article explains the difference and the best situation to choose between them.

Read More


PrestaShop - A feature rich Open Source eCommerce solution

PrestaShop is an Open Source eCommerce Solution. It comes complete with over 310 features that have been carefully developed to assist business owners in increasing sales with virtually little effort. It is being used in more than 150,000 online stores.

Read More


Push Notifications using Angular

  • angular push-notifications notifications

Notifications is a message pushed to user's device passively. Browser supports notifications and push API that allows to send message asynchronously to the user. Messages are sent with the help of service workers, it runs as background tasks to receive and relay the messages to the desktop if the application is not opened. It uses web push protocol to register the server and send message to the application. Once user opt-in for the updates, it is effective way of re-engaging users with customized content.

Read More


Web based commenting system. Embed directly in to your site

  • comment free commenting-system

Comments are very important for a blog or website to get feedback from their users. Comments could be threaded where users could be discuss and post reply to the comment. Here we going discuss about the most popular and widely used free commenting system. You need to embed their javascript code in your every page and it will take care the rest of the task.

Read More


Lucene Vs Solr

  • searchengine lucene solr

Lucene is a search library built in Java. Solr is a web application built on top of Lucene. Certainly Solr = Lucene + Added features. Often there would a question, when to choose Solr and when to choose Lucene.

Read More


Caching using Ehcache Java Library

  • ehcache cache java map key-value

Ehcache from Terracotta is one of Java's most widely used Cache. It is concurrent and highly scalable. It has small footprint with SL4J as the only dependencies. It supports multiple strategies like Expiration policies, Eviction policies. It supports three storage tiers, heap, off-heap, disk storage. There are very few caching products supports multiple tier storage. If you want to scale, you cannot store all items in heap there should be support for off-heap and disk storage. Ehcache is licensed under Apache 2.0. In this article, we can see about basic usage of Ehcache.

Read More


An Introduction to the UnQLite Embedded NoSQL Database Engine

  • database nosql embedded key-value-store

UnQLite is an embedded NoSQL database engine. It's a standard Key/Value store similar to the more popular Berkeley DB and a document-store database similar to MongoDB with a built-in scripting language called Jx9 that looks like Javascript. Unlike most other NoSQL databases, UnQLite does not have a separate server process. UnQLite reads and writes directly to ordinary disk files. A complete database with multiple collections is contained in a single disk file. The database file format is cross-platform, you can freely copy a database between 32-bit and 64-bit systems or between big-endian and little-endian architectures.

Read More


MailHog - Web and API based SMTP testing

  • smtp-testing testing-tool smtp test automation email-server email

Most of the projects will have a requirement of sending and receiving mails. We have mentioned about GreenMail - Email Test Framework, in our previous article about API based SMTP testing. In this article, we discuss about MailHog - Web and API based SMTP testing. You send out a mail from your code and you can check it via web visually and also via API. Those who do API testing can check via API. Developers may want to visually verify the format of the mail. MailHog is a best bet for SMTP testing.

Read More


Restrict Solr Admin Access

  • solr searchengine tips

Solr is a search engine built on top of Lucene. It supports REST interface and has lot of built-in capabilities. Solr package has Admin UI interface which has support to perform query and even delete the contents of the index. If you are using Solr in production then you may need to restrict access. I saw couple of questions in the group related to this topic. Thought to write an article explaining few tips to restrict the user access to Solr admin UI.

Read More


An introduction to LucidWorks Enterprise Search

  • lucene solr search engine enterprise

Lucidworks Enterprise search solution is built on top of Apache Solr. It scales seamlessly w/sub-second response times under extreme query loads for multi-billion document collections. It has user friendly UI, which does all the job of configuration and search.

Read More