Question

In order to disable browser cache, to reliably instructing the browser not to cache, I found the best solution was to create your own [NoCache] attribute class

public class NoCacheSettingsAttribute : ActionFilterAttribute
{
    public override void OnResultExecuting(ResultExecutingContext filterContext)
    {
        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();

        base.OnResultExecuting(filterContext);
    }
}

And a global filter settings

public static void RegisterGlobalFilters(GlobalFilterCollection filters)
{
    // Makes sure that cached pages are not served to any browser including chrome
    filters.Add(new NoCacheSettingsAttribute());
}

I want to use [OutputCache(CacheProfile = "2Hour")] in some ActionResult of a controller and also want to use NoCacheSetting for rest of controller globally , Let say in BaseController, (all controller inherit from BaseController)

So the question is that will it work properly ? Or I have to put rest of controller 1 by one ?

Was it helpful?

Solution

Why not simply exclude controller actions already decorated with the OutputCache attribute from processing:

public class NoCacheSettingsAttribute : ActionFilterAttribute
{
    public override void OnResultExecuting(ResultExecutingContext filterContext)
    {
        var descriptor = new ReflectedControllerDescriptor(
            filterContext.Controller.GetType()
        );

        var action = descriptor.FindAction(
            filterContext.Controller.ControllerContext, 
            filterContext.RequestContext.RouteData.GetRequiredString("action")
        );

        if (!action.GetCustomAttributes(typeof(OutputCacheAttribute), true).Any())
        {
            // The controller action is not decorated with the 
            // [OutputCache] attribute, so you could apply your NoCache logic here

            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();
        }
    }
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top