Asp.net mvc 4 一旦通过SetCacheability方法设置了Pragma no cache响应头,是否可以将其删除?

Asp.net mvc 4 一旦通过SetCacheability方法设置了Pragma no cache响应头,是否可以将其删除?,asp.net-mvc-4,Asp.net Mvc 4,我有一个MVC4 GET操作方法,它返回一个FileStreamResult。存在一个要求,即只使用SSL,不允许缓存所提供的文档,因此使用SSL。我还使用了具有以下属性的OutputCache过滤器: [OutputCache(NoStore = true, Duration = 0, VaryByParam = "None", Location = OutputCacheLocation.None)] 这将按预期运行,并生成以下响应头: Cache-Control: no-cache, n

我有一个MVC4 GET操作方法,它返回一个
FileStreamResult
。存在一个要求,即只使用SSL,不允许缓存所提供的文档,因此使用SSL。我还使用了具有以下属性的
OutputCache
过滤器:

[OutputCache(NoStore = true, Duration = 0, VaryByParam = "None", Location = OutputCacheLocation.None)]
这将按预期运行,并生成以下响应头:

Cache-Control: no-cache, no-store
Expires: -1
Pragma: no-cache
在被要求也支持IE8之前,一切都很好,这里的许多人也遇到过这样的情况:在混合使用无缓存集和SSL的情况下,文档无法下载。IE8及以下版本的解决方法是添加一些实际上不可行的注册表设置,或者删除违反基本要求的无缓存头

我试用了Fiddler和IE8,如果我删除了pragma:no cache头,但保留了
缓存控制
头,就可以下载文档。这似乎没有在我的临时internet文件中留下文档的副本,但我可能需要进一步测试

考虑到这些信息,我认为在操作中使用过滤器删除pragma可能是一项简单的任务,但似乎无论我做什么,我都无法更改将要设置的
OutputCache
。我甚至删除了
OutputCache
属性并使用了:

Response.Cache.SetCacheability(HttpCacheability.NoCache)
单独使用此方法可确保获得与以前相同的缓存设置,但不会在调用此方法时设置它们。这只是设置了缓存策略,该策略在响应管道中的某个点应用,但我不知道在哪里

有人知道是否有一种方法可以挂接到响应管道中,以便在写入缓存头时更改它们吗

编辑 我已经在管道中添加了一个简单的自定义
IHttpModule
,用于查找和删除响应
NameValueCollection
中的任何pragma头,当设置缓存控件时,pragma不在那里。这是否意味着IIS 7.5正在根据它在缓存控件中看到的内容插入pragma本身?我确信我没有为一个简单的网站设置任何超出默认值的东西

编辑
检查模块内的
缓存控制
标头值,并将其设置为私有,因此缓存标头尚未应用于响应。因此,在执行模块之后,可能会添加缓存头?

我对这个问题进行了故障排除,并在删除pragma头时遇到了同样的问题。当.NET呈现
页面
对象时,它会输出缓存头。缓存处理由
HttpModule
控制。我尝试了几种方法来删除pragma头,但都没有用

我还没有尝试过一种方法,它看起来可能有效,但也像PITA,它是通过
Response.filter=new MyCustomFilter(…)
Response
输出流上实现一个过滤器

在此之前,我尝试检查不同位置的头,但输出缓存处理尚未执行,pragma头不存在,因此无法删除。值得注意的是,
HttpApplication
事件
PreSendRequestHeaders
不起作用

其他一些选项包括实现您自己的
OutputCache
模块,而不是使用内置框架版本,或者以某种方式覆盖呈现pragma头的
System.Web.HttpCachePolicy

pragma头作为
HttpCacheability.NoCache
选项的一部分呈现:

  if (httpCacheability == HttpCacheability.NoCache || httpCacheability == HttpCacheability.Server)
  {
    if (HttpCachePolicy.s_headerPragmaNoCache == null)
      HttpCachePolicy.s_headerPragmaNoCache = new HttpResponseHeader(4, "no-cache");
    this._headerPragma = HttpCachePolicy.s_headerPragmaNoCache;
    if (this._allowInHistory != 1)
    {
      if (HttpCachePolicy.s_headerExpiresMinus1 == null)
        HttpCachePolicy.s_headerExpiresMinus1 = new HttpResponseHeader(18, "-1");
      this._headerExpires = HttpCachePolicy.s_headerExpiresMinus1;
    }
  }

我发现唯一实用的选择是将缓存控件设置为private,并为URL设置一个短的过期时间。它没有解决任何一方的根本原因,但最终的效果几乎与预期效果相同。

FWIW,您可能希望阅读以下内容:。即使没有设置缓存头,响应通常仍会在磁盘上的临时文件中结束;理想情况下,它会很快被清理干净,但这不能保证。谢谢你。我在搜索中确实遇到过这篇文章,正是这篇文章促使我在浏览器收到流之前使用fiddler修改响应标题。这是当我注意到,只是不包括pragma,但保持缓存控制完整的文件将下载,但我无法看到它在临时互联网文件文件夹。我仍然认为我需要重新测试一下,以确保它没有缓存在某个地方。我有一个问题,无法找到一种方法使
Response.Cache.SetCacheability
工作-它总是添加
Pragma
标题,并且总是将
无缓存
放在
无存储
之前。不过这应该是可控的——除非你是在处理IE3/Netscape Navigator,否则发送
Pragma
标题是毫无意义的。我做了一些进一步的测试,看看不同浏览器中“私有,无存储”的效果如何可能是,而且看起来我在浏览器缓存中找不到任何下载的文件,所以这可能是解决方案。我在这里的想法是,private只是告诉任何代理服务器不要存储内容,而no store会覆盖客户端上的private。Mark,你有没有找到一种方法在不保留缓存集的情况下删除pragma头?我在IE8上下载文档时遇到了同样的问题。