使用ZipArchive类在C#中创建归档文件夹

问题描述:

正如标题所示,我试图在zip中创建一个zip文件。使用ZipArchive类在C#中创建归档文件夹

我有一个变量来创建一个zip压缩文件名为“TargetFilePath”

var projectDirectoryPath = currentProjectViewModel.DirectoryPath; 
ZipFile.CreateFromDirectory(projectDirectoryPath, [email protected]"/Project.zip"); 

以上都不行,我假设,因为路径C:\ test.zip \ project.zip不是有效路径。

编辑为了清楚起见:我从字面上想要压缩一些文件并将该压缩文件放入另一个压缩文件中。它必须使用System.IO.Compression,而不是第三方方法。

从我的理解,你必须创建一个目标地址为zip文件,并且,也是从我的经验,目标地址不能是无效的路径,如“C:\ test.zip \ project.zip”

+0

递归调用也许? –

+1

如果'projectDirectoryPath'有一个.zip文件+其中的任何其他文件,那么它应该工作。如果您已经有一个.zip文件,并且想要将zip文件添加到该文件中,那么[this](https://msdn.microsoft.com/zh-cn/library/hh158346(v = vs.110).aspx )是做到这一点的一种方式,但对我来说这看起来很痛苦。我只会努力工作,首先创建内部zip文件,然后将其压缩,而不是创建outter zip并将其他文件添加到其中。有关其他选项,请参阅[此处](https://msdn.microsoft.com/en-us/library/system.io.compression.zipfile(v = vs.110).aspx)的备注。 – Quantic

+1

或者,将现有压缩文件解压缩到一个目录中,将其他压缩文件复制到该目录中,然后使用您拥有的相同命令压缩该文件夹。我这样说是因为[ZipArchive.CreateEntry](https://msdn.microsoft.com/en-us/library/hh158346(v = vs.110).aspx)看起来很笨拙,你不能只是“添加这个文件到压缩文件“,您必须以某种方式将文件流式传输到该文件中。如果你有这些资源,那么只需使用一些IO,一段时间让生活更轻松,IMO。 – Quantic

最简单的方法是在您的projectDirectoryPath的内容的临时文件中创建您的压缩文件,一旦完成,您将该文件添加到您的目标zip压缩文件。

所以基本上是这样的:

var projectDirectoryPath = currentProjectViewModel.DirectoryPath; 
var tempFile = Path.Combine(Path.GetTempPath(), Path.GetRandomFileName()); 
try 
{ 
    ZipFile.CreateFromDirectory(projectDirectoryPath, tempFile); 

    using (var archive = ZipFile.Open(TargetFilePath, ZipArchiveMode.Update)) 
    { 
     archive.CreateEntryFromFile(tempFile, "Project.zip", CompressionLevel.NoCompression); 
    } 
} 
finally 
{ 
    System.IO.File.Delete(tempFile); 
} 

我建议你使用CompressionLevel.NoCompression因为zip压缩包已经被压缩和压缩的另一层将没有价值添加到它。在打开存档时使用ZipArchiveMode.Update非常重要,因此实际上zip文件已被更改。此枚举器的其他值用于从头开始创建新的存档或以只读方式打开它。

在这个例子中我使用了CreateEntryFromFile函数。这是一种扩展方法,因此请确保您在using声明中具有名称空间。

可以通过某种方式实现此目的,因此不需要临时文件,但需要更多的代码,因为您必须自己创建新的zip文件并将其直接写入创建achive中的新条目。但是在大多数情况下,我给出的例子应该可以完成这项工作

+0

当我使用这种方法时,我得到一个例外,即临时文件已经存在 –

+0

修正了这个问题。现在它使用一个非常安全的方法来生成临时文件。如果文件名已被使用,这可能仍然失败。如果你想确保这个工作正常,你必须循环,直到你得到一个免费的文件名并检查文件是否已被使用。 – Nitram

+0

http://pastebin.com/HyEdu0Sm此代码仍然创建相同的错误。我能够检查变量的值,并且“fileExists”确实返回false,所以我会假设这会起作用 –