如何通过点击asp.net中的图像按钮来传输zip文件?

时间:2009-03-06 17:12:41

标签: c# asp.net streaming zip

我的问题:当用户点击aspx页面上的图像按钮时,代码隐藏会创建一个zip文件,然后我会尝试将该zip文件传输给用户。

要传输文件,我使用以下代码:

FileInfo toDownload = new FileInfo(fullFileName);
if (toDownload.Exists)
{
   Response.Clear();
   Response.ContentType = "application/zip";
   Response.AppendHeader("Content-Disposition", "attachment;filename=" +
             toDownload.Name);
   Response.AppendHeader("Content-Length", toDownload.Length.ToString());
   Response.TransmitFile(fullFileName);
   HttpContext.Current.ApplicationInstance.CompleteRequest();
}

当我尝试执行此操作时,我在页面上收到以下错误:

Sys.WebForms.PageRequestManagerParserErrorException:无法解析从服务器收到的消息。此错误的常见原因是通过调用Response.Write(),响应过滤器,HttpModules或服务器跟踪来修改响应。 详细信息:解析'PK ...'附近时出错。

PK是zip文件中的前两个字符,用于将其标识为zip文件,因此我知道它正在尝试将zip文件发送到浏览器。但是,我得到的印象是浏览器正在尝试解释和/或呈现zip文件,而我希望它弹出下载文件选项。

想法?

编辑:Here's a link to a post from the guy who wrote the above error message.

3 个答案:

答案 0 :(得分:2)

例如,以下是我在我的某个应用程序中向客户端发送PDF的方式(您必须填写/更改一些缺少的变量声明):

        byte[] rendered = uxReportViewer.LocalReport.Render("PDF", null, out mimeType, out encoding, out extension, out streamIds, out warnings);

        Response.Buffer = true;
        Response.Clear();
        Response.ClearHeaders();
        Response.ContentType = mimeType;
        Response.CacheControl = "public";
        Response.AddHeader("Pragma", "public");
        Response.AddHeader("Expires", "0");
        Response.AddHeader("Cache-Control", "must-revalidate, post-check=0, pre-check=0");
        Response.AddHeader("Content-Description", "Report Export");
        Response.AddHeader("Content-Disposition", "attachment; filename=\"" + filename + "." + extension + "\"");

        Response.BinaryWrite(rendered);
        Response.Flush();
        Response.End();

您要更改内容类型,并将您的zip文件转换为字节数组,然后我认为您可以填写其余内容。

答案 1 :(得分:1)

我终于解决了这个问题并且还注意到我可能没有在问题中提供足够的信息:图像按钮位于UpdatePanel内。

解决方案是为控件创建一个PostBackTrigger:

<Triggers>
    <asp:PostBackTrigger ControlID="ibDownload" />
</Triggers>

答案 2 :(得分:0)

盖伊,你不是在使用DotNetZip来生成zip文件吗?如果您没有在磁盘上创建zip文件但仅在内存中创建该怎么办?这个例子使用DotNetZip来做到这一点。

    Response.Clear();
    Response.BufferOutput = false;
    String ReadmeText= "This is content that will appear in a file " + 
                       "called Readme.txt.\n" + 
                       System.DateTime.Now.ToString("G") ; 
    string archiveName= String.Format("archive-{0}.zip", 
                                      DateTime.Now.ToString("yyyy-MMM-dd-HHmmss")); 
    Response.ContentType = "application/zip";
    Response.AddHeader("content-disposition", "attachment; filename=" + archiveName);

    using (ZipFile zip = new ZipFile())
    {
        // add an entry from a string: 
        zip.AddEntry("Readme.txt", "", ReadmeText);
        zip.AddFiles(filesToInclude, "files");
        zip.Save(Response.OutputStream);
    }
    // Response.End();  // no - see http://stackoverflow.com/questions/1087777
    HttpContext.Current.ApplicationInstance.CompleteRequest();