/** * Returns a request to unconditionally validate a cache entry with * the origin. In certain cases (due to multiple intervening caches) * our cache may actually receive a response to a normal conditional * validation where the Date header is actually older than that of * our current cache entry. In this case, the protocol recommendation * is to retry the validation and force syncup with the origin. * @param request client request we are trying to satisfy * @return an unconditional validation request */ public T buildUnconditionalRequest(final T request) { final T newRequest = messageCopier.copy(request); newRequest.addHeader(HeaderConstants.CACHE_CONTROL,HeaderConstants.CACHE_CONTROL_NO_CACHE); newRequest.addHeader(HeaderConstants.PRAGMA,HeaderConstants.CACHE_CONTROL_NO_CACHE); newRequest.removeHeaders(HeaderConstants.IF_RANGE); newRequest.removeHeaders(HeaderConstants.IF_MATCH); newRequest.removeHeaders(HeaderConstants.IF_NONE_MATCH); newRequest.removeHeaders(HeaderConstants.IF_UNMODIFIED_SINCE); newRequest.removeHeaders(HeaderConstants.IF_MODIFIED_SINCE); return newRequest; }
newRequest.addHeader(HeaderConstants.CACHE_CONTROL, HeaderConstants.CACHE_CONTROL_MAX_AGE + "=0");
@Test public void testBuildUnconditionalRequestDoesNotUseIfUnmodifiedSince() throws Exception { request.addHeader("If-Unmodified-Since", DateUtils.formatDate(new Date())); final HttpRequest result = impl.buildUnconditionalRequest(request); Assert.assertNull(result.getFirstHeader("If-Unmodified-Since")); }
@Test public void testBuildUnconditionalRequestDoesNotUseIfModifiedSince() throws Exception { request.addHeader("If-Modified-Since", DateUtils.formatDate(new Date())); final HttpRequest result = impl.buildUnconditionalRequest(request); Assert.assertNull(result.getFirstHeader("If-Modified-Since")); }
@Test public void testBuildUnconditionalRequestDoesNotUseIfMatch() throws Exception { request.addHeader("If-Match","\"etag\""); final HttpRequest result = impl.buildUnconditionalRequest(request); Assert.assertNull(result.getFirstHeader("If-Match")); }
@Test public void testBuildUnconditionalRequestDoesNotUseIfNoneMatch() throws Exception { request.addHeader("If-None-Match","\"etag\""); final HttpRequest result = impl.buildUnconditionalRequest(request); Assert.assertNull(result.getFirstHeader("If-None-Match")); }
@Test public void testBuildUnconditionalRequestDoesNotUseIfRange() throws Exception { request.addHeader("If-Range","\"etag\""); final HttpRequest result = impl.buildUnconditionalRequest(request); Assert.assertNull(result.getFirstHeader("If-Range")); }
@Test public void testBuildUnconditionalRequestCarriesOtherRequestHeaders() throws Exception { request.addHeader("User-Agent","MyBrowser/1.0"); final HttpRequest result = impl.buildUnconditionalRequest(request); Assert.assertEquals("MyBrowser/1.0", result.getFirstHeader("User-Agent").getValue()); }
@Test public void testSuitableEvenIfStaleButPermittedByRequestMaxStale() { request.addHeader("Cache-Control", "max-stale=10"); final Header[] headers = { new BasicHeader("Date", DateUtils.formatDate(tenSecondsAgo)), new BasicHeader("Cache-Control", "max-age=5"), new BasicHeader("Content-Length","128") }; entry = getEntry(headers); Assert.assertTrue(impl.canCachedResponseBeUsed(host, request, entry, now)); }
@Test public void testSuitableIfFreshAndFreshnessLifetimeGreaterThanRequestMinFresh() { request.addHeader("Cache-Control", "min-fresh=10"); final Header[] headers = { new BasicHeader("Date", DateUtils.formatDate(tenSecondsAgo)), new BasicHeader("Cache-Control", "max-age=3600"), new BasicHeader("Content-Length","128") }; entry = getEntry(headers); Assert.assertTrue(impl.canCachedResponseBeUsed(host, request, entry, now)); }
@Test public void testNotSuitableIfFreshnessLifetimeLessThanRequestMinFresh() { request.addHeader("Cache-Control", "min-fresh=10"); final Header[] headers = { new BasicHeader("Date", DateUtils.formatDate(tenSecondsAgo)), new BasicHeader("Cache-Control", "max-age=15"), new BasicHeader("Content-Length","128") }; entry = getEntry(headers); Assert.assertFalse(impl.canCachedResponseBeUsed(host, request, entry, now)); }
@Test public void testSuitableIfFreshAndAgeIsUnderRequestMaxAge() { request.addHeader("Cache-Control", "max-age=15"); final Header[] headers = { new BasicHeader("Date", DateUtils.formatDate(tenSecondsAgo)), new BasicHeader("Cache-Control", "max-age=3600"), new BasicHeader("Content-Length","128") }; entry = getEntry(headers); Assert.assertTrue(impl.canCachedResponseBeUsed(host, request, entry, now)); }
@Test public void testNotSuitableIfRequestHasNoCache() { request.addHeader("Cache-Control", "no-cache"); final Header[] headers = { new BasicHeader("Date", DateUtils.formatDate(tenSecondsAgo)), new BasicHeader("Cache-Control", "max-age=3600"), new BasicHeader("Content-Length","128") }; entry = getEntry(headers); Assert.assertFalse(impl.canCachedResponseBeUsed(host, request, entry, now)); }
@Test public void testNotSuitableIfAgeExceedsRequestMaxAge() { request.addHeader("Cache-Control", "max-age=10"); final Header[] headers = { new BasicHeader("Date", DateUtils.formatDate(tenSecondsAgo)), new BasicHeader("Cache-Control", "max-age=3600"), new BasicHeader("Content-Length","128") }; entry = getEntry(headers); Assert.assertFalse(impl.canCachedResponseBeUsed(host, request, entry, now)); }
@Test public void testNotSuitableIfStaleButTooStaleForRequestMaxStale() { request.addHeader("Cache-Control", "max-stale=2"); final Header[] headers = { new BasicHeader("Date", DateUtils.formatDate(tenSecondsAgo)), new BasicHeader("Cache-Control", "max-age=5"), new BasicHeader("Content-Length","128") }; entry = getEntry(headers); Assert.assertFalse(impl.canCachedResponseBeUsed(host, request, entry, now)); }
@Test public void testMalformedCacheControlMaxAgeRequestHeaderCausesUnsuitableEntry() { request.addHeader(new BasicHeader("Cache-Control", "max-age=foo")); final Header[] headers = { new BasicHeader("Date", DateUtils.formatDate(tenSecondsAgo)), new BasicHeader("Cache-Control", "max-age=3600"), new BasicHeader("Content-Length","128") }; entry = getEntry(headers); Assert.assertFalse(impl.canCachedResponseBeUsed(host, request, entry, now)); }
@Test public void testMalformedCacheControlMinFreshRequestHeaderCausesUnsuitableEntry() { request.addHeader(new BasicHeader("Cache-Control", "min-fresh=foo")); final Header[] headers = { new BasicHeader("Date", DateUtils.formatDate(tenSecondsAgo)), new BasicHeader("Cache-Control", "max-age=3600"), new BasicHeader("Content-Length","128") }; entry = getEntry(headers); Assert.assertFalse(impl.canCachedResponseBeUsed(host, request, entry, now)); }
@Test public void testBuildConditionalRequestWithETag() { final String theMethod = "GET"; final String theUri = "/theuri"; final String theETag = "this is my eTag"; final HttpRequest basicRequest = new BasicHttpRequest(theMethod, theUri); basicRequest.addHeader("Accept-Encoding", "gzip"); final HttpRequest requestWrapper = RequestCopier.INSTANCE.copy(basicRequest); final Header[] headers = new Header[] { new BasicHeader("Date", DateUtils.formatDate(new Date())), new BasicHeader("Last-Modified", DateUtils.formatDate(new Date())), new BasicHeader("ETag", theETag) }; final HttpCacheEntry cacheEntry = HttpTestUtils.makeCacheEntry(headers); final HttpRequest newRequest = impl.buildConditionalRequest(requestWrapper, cacheEntry); Assert.assertNotSame(basicRequest, newRequest); Assert.assertEquals(theMethod, newRequest.getMethod()); Assert.assertEquals(theUri, newRequest.getRequestUri()); Assert.assertEquals(3, newRequest.getHeaders().length); Assert.assertEquals("Accept-Encoding", newRequest.getHeaders()[0].getName()); Assert.assertEquals("gzip", newRequest.getHeaders()[0].getValue()); Assert.assertEquals("If-None-Match", newRequest.getHeaders()[1].getName()); Assert.assertEquals(theETag, newRequest.getHeaders()[1].getValue()); }
request.addHeader("Via",via);
@Test public void testBuildConditionalRequestWithLastModified() { final String theMethod = "GET"; final String theUri = "/theuri"; final String lastModified = "this is my last modified date"; final HttpRequest basicRequest = new BasicHttpRequest(theMethod, theUri); basicRequest.addHeader("Accept-Encoding", "gzip"); final HttpRequest requestWrapper = RequestCopier.INSTANCE.copy(basicRequest); final Header[] headers = new Header[] { new BasicHeader("Date", DateUtils.formatDate(new Date())), new BasicHeader("Last-Modified", lastModified) }; final HttpCacheEntry cacheEntry = HttpTestUtils.makeCacheEntry(headers); final HttpRequest newRequest = impl.buildConditionalRequest(requestWrapper, cacheEntry); Assert.assertNotSame(basicRequest, newRequest); Assert.assertEquals(theMethod, newRequest.getMethod()); Assert.assertEquals(theUri, newRequest.getRequestUri()); Assert.assertEquals(2, newRequest.getHeaders().length); Assert.assertEquals("Accept-Encoding", newRequest.getHeaders()[0].getName()); Assert.assertEquals("gzip", newRequest.getHeaders()[0].getValue()); Assert.assertEquals("If-Modified-Since", newRequest.getHeaders()[1].getName()); Assert.assertEquals(lastModified, newRequest.getHeaders()[1].getValue()); }