I'm trying to compress two text files to a zip file. This is how my public method looks like:
public ActionResult Index()
{
byte[] file1 = System.IO.File.ReadAllBytes(@"C:\file1.txt");
byte[] file2 = System.IO.File.ReadAllBytes(@"C:\file2.txt");
Dictionary<string, byte[]> fileList = new Dictionary<string, byte[]>();
fileList.Add("file1.txt", file1);
fileList.Add("file2.txt", file2);
CompressToZip("zip.zip", fileList);
return View();
}
This is how my compress method looks like:
private void CompressToZip(string fileName, Dictionary<string, byte[]> fileList)
{
using (var memoryStream = new MemoryStream())
{
foreach (var file in fileList)
{
using (var archive = new ZipArchive(memoryStream, ZipArchiveMode.Create, true))
{
var demoFile = archive.CreateEntry(file.Key);
using (var entryStream = demoFile.Open())
using (var b = new BinaryWriter(entryStream))
{
b.Write(file.Value);
}
}
}
using (var fileStream = new FileStream(fileName, FileMode.Create))
{
memoryStream.Seek(0, SeekOrigin.Begin);
memoryStream.CopyTo(fileStream);
}
}
}
In this approach, the zip folder is perfectly created. However the issue is I'm getting only one file inside the zip folder (Just the second file will be created inside the zip folder). There are no errors found.
Question: How to compress both text files into the zip folder?
Thank you in advanced!
Zipped (compressed) files take up less storage space and can be transferred to other computers more quickly than uncompressed files. In Windows, you work with zipped files and folders in the same way that you work with uncompressed files and folders.
Let's say there are folders named A, B, C, etc. through Z. Inside each folder are a number of zip files. I can select all the zips in a folder, right click, select 7zip, and select Extract to "*" and it works perfectly.
Your code is actually saving two separate zip archives to the zip.zip
file (a new ZipArchive
is created for each file to be compressed). The first zip archive contains only file1.txt
, the second only file2.txt
. When you open zip.zip
in Windows Explorer, it shows just the contents of the second zip archive.
To create a single zip archive containing both files, just move the creation of the ZipArchive
outside of your fileList
loop:
using (var archive = new ZipArchive(memoryStream, ZipArchiveMode.Create, true))
{
foreach (var file in fileList)
{
var demoFile = archive.CreateEntry(file.Key);
using (var entryStream = demoFile.Open())
using (var b = new BinaryWriter(entryStream))
{
b.Write(file.Value);
}
}
}
At first glance, I would suggest that your foreach
statement around the using var (archive = new ZipArchive...)
is the wrong way round.
This way you are creating a new ZipArchive
each time you iterate the foreach
loop.
Surely you want to create the ZipArchive
and loop through the foreach
inside of that?
Like this:
private void CompressToZip(string fileName, Dictionary<string, byte[]> fileList)
{
using (var memoryStream = new MemoryStream())
{
using (var archive = new ZipArchive(memoryStream, ZipArchiveMode.Create, true))
{
foreach (var file in fileList)
{
var demoFile = archive.CreateEntry(file.Key);
using (var entryStream = demoFile.Open())
using (var b = new BinaryWriter(entryStream))
{
b.Write(file.Value);
}
}
}
using (var fileStream = new FileStream(fileName, FileMode.Create))
{
memoryStream.Seek(0, SeekOrigin.Begin);
memoryStream.CopyTo(fileStream);
}
}
}
Hope this helps!
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With