C# 如何将站点范围的无缓存头添加到MVC 3应用程序

C# 如何将站点范围的无缓存头添加到MVC 3应用程序,c#,asp.net-mvc,asp.net-mvc-3,C#,Asp.net Mvc,Asp.net Mvc 3,我构建了一个MVC3应用程序,应用程序有很多页面,现在因为安全问题,我需要在http头中添加无缓存设置,有更简单的方法吗?如果我们可以修改一个地方,那么它将适用于整个应用程序,这将是完美的 你们能帮帮我吗?在应用程序中设置标题如何?在全局.asax中呈现请求标题事件 编辑 您可以使用Response.Cache.SetCacheability而不是直接设置头* void Application_PreSendRequestHeaders(Object sender, EventArgs e) {

我构建了一个MVC3应用程序,应用程序有很多页面,现在因为安全问题,我需要在http头中添加无缓存设置,有更简单的方法吗?如果我们可以修改一个地方,那么它将适用于整个应用程序,这将是完美的


你们能帮帮我吗?

应用程序中设置标题如何?在全局.asax中呈现请求标题
事件

编辑 您可以使用
Response.Cache.SetCacheability
而不是直接设置头*

void Application_PreSendRequestHeaders(Object sender, EventArgs e)
{
    Response.Cache.SetCacheability(HttpCacheability.NoCache);
}
在Fiddler中测试。


另一种方法是手动设置标题


我会在IIS本身(假设您正在使用)或web.config中执行此操作:

<configuration>
   <system.webServer>
      <staticContent>
         <clientCache cacheControlMode="DisableCache" />
      </staticContent>
   </system.webServer>
</configuration>

代码越少越好

根据IIS的版本,设置略有不同


有关更多信息,请参阅。

我建议将这些调用限制为非GET请求,以避免失去GET缓存的好处。以下内容确保即使是像iOS 6 Safari这样的激进缓存浏览器也不会缓存任何非GET请求的内容

我使用了一个控制器基类,我的所有控制器都是从该基类继承的,原因有很多,这很好,因为我的初始化重写可以有条件地处理设置缓存头

public class SmartController : Controller
{
    ...
    public HttpContextBase Context { get; set; }

    protected override void Initialize(System.Web.Routing.RequestContext requestContext)
    {
        Context = requestContext.HttpContext;

        if (Context.Request.RequestType != "GET")
        {
            Context.Response.Cache.SetCacheability(HttpCacheability.NoCache);
        }

        base.Initialize(requestContext);
        ...
    }
...
}

对于那些需要方法/操作或类/控制器范围的
无缓存的用户,可选择此选项

[OutputCache(Location = OutputCacheLocation.None)]
public class HomeController : Controller
{
...
}
如下文所述:

无:已为请求的页面禁用输出缓存。此值 对应于HttpCacheability.NoCache枚举值

NoCache-设置缓存控制:无缓存头


设置一个全局过滤器

public class MvcApplication : System.Web.HttpApplication
{

    public static void RegisterGlobalFilters(GlobalFilterCollection filters)
    {
        filters.Add(new NoCacheGlobalActionFilter());
    }    
}

public class NoCacheGlobalActionFilter : ActionFilterAttribute
{
    public override void OnResultExecuted(ResultExecutedContext filterContext)
    {
        HttpCachePolicyBase cache = filterContext.HttpContext.Response.Cache;
        cache.SetCacheability(HttpCacheability.NoCache);

        base.OnResultExecuted(filterContext);
    }
}

我已经编辑了我的答案,以使用
Response.Cache.SetCacheability()方法,而不是手动设置标题。在Fiddler中测试并按预期工作。该配置仅适用于静态内容(img、js、css等),还是名称有点误导?从IIS网站上看不太清楚。@Troy-我想这就是一切。很容易测试,只需检查应用程序中fiddler/firebug/etcControlling缓存中的响应头对我来说似乎更合适,因为我预计大多数人都希望缓存静态内容。另外,我不会说您的解决方案需要更少的代码:-),它需要更少的代码。这只是一个web.config更改。换句话说,它不需要重新编译和修补,如果需要,它可以转到根web.config并在站点范围内应用。谢谢,顺便说一句,这正是我想要的!ASP.NET输出缓存与OP询问的无缓存HTTP头不同。@MikeMarynowski是,但您确定吗?我相信None意味着既不是服务器也不是客户端,并为客户端生成“缓存控制:无缓存”头。。。嗯,这很有趣,我从来没有见过这种方法被用来阻止客户端缓存,但我认为我是正确的。我想知道,如果是这样的话,为什么不经常使用和建议它——我几乎只看到使用Response.Cache.SetCacheability的建议。你的方式看起来更像MVC风格。如果你可以编辑你的答案,添加一行关于我将向上投票的内容,它会锁定向下投票,除非答案被编辑。这太多了,没有缓存!如果你这样做,你就不会缓存所有的javascript、css、图标等,也不会对你的带宽和响应能力造成很大影响。@ScottStafford read OPs request“如果我们可以修改一个位置,那么它将适用于整个应用程序,这将是完美的。”显然,有些文件可以过滤,但这不是请求的内容。我知道他是这么说的。我没有-1或其他任何东西,但我想确保他(和其他读者)知道这种高压手段的后果。加入一个“这是一个aspx文件吗”的测试,它的适用范围更广。@ScottStafford,这个(.aspx filter)在MVC中实际上不起作用,但应该进行类似的筛选。基于HTTP谓词设置缓存策略对于各种各样的应用来说是不够的。假设您有一个页面,使用GET和查询字符串加载医院患者数据?您不希望缓存该页面。Larry,在这种情况下,您肯定不希望像我在这里建议的那样实现基本控制器逻辑。:)
public class MvcApplication : System.Web.HttpApplication
{

    public static void RegisterGlobalFilters(GlobalFilterCollection filters)
    {
        filters.Add(new NoCacheGlobalActionFilter());
    }    
}

public class NoCacheGlobalActionFilter : ActionFilterAttribute
{
    public override void OnResultExecuted(ResultExecutedContext filterContext)
    {
        HttpCachePolicyBase cache = filterContext.HttpContext.Response.Cache;
        cache.SetCacheability(HttpCacheability.NoCache);

        base.OnResultExecuted(filterContext);
    }
}