I would like to have certain pages have a 10 minute Cache for clients and 24 hours for the server. The reason is if the page changes, the client will fetch the updated version within 10 minutes, but if nothing changes the server will only have to rebuild the page once a day.
The problem is that Output Cache settings seem to override the Client settings. Here is what I have setup:
Custom ActionFilterAttribute Class
public class ClientCacheAttribute : ActionFilterAttribute
{
private bool _noClientCache;
public int ExpireMinutes { get; set; }
public ClientCacheAttribute(bool noClientCache)
{
_noClientCache = noClientCache;
}
public override void OnResultExecuting(ResultExecutingContext filterContext)
{
if (_noClientCache || ExpireMinutes <= 0)
{
filterContext.HttpContext.Response.Cache.SetExpires(DateTime.UtcNow.AddDays(-1));
filterContext.HttpContext.Response.Cache.SetValidUntilExpires(false);
filterContext.HttpContext.Response.Cache.SetRevalidation(HttpCacheRevalidation.AllCaches);
filterContext.HttpContext.Response.Cache.SetCacheability(HttpCacheability.NoCache);
filterContext.HttpContext.Response.Cache.SetNoStore();
}
else
{
filterContext.HttpContext.Response.Cache.SetExpires(DateTime.UtcNow.AddMinutes(ExpireMinutes));
}
base.OnResultExecuting(filterContext);
}
}
Web Config settings
<outputCacheSettings>
<outputCacheProfiles>
<add name="Cache24Hours" location="Server" duration="86400" varyByParam="none" />
</outputCacheProfiles>
</outputCacheSettings>
How I'm calling it:
[OutputCache(CacheProfile = "Cache24Hours")]
[ClientCacheAttribute(false, ExpireMinutes = 10)]
public class HomeController : Controller
{
[...]
}
But looking at the HTTP Header shows:
HTTP/1.1 200 OK
Cache-Control: no-cache
Pragma: no-cache
Content-Type: text/html; charset=utf-8
Expires: -1
How can I implement this properly? It is an ASP.NET MVC 4 application.
You need to implement your own solution for server side caching and for client side caching either use ClientCacheAttribute or OutputCache. Here are the reason for why you would require your custom solution for server side cache.
Here what I'm trying to highlight is that we don't have collection of HttpCachePolicyBase but we only have one object of HttpCachePolicyBase so we can't set multiple cache policy for given response.
Even if we can set Http Cacheability to HttpCacheability.ServerAndPrivate but again you will run in other issue with cache duration (i.e. for client 10 minute & server 24 hours)
What I would suggest is that use OutputCache for client side caching and implement your own caching mechanism for server side caching.
In your OutputCache profile, set the location to ServerAndClient. Your action filter should properly override the output once you do this.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With