ASP.NET MVC:如何让浏览器打开并显示PDF,而不是显示下载提示框?
ASP.NET MVC:如何让浏览器打开并显示PDF,而不是显示下载提示框?
我有一个生成PDF并返回给浏览器的操作方法。问题是,IE和Chrome都会显示下载提示,而不是自动打开PDF,尽管它们知道文件的类型。在这两个浏览器中,如果我点击存储在服务器上的PDF文件的链接,它会正常打开,而不会显示下载提示。
以下是用于返回PDF的代码:
public FileResult Report(int id) { var customer = customersRepository.GetCustomer(id); if (customer != null) { return File(RenderPDF(this.ControllerContext, "~/Views/Forms/Report.aspx", customer), "application/pdf", "Report - Customer # " + id.ToString() + ".pdf"); } return null; }
这是服务器的响应头:
HTTP/1.1 200 OK Server: ASP.NET Development Server/10.0.0.0 Date: Thu, 16 Sep 2010 06:14:13 GMT X-AspNet-Version: 4.0.30319 X-AspNetMvc-Version: 2.0 Content-Disposition: attachment; filename="Report - Customer # 60.pdf" Cache-Control: private, s-maxage=0 Content-Type: application/pdf Content-Length: 79244 Connection: Close
我需要在响应中添加特殊内容才能让浏览器自动打开PDF吗?
非常感谢您的帮助!谢谢!
问题出现的原因是在HTTP级别上,'Content-Disposition'头部应该使用'inline'而不是'attachment'。然而,FileResult(或其派生类)不直接支持这一点。如果您已经在页面或处理程序中生成了文档,可以简单地将浏览器重定向到那里。如果这不是您想要的,您可以子类化FileResult并添加支持以内联方式流式传输文档的功能。
public class CustomFileResult : FileContentResult { public CustomFileResult(byte[] fileContents, string contentType) : base(fileContents, contentType) { } public bool Inline { get; set; } public override void ExecuteResult(ControllerContext context) { if (context == null) { throw new ArgumentNullException("context"); } HttpResponseBase response = context.HttpContext.Response; response.ContentType = ContentType; if (!string.IsNullOrEmpty(FileDownloadName)) { string str = new ContentDisposition { FileName = this.FileDownloadName, Inline = Inline }.ToString(); context.HttpContext.Response.AddHeader("Content-Disposition", str); } WriteFile(response); } }
一个更简单的解决方法是在Controller.File方法上不指定文件名。这样,您就不会获得ContentDisposition头部,这意味着在保存PDF时丢失了文件名提示。
我首先采用ContentDisposition助手类的方法,只是意识到MVC也在内部使用它,但是对于正确处理utf-8文件名的一些hack。 ContentDisposition助手类在编码utf-8值时做得不对。详细信息请参见这里的我的评论。