View Javadoc
1   /***
2    * Copyright (C) 2009 TM-Search Community.
3    *
4    * This file is part of TM-Search Services.
5    *
6    * Foobar is free software: you can redistribute it and/or modify
7    * it under the terms of the GNU General Public License as published by
8    * the Free Software Foundation, either version 3 of the License, or
9    * (at your option) any later version.
10   *
11   * Foobar is distributed in the hope that it will be useful,
12   * but WITHOUT ANY WARRANTY; without even the implied warranty of
13   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14   * GNU General Public License for more details.
15   *
16   * You should have received a copy of the GNU General Public License
17   * along with Foobar.  If not, see <http://www.gnu.org/licenses/>.
18   */
19  
20  package eu.europa.tmsearch.services.resources.util;
21  
22  import java.util.Date;
23  
24  import javax.ws.rs.core.Request;
25  import javax.ws.rs.core.Response;
26  import javax.xml.datatype.DatatypeConfigurationException;
27  import javax.xml.datatype.DatatypeFactory;
28  import javax.xml.datatype.XMLGregorianCalendar;
29  
30  import org.apache.log4j.Logger;
31  import org.joda.time.DateTime;
32  
33  /***
34   * Convenience super class for creating cacheable HTTP responses.
35   */
36  public abstract class CacheableResponseSupport {
37  
38      private static Logger log = Logger.getLogger(CacheableResponseSupport.class);
39  
40      /***
41       * A ETagGenerator service interface. Implementation defaults to
42       * MD5ETagGenerator if none is set.
43       */
44      private ETagGenerator eTagGenerator;
45  
46      /***
47       * A time stamp of the resource last modification
48       */
49      private Date lastModified;
50  
51      /***
52       * A time stamp for the resource expiration
53       */
54      private Date expires;
55  
56      /***
57       * Checks if the resource hold by the client is expired
58       * 
59       * @param request
60       *            Jersey request
61       * @param lastModified
62       *            Server-side last modified timestamp for the resource the
63       *            client is requesting
64       * @return Null if not server-side last modified timestamp is provided. Null
65       *         if the client-side resource is expired. An HTTP 304 error if
66       *         client-side resource is not expired.
67       * 
68       * 
69       */
70      public Response checkForStaleResource(Request request) {
71  	if (this.getLastModified() != null) {
72  	    Response.ResponseBuilder responseBuilder = request.evaluatePreconditions(this.getLastModified());
73  	    if (responseBuilder != null) {
74  		log.debug("Client-side instance of requested resource is not expired.");
75  		return responseBuilder.build();
76  	    }
77  	}
78  	log.debug("Client-side instance of requested resource is stale.");
79  	return null;
80      }
81  
82      /***
83       * Checks if the resource hold by the client is valid (expired but not
84       * changed)
85       * 
86       * @param request
87       * @param eTag
88       *            Server-side eTag for the resource the client is requesting
89       * @return Null if not server-side eTag is provided. Null if the client-side
90       *         resource is no longer valid. An HTTP 304 error if client-side
91       *         resource is still valid.
92       * 
93       * 
94       */
95      public Response checkForValidResource(Request request) {
96  	if (this.getETagGenerator().getETag() != null) {
97  	    Response.ResponseBuilder responseBuilder = request.evaluatePreconditions(this.getETagGenerator()
98  		    .getETag());
99  	    if (responseBuilder != null) {
100 		log.debug("Client-side instance of requested resource is still valid.");
101 		return responseBuilder.build();
102 	    }
103 	}
104 	log.debug("Client-side instance of requested resource is no longer valid.");
105 	return null;
106     }
107 
108     public XMLGregorianCalendar getDateTimeStamp(Date date) {
109 	XMLGregorianCalendar calendar = null;
110 	try {
111 	    DatatypeFactory dataTypeFactory = DatatypeFactory.newInstance();
112 	    if (date == null) {
113 		calendar = dataTypeFactory.newXMLGregorianCalendar();
114 	    } else {
115 		calendar = dataTypeFactory.newXMLGregorianCalendar(new DateTime(date).toGregorianCalendar());
116 	    }
117 	} catch (DatatypeConfigurationException e) {
118 	    log
119 		    .error("Exception while generating transaction timestamp. Resource generated without timestamp. Exception: "
120 			    + e);
121 	}
122 	return calendar;
123     }
124 
125     public ETagGenerator setETagGenerator(ETagGenerator tagGenerator) {
126 	eTagGenerator = tagGenerator;
127 	return eTagGenerator;
128     }
129 
130     public ETagGenerator getETagGenerator() {
131 	if (eTagGenerator == null)
132 	    this.eTagGenerator = new MD5ETagGenerator();
133 	return this.eTagGenerator;
134     }
135 
136     public Date getLastModified() {
137 	return lastModified;
138     }
139 
140     public void setLastModified(Date lastModified) {
141 	this.lastModified = lastModified;
142     }
143 
144     public Date getExpires() {
145 	return expires;
146     }
147 
148     public void setExpires(Date expires) {
149 	this.expires = expires;
150     }
151 
152 }