|
|
|
[
Permlink
| « Hide
]
Andres March - [12/Mar/05 01:42 AM ]
Please be more specific
I didn't post the Jira issue but this is what I think it means:
Provide the possibility to always regenerate the content (ignore the cache) if the session supplied with the request is tracked via URL (jsessionid exists the URL). Then I could safely include <%=response.encodeUrl()%> links in my cached content. It is safe for both cookie- and url-rewriting sessions. The downside of course is that the content is not served from cache in the latter case. But still way better than a security nightmare. I found some (ugly) workaround, which does more or less the same: <cache:cache key="<%="index_lat" + request.isRequestedSessionIdFromURL()%>" time="30" scope="application" refresh="<%=request.isRequestedSessionIdFromURL()%>"> It reads like this: There are different cache keys for cookie and url-sessions. If it's url-session, the refresh attribute forces to regenerate the content. Let's discuss if this can be done efficiently
Introducing a "isCacheable" method (see
/** * isCacheable is a method allowing subclass to decide if a response id * cachable or not. * * @param request The HTTP servlet request * @param response The HTTP servlet response * @return Returns a boolean indicating if the request can be cached or not. */ protected boolean isCacheable(HttpServletRequest request, HttpServletResponse response) { boolean cachable = ! response.containsHeader("Cache-control"); if (log.isDebugEnabled()) { log.debug("<cache>: the response " + ((cachable) ? "is" : "is not") + " cachable."); } return cachable; } and change the SC_OK check to if ((cacheResponse.getStatus() == HttpServletResponse.SC_OK) && isCacheable(httpRequest, cacheResponse)) { should allow to implement this. Should we split the method into
protected boolean isCacheable(HttpServletRequest request) protected boolean isCacheable(HttpServletResponse response) ? Because we have to check the request at the beginning of CacheFilter by "isFilteredBefore" and at the end of CacheFilter by "getStatus() SC_OK". instead of just doing:
if ((cacheResponse.getStatus() == HttpServletResponse.SC_OK) && isCacheable(httpRequest, cacheResponse)) { I would rather do: if (isCacheable(httpRequest, httpResponse)) { CacheHttpServletResponseWrapper cacheResponse = new CacheHttpServletResponseWrapper(httpResponse, fragmentRequest); chain.doFilter(request, cacheResponse); cacheResponse.flushBuffer(); // Only cache if the response was 200 if ((cacheResponse.getStatus() == HttpServletResponse.SC_OK)) { //Store as the cache content the result of the response cache.putInCache(key, cacheResponse.getContent(), expiresRefreshPolicy); updateSucceeded = true; } } else { chain.doFilter(request, response); } This way we don't use the CacheHttpServletResponseWrapper and don't have to fill up the ResponseContent, if the page is not to be cached. In your code you havn't no data in httpResponse that can be checked, because any response isn't put into the cacheResponse/httpResponse until cache.doFilter is invoked.
Right, httpResponse has no sense at that moment, only httpRequest.
So I assume something like this: if (isCacheable(httpRequest)) { CacheHttpServletResponseWrapper cacheResponse = new CacheHttpServletResponseWrapper(httpResponse, fragmentRequest); chain.doFilter(request, cacheResponse); cacheResponse.flushBuffer(); // Only cache if the response was 200 if ((cacheResponse.getStatus() == HttpServletResponse.SC_OK) && isCacheable(httpResponse)) { //Store as the cache content the result of the response cache.putInCache(key, cacheResponse.getContent(), expiresRefreshPolicy); updateSucceeded = true; } } else { chain.doFilter(request, response); } Correction (cacheResponse instead of httpResponse) :
if (isCacheable(httpRequest)) { CacheHttpServletResponseWrapper cacheResponse = new CacheHttpServletResponseWrapper(httpResponse, fragmentRequest); chain.doFilter(request, cacheResponse); cacheResponse.flushBuffer(); // Only cache if the response was 200 if ((cacheResponse.getStatus() == HttpServletResponse.SC_OK) && isCacheable(cacheResponse)) { //Store as the cache content the result of the response cache.putInCache(key, cacheResponse.getContent(), expiresRefreshPolicy); updateSucceeded = true; } } else { chain.doFilter(request, response); } The option can be implemented with the upcoming isCacheable(httpRequest) method.
Added a new option "nocache" with parameter "sessionIdInURL": Don't cache requests if session id is contained in URL.
| |||||||||||||||||||||||||||||||||||||||