C#ZipArchive.CreateEntryFromFile()不会将文件从磁盘添加到存档

问题描述 投票:2回答:3

我在.NET 4.5中使用以下代码来使用SmtpClient发送电子邮件附件。我将下面创建的内存流添加到Attachement消息集合中。

using System.IO;
using System.IO.Compression;

var memoryStream = new MemoryStream();
using (var archive = new ZipArchive(memoryStream, ZipArchiveMode.Create, true))
{
    archive.CreateEntryFromFile(@"c:\Files\File1.txt", "File1.txt");
}

当我收到电子邮件时,它显示zip文件,但存档没有File1.txt。这里缺少什么?

.net-4.5 .net
3个回答
0
投票

我在程序中有类似的场景,在MemoryStream中创建Zip文件。正如Jack Bradford所提到的那样,执行Close / Dispose操作非常重要,但还有一些棘手的问题:

首先,您无法关闭/处置MemoryStream,因为您需要打开它才能通过电子邮件附件发送它。

其次,您无法关闭/处置ZipArchive。其底层逻辑将在MemoryStream对象中执行Close操作。

第三,通常在写入MemoryStream对象之后,指针留在流的末尾。如果您尝试从中读取,则将读取0个字节。这可能是您获得空zip文件的原因。

解决方案是将MemoryStream光标设置在流的开头,这样您的下一个读操作就能获得所有数据:

  memoryStream.Position = 0;
  <Mail code>
  System.Net.Mime.ContentType ct = new    System.Net.Mime.ContentType(System.Net.Mime.MediaTypeNames.Application.Zip);
  System.Net.Mail.Attachment attachment = new System.Net.Mail.Attachment(memoryStream,"ZipFile.zip", ct.MediaType);
   <Add attachment to email and send email>
   <Stream and Zip Close/Dispose operations>

0
投票

我遇到了同样的问题,我做的是:

 using (var archive = new ZipArchive(zipStream, ZipArchiveMode.Create, false)) {
       archive.CreateEntryFromFile(udf.FilePath, Path.GetFileName(udf.FilePath));
 }

在ZipArchive和我发过的电子邮件部分中使用“false”:

mail.Attachments.Add(new Attachment(new MemoryStream(ai.Stream.ToArray()), ai.AttachedFilename, ai.MediaType));

我在电子邮件中添加了像new MemoryStream(ai.Stream.ToArray())and这样的流,现在附件很好。


-4
投票

确保丢弃ZipArchive并关闭MemoryStream

var memoryStream = new MemoryStream();
    using (var archive = new ZipArchive(memoryStream, ZipArchiveMode.Create, true))
    {
         archive.CreateEntryFromFile(@"c:\Files\File1.txt", "File1.txt");
    }

archive.Dispose();
memoryStream.Close();

//Send Email
© www.soinside.com 2019 - 2024. All rights reserved.