Asp.net mvc 4 使用Asp MVC 4.0文件结果时出现Internet Explorer错误

Asp.net mvc 4 使用Asp MVC 4.0文件结果时出现Internet Explorer错误,asp.net-mvc-4,asp.net-mvc,Asp.net Mvc 4,Asp.net Mvc,我有以下代码,部署在https Asp站点上,使用MVC 4.0构建: public FileResult ANotSoWorkingFunction(string filePath, string fileName) { pathToFile = string.Format("~/{0}/{1}", pathToFile, fileName); return File(new FileStream(pathToFile, FileMode.Open), "application/pdf",

我有以下代码,部署在https Asp站点上,使用MVC 4.0构建:

public FileResult ANotSoWorkingFunction(string filePath, string fileName)
{
 pathToFile = string.Format("~/{0}/{1}", pathToFile, fileName);
 return File(new FileStream(pathToFile, FileMode.Open), "application/pdf", fileName);
}
这将适用于Chrome、Firefox和IE9(你们很多人可能已经猜到了)。但它将抛出一个:

---------------------------
Windows Internet Explorer
---------------------------
Internet Explorer cannot download someFileName from a_site.com.


Internet Explorer was not able to open this Internet site.  The requested site is either unavailable or cannot be found.  Please try again later.
---------------------------
OK   
---------------------------
关于IE6,7,8

任何关于这一点的想法或线索都非常感谢,因为我已经花了一天的时间玩html标题

编辑:

以下是IE7的标题:

HTTP/1.1 200 OK
Cache-Control: private, no-cache="Set-Cookie"
Content-Type: application/pdf
Server: Microsoft-IIS/7.5
X-AspNetMvc-Version: 4.0
X-AspNet-Version: 4.0.30319
Set-Cookie: .ASPXAUTH=; expires=Mon, 11-Oct-1999 21:00:00 GMT; path=/; HttpOnly
X-Powered-By: ASP.NET
Date: Wed, 04 Apr 2012 08:43:50 GMT
Content-Length: 233324
以下是IE9中的内容:

HTTP/1.1 200 OK
Cache-Control: private, no-cache="Set-Cookie"
Content-Type: application/pdf
Server: Microsoft-IIS/7.5
X-AspNetMvc-Version: 4.0
X-AspNet-Version: 4.0.30319
Set-Cookie: .ASPXAUTH=; expires=Mon, 11-Oct-1999 21:00:00 GMT; path=/; HttpOnly
X-Powered-By: ASP.NET
Date: Wed, 04 Apr 2012 08:42:14 GMT
Content-Length: 233324

谢谢,

在旧版本的IE中,如果用户试图通过HTTPS连接下载文件,任何阻止缓存的响应头都将导致文件下载过程失败。以下是导致问题的最常见标题:

  • 值为“无缓存”或“无存储”的缓存控件
  • 随价值变化
  • 不带缓存值的杂注
您可以创建一个ActionFilterAttribute,它将为您清除缓存头,如下所示:

public class ClearCacheHeadersAttribute : FilterAttribute, IActionFilter
{
    public void OnActionExecuted(ActionExecutedContext filterContext)
    {
        return;
    }

    public void OnActionExecuting(ActionExecutingContext filterContext)
    {
        HttpContext.Current.Response.Headers.Remove("Cache-Control");
        HttpContext.Current.Response.Headers.Remove("Vary");
        HttpContext.Current.Response.Headers.Remove("Pragma");

        //Set the cache headers any way you like keeping in mind which values can brake the download
    }
}
用它来装饰我们的行动:

[ClearCacheHeaders]
public FileResult ANotSoWorkingFunction(string filePath, string fileName)
{
    pathToFile = string.Format("~/{0}/{1}", pathToFile, fileName);
    return File(new FileStream(pathToFile, FileMode.Open), "application/pdf", fileName);
}

我们通过在流式传输文件之前更改缓存控制头来解决这个问题

简化代码示例:

var browserInformation = Request.Browser;

//Set as private if current browser type is IE
Response.AppendHeader("cache-control", 
                    browserInformation.Browser == "IE" ? "private" : "no-cache");

return File(fileName, contentType, downloadFileName);
这起作用了(耶)。。但我不清楚为什么我们要用这种方式为那个特定的网站服务。我们有四个网站运行在同一个盒子上,都在SSL下,只有一个有这个标题问题。我比较了web.config文件并查看了IIS中的设置,但无法进一步说明为什么该站点需要显式设置这些标题


如果有人有更多的补充以上(增加克莱蒂),这将是伟大的

我想我也遇到了你的问题

我还运行IIS 7.5,并通过HTTPS请求上的操作下载PDF。出于我尚未隔离的原因,IIS 7.5似乎将
no cache=“Set Cookie”
附加到我的
缓存控制
响应头中,而不管我在响应中设置了什么缓存设置。这是造成的

为了解决这个问题,我在FileContentResult周围做了一个小包装,它清除了标题,称为父级,然后将可缓存性设置为“Private”。这回避了IIS 7.5坚持在头文件中添加
no cache=“Set Cookie”
,并在我测试的所有浏览器中正确下载了文件。如果您想模仿我所做的,首先,这里是我的FileContentResult包装器

公共类PdfContentResult:FileContentResult{ 公共PdfContentResult(字节[]数据):数据库(数据,“应用程序/pdf”){} 公共PdfContentResult(字节[]数据,字符串文件名):此(数据){ 如果(文件名==null){ 抛出新的ArgumentNullException(“文件名”); } this.FileDownloadName=文件名; } 公共覆盖无效ExecuteSult(ControllerContext上下文){ context.HttpContext.Response.ClearHeaders(); base.executesult(上下文); context.HttpContext.Response.Cache.SetCacheability(HttpCacheability.Private); } } 然后,我在我的
ControllerExtensions
中添加了一个扩展方法,这样就很容易找到:

公共静态类控制器扩展{
公共静态PdfContentResult Pdf(此控制器,字节[]文件内容,字符串文件名){
返回新的PdfContentResult(fileContents,fileName);
}
}
最后,在行动中,我做了与之相当的事情:

public ActionResult MyGeneratedPdf(){
字节[]myPdfContentInByteStream=GetPdfFromModel();
返回此.Pdf(myPdfContentInByteStream,“MyFile.Pdf”);
}

显然,如果您正在下载各种类型的数据,您可能不想将解决方案与PDF绑定得如此紧密。

您可以向我们展示您的“缓存控制”和“设置Cookie”响应头吗?当然可以,Lezi,谢谢您在这方面的指导,可能与mvc 3中的问题相同谢谢您的回答,我昨天在搜索中尝试过这个,但由于某种原因,它仍然会在Web.config或IIS配置文件中添加缓存控制头请检查配置/system.webServer/staticContent节点。您也可以自己尝试将缓存控制设置为允许的值,例如:HttpContext.Current.Response.Cache.SetRevalidation(HttpCacheRevalidation.AllCaches);HttpContext.Current.Response.Cache.SetCacheability(HttpCacheability.Public);运气不好,检查了web.config%windir%\Microsoft.NET\Framework\Framework\u version\config;%windir%\Microsoft.NET\Framework\Framework\u version\CONFIG;%windir%\system32\inetsrv\config试图将标头更新为HttpCacheability public,但downloa仍不工作web服务器是否运行不同版本的IIS?我的问题似乎是针对IIS 7.5的。我会尝试一下,让您知道它是如何运行的。我建议您不要做的一件事是从响应中清除标题!原因如下。窗体身份验证、Windows身份基础等为您提供了一个cookie,您可以通过它来标识自己。如果您支持滑动用户会话的概念,那么您将发布一个新的cookie/令牌,并通过“Set cookie”将其添加到响应头中。下载文件时清除标题意味着此新cookie可能会丢失,并且您的用户不再经过身份验证!这不是一件好事。