【问题标题】:How do I generate and send a .zip file to a user in C# ASP.NET?如何在 C# ASP.NET 中生成 .zip 文件并将其发送给用户?
【发布时间】:2009-05-07 13:02:07
【问题描述】:

我需要构建一个 zip 并将其发送给用户。

我看到过一个例子,但不是两者都做,我很好奇是否有任何“最佳实践”或任何东西。

很抱歉给您带来了困惑。我将为网络用户即时生成 zip,并在 HTTP 响应中将其发送给他们。不在电子邮件中。

标记

【问题讨论】:

    标签: c# asp.net file zip


    【解决方案1】:

    我会支持SharpZipLib 创建 Zip 文件。然后你需要在输出中附加一个响应头来强制下载对话框。

    http://aspalliance.com/259

    应该给你一个很好的起点来实现这一点。您基本上需要添加响应头,设置内容类型并将文件写入输出流:

    Response.AppendHeader( "content-disposition", "attachment; filename=" + name );
    Response.ContentType = "application/zip";
    Response.WriteFile(pathToFile);
    

    如果您不想保存到临时文件,可以将最后一行更改为 Response.Write(filecontents)。

    【讨论】:

      【解决方案2】:

      DotNetZip 让您轻松完成此操作,而无需写入服务器上的磁盘文件。您可以将 zip 存档直接写入响应流,这将导致下载对话框在浏览器上弹出。

      Example ASP.NET code for DotNetZip

      More example ASP.NET code for DotNetZip

      截图:

          Response.Clear();
          Response.BufferOutput = false; // false = stream immediately
          System.Web.HttpContext c= System.Web.HttpContext.Current;
          String ReadmeText= String.Format("README.TXT\n\nHello!\n\n" + 
                                           "This is text for a readme.");
          string archiveName= String.Format("archive-{0}.zip", 
                                            DateTime.Now.ToString("yyyy-MMM-dd-HHmmss")); 
          Response.ContentType = "application/zip";
          Response.AddHeader("content-disposition", "filename=" + archiveName);
      
          using (ZipFile zip = new ZipFile())
          {
              zip.AddFiles(f, "files");            
              zip.AddFileFromString("Readme.txt", "", ReadmeText);
              zip.Save(Response.OutputStream);
          }
          Response.Close();
      

      或在 VB.NET 中:

          Response.Clear
          Response.BufferOutput= false
          Dim ReadmeText As String= "README.TXT\n\nHello!\n\n" & _
                                    "This is a zip file that was generated in ASP.NET"
          Dim archiveName as String= String.Format("archive-{0}.zip", _
                     DateTime.Now.ToString("yyyy-MMM-dd-HHmmss"))
          Response.ContentType = "application/zip"
          Response.AddHeader("content-disposition", "filename=" + archiveName)
      
          Using zip as new ZipFile()
              zip.AddEntry("Readme.txt", "", ReadmeText, Encoding.Default)
              '' filesToInclude is a string[] or List<String>
              zip.AddFiles(filesToInclude, "files")            
              zip.Save(Response.OutputStream)
          End Using
          Response.Close
      

      【讨论】:

      • 迄今为止最好的 C# ZIP 库
      • 截至 2014 年 9 月(和 .Net 4.5)DotNetZip 现在不可靠,经常生成损坏或无法打开的 zip 存档。很遗憾,因为它在我拥有它的第一年左右工作得很好。
      【解决方案3】:

      我相信其他人会推荐SharpZipLib

      您打算如何“发送”它。 .NET 内置了通过 SMTP 发送电子邮件的库

      编辑

      在这种情况下,您需要从 SharpZipLib 捕获输出流并将其直接写入响应。只需确保您在响应标头(应用程序/zip)中设置了正确的 Mimetype,并确保您没有响应。向用户写入任何其他内容。

      【讨论】:

        【解决方案4】:

        同意以上观点,SharpZipLib,用于在 .NET 中创建 .zip 文件,这似乎是一个非常受欢迎的选择。

        至于“发送”,如果您的意思是通过 SMTP/电子邮件,您将需要使用 System.Net.Mail 名称空间。 System.Net.Mail.Attachment Class 文档有一个如何通过电子邮件发送文件的示例

        从上面写一下,当我发布这个时,我看到你的意思是通过 HTTP 响应返回。

        【讨论】:

          【解决方案5】:

          一个问题是您将流式传输到客户端的文件的大小。如果您使用 SharpZipLib 在内存中构建 ZIP,则无需清理任何临时文件,但如果文件很大并且许多并发用户正在下载文件,您很快就会遇到内存问题。 (当 ZIP 大小达到 200 MB+ 范围时,我们经常遇到这种情况。)我通过临时文件到磁盘解决这个问题,将其流式传输给用户,然后在请求完成时将其删除。

          【讨论】:

            【解决方案6】:

            DotNetZip 创建流时不会在服务器上保存任何资源,因此您无需记住删除任何内容。正如我之前所说,它的编码快速直观,实现高效。

            莫舍

            【讨论】:

              【解决方案7】:

              我修改了一些代码如下,我使用 System.IO.Compression

               public static void Zip(HttpResponse Response, HttpServerUtility Server, string[] pathes)
                  {
                      Response.Clear();
                      Response.BufferOutput = false;         
              
                      string archiveName = String.Format("archive-{0}.zip",
                                                        DateTime.Now.ToString("yyyy-MMM-dd-HHmmss"));
                      Response.ContentType = "application/zip";
                      Response.AddHeader("content-disposition", "filename=" + archiveName);
              
                      var path = Server.MapPath(@"../TempFile/TempFile" + DateTime.Now.Ticks);
                      if (!Directory.Exists(Server.MapPath(@"../TempFile")))
                          Directory.CreateDirectory(Server.MapPath(@"../TempFile"));
              
                      if (!Directory.Exists(path))
                          Directory.CreateDirectory(path);
                      var pathzipfile = Server.MapPath(@"../TempFile/zip_" + DateTime.Now.Ticks + ".zip");
                      for (int i = 0; i < pathes.Length; i++)
                      {
                          string dst = Path.Combine(path, Path.GetFileName(pathes[i]));
                          File.Copy(pathes[i], dst);
                      }
                      if (File.Exists(pathzipfile))
                          File.Delete(pathzipfile);
                      ZipFile.CreateFromDirectory(path, pathzipfile);
                      {
                          byte[] bytes = File.ReadAllBytes(pathzipfile);
                          Response.OutputStream.Write(bytes, 0, bytes.Length);
                      }
                      Response.Close();
                      File.Delete(pathzipfile);
                      Directory.Delete(path, true);
                  }  
              

              此代码获取一些包含文件列表的列表,将它们复制到临时文件夹中 ,创建临时 zip 文件,然后读取该文件的所有字节并在响应流中发送字节,最后删除临时文件和文件夹

              【讨论】:

                猜你喜欢
                • 1970-01-01
                • 2022-11-01
                • 2012-04-17
                • 1970-01-01
                • 1970-01-01
                • 2014-04-06
                • 2017-02-07
                • 1970-01-01
                • 2014-02-16
                相关资源
                最近更新 更多