From e236e640559d1a7e4f2820a75ff85f9af0bb0103 Mon Sep 17 00:00:00 2001 From: John Luo Date: Mon, 12 Sep 2016 17:24:39 -0700 Subject: [PATCH] Fallback to empty cache control when none is explicitly cached --- .../CacheabilityValidator.cs | 14 ++++++++------ .../CacheabilityValidatorTests.cs | 10 ++++++++++ 2 files changed, 18 insertions(+), 6 deletions(-) diff --git a/src/Microsoft.AspNetCore.ResponseCaching/CacheabilityValidator.cs b/src/Microsoft.AspNetCore.ResponseCaching/CacheabilityValidator.cs index 0e46bd470d..2669c32041 100644 --- a/src/Microsoft.AspNetCore.ResponseCaching/CacheabilityValidator.cs +++ b/src/Microsoft.AspNetCore.ResponseCaching/CacheabilityValidator.cs @@ -4,7 +4,6 @@ using System; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Http.Headers; -using Microsoft.AspNetCore.ResponseCaching.Internal; using Microsoft.Extensions.Primitives; using Microsoft.Net.Http.Headers; @@ -12,6 +11,8 @@ namespace Microsoft.AspNetCore.ResponseCaching { public class CacheabilityValidator : ICacheabilityValidator { + private static readonly CacheControlHeaderValue EmptyCacheControl = new CacheControlHeaderValue(); + public virtual bool RequestIsCacheable(HttpContext httpContext) { var state = httpContext.GetResponseCachingState(); @@ -157,6 +158,7 @@ namespace Microsoft.AspNetCore.ResponseCaching { var state = httpContext.GetResponseCachingState(); var age = state.CachedEntryAge; + var cachedControlHeaders = cachedResponseHeaders.CacheControl ?? EmptyCacheControl; // Add min-fresh requirements if (state.RequestCacheControl.MinFresh != null) @@ -165,18 +167,18 @@ namespace Microsoft.AspNetCore.ResponseCaching } // Validate shared max age, this overrides any max age settings for shared caches - if (age > cachedResponseHeaders.CacheControl.SharedMaxAge) + if (age > cachedControlHeaders.SharedMaxAge) { // shared max age implies must revalidate return false; } - else if (cachedResponseHeaders.CacheControl.SharedMaxAge == null) + else if (cachedControlHeaders.SharedMaxAge == null) { // Validate max age - if (age > cachedResponseHeaders.CacheControl.MaxAge || age > state.RequestCacheControl.MaxAge) + if (age > cachedControlHeaders.MaxAge || age > state.RequestCacheControl.MaxAge) { // Must revalidate - if (cachedResponseHeaders.CacheControl.MustRevalidate) + if (cachedControlHeaders.MustRevalidate) { return false; } @@ -190,7 +192,7 @@ namespace Microsoft.AspNetCore.ResponseCaching return false; } - else if (cachedResponseHeaders.CacheControl.MaxAge == null && state.RequestCacheControl.MaxAge == null) + else if (cachedControlHeaders.MaxAge == null && state.RequestCacheControl.MaxAge == null) { // Validate expiration if (state.ResponseTime > cachedResponseHeaders.Expires) diff --git a/test/Microsoft.AspNetCore.ResponseCaching.Tests/CacheabilityValidatorTests.cs b/test/Microsoft.AspNetCore.ResponseCaching.Tests/CacheabilityValidatorTests.cs index 5ead7ab80e..e3cd724195 100644 --- a/test/Microsoft.AspNetCore.ResponseCaching.Tests/CacheabilityValidatorTests.cs +++ b/test/Microsoft.AspNetCore.ResponseCaching.Tests/CacheabilityValidatorTests.cs @@ -386,6 +386,16 @@ namespace Microsoft.AspNetCore.ResponseCaching.Tests Assert.False(new CacheabilityValidator().ResponseIsCacheable(httpContext)); } + [Fact] + public void EntryIsFresh_NoCachedCacheControl_FallsbackToEmptyCacheControl() + { + var utcNow = DateTimeOffset.UtcNow; + var httpContext = CreateDefaultContext(); + httpContext.GetResponseCachingState().ResponseTime = DateTimeOffset.MaxValue; + + Assert.True(new CacheabilityValidator().CachedEntryIsFresh(httpContext, new ResponseHeaders(new HeaderDictionary()))); + } + [Fact] public void EntryIsFresh_NoExpiryRequirements_IsFresh() {