HttpContent httpContent;
CachedHttpContentState state = null;
HTTPResponseAccessor accessor;
boolean cacheable = false;
ProviderResult result = null;
try {
// check if validation headers can be added
if (entry != null) {
final CachedHttpContentState existingState =
(CachedHttpContentState) entry.getExtensionObject();
if (existingState != null) {
// this is a validation
// set the If-Modified-Since header using the stored
// last modified value (if there is any)
final Time lastModified = existingState.getLastModified();
if (lastModified != null) {
final String lastModifiedAsString;
// SimpleDateFormat is not thread safe
synchronized (RFC1123) {
lastModifiedAsString = RFC1123.format(
new Date(lastModified.inMillis()));
}
final Header header =
new HeaderImpl(HeaderNames.IF_MODIFIED_SINCE_HEADER);
header.setValue(lastModifiedAsString);
executor.addRequestHeader(header);
}
// set the If-None-Match header with the eTag value, if
// there is any
final String eTag = existingState.getETag();
if (eTag != null && eTag.trim().length() > 0) {
final Header header =
new HeaderImpl(HeaderNames.IF_NONE_MATCH_HEADER);
header.setValue(eTag);
executor.addRequestHeader(header);
}
}
}
// record the request time
final CachedHttpContentStateBuilder builder =
new CachedHttpContentStateBuilder();
builder.setRequestTime(clock.getCurrentTime());
accessor = executor.execute();
// record response time
builder.setResponseTime(clock.getCurrentTime());
// process the response
builder.setMethodAccessor(
new HttpResponseHeaderAccessorWrapper(accessor));
httpContent = new HTTPResponseAccessorWrapper(accessor);
final int statusCode = accessor.getStatusCode();
if (isStatusCodeCachable(statusCode)) {
state = builder.build();
if (state != null && state.isCacheable()) {
httpContent = new CachedHttpContent(httpContent, state, clock,
new CacheableDependency(key, state, clock,
cache, this));
cacheable = true;
}
} else if (statusCode == 304) {
// 304 Not Modified
// it is only possible if it is a revalidation cache entry holds
// the exisiting cache config as an extension object
state = builder.merge(
((CachedHttpContentState) entry.getExtensionObject()));
cacheable = state.isCacheable();
// entry must have a CachedHttpContent
final CachedHttpContent originalContent =
(CachedHttpContent) entry.getValue();
originalContent.combineHeaders(httpContent, state);
httpContent = originalContent;
}
result = new ProviderResult(httpContent, group, cacheable, state);
} catch (Throwable e) {
// Yep, thats right. We do want to catch all exceptions. Return a
// 500 error (internal server error).
try {
httpContent = new HTTPResponseAccessorWrapper(
ERROR_500_RESPONSE_ACCESSOR);
} catch (HTTPException e1) {
throw new IllegalStateException(
"Wrapping ERROR_500 Accessor failed");
}
result = new ProviderResult(e, group, false, null);
}
return result;
}