Share via


C# ZipArchive returning empty files

Question

Thursday, June 18, 2015 4:07 PM

I am trying to bundle up a bunch of files in the C# ZipArchive with the following code adapted from this page:

http://stackoverflow.com/questions/17232414/creating-a-zip-archive-in-memory-using-system-io-compression

My version is a little different because I am adding a Stream from an existing method.

Also, I am returning a byte array.

                byte[] arrayByteReturn = null;

                using (var memoryStream = new MemoryStream())
                {
                    using (var archive = new ZipArchive(memoryStream, ZipArchiveMode.Create, true))
                    {
                        foreach (string strFileName in arrayFileNames)
                        {
                            strErrorFileName = strFileName;
                            var demoFile = archive.CreateEntry(strFileName);

                            using (var entryStream = demoFile.Open())
                            using (var streamWriter = new StreamWriter(entryStream))
                            {
                                Stream strFile= GetStream.OpenFile(strFileName);
                                streamWriter.Write(strFile);
                            }
                        }
                    }
                    arrayByteReturn = memoryStream.ToArray();
                }

This does produces the a zip with the correct filenames but all the files are empty.

Can someone help?

All replies (5)

Thursday, June 18, 2015 5:26 PM ✅Answered

@jjmonty

untested by me, so not sure if this is the problem;

from your SO link, note this code:

using (var fileStream = new FileStream(@"C:\Temp\test.zip", FileMode.Create))
{
    memoryStream.Seek(0, SeekOrigin.Begin);
    memoryStream.CopyTo(fileStream);
}

and this comment:

"Your files position goes to the end of file so it is unable to write anything so that if you try reset the position property of stream to 0 it will work." –  Coder of Code Jul 30 '13 at 6:08


Friday, June 19, 2015 12:11 AM

This line

streamWriter.Write(strFile);

sends streamWriter (which is your archive file) to strFile (which is the source file) - basically you have it back to front.  Try something like

strFile.CopyTo(streamWriter);

(I don't know what GetStream is but I would guess that you need to close the source file when you are finished with it.)

PS - You might want to have a look to make sure that there is something in your source files as well.


Friday, June 19, 2015 8:31 AM

Hi jjmonty,

As you use a MemoryStream and the MemoryStream is not clear, if you stream supports writing and it is the file path that you want to create, I think you could refer to the following codes. It just is a reference and may be helpful to you.

            using (FileStream zipToCreate = new FileStream(@"C:\Users\xxx\Desktop\abc.zip", FileMode.CreateNew))
            {
                using (ZipArchive archive = new ZipArchive(zipToCreate, ZipArchiveMode.Create))
                {
                    string[] filePaths = Directory.GetFiles(@"C:\Users\xxx\Desktop\Temp\");
                    for (int i = 0; i < filePaths.Length; i++)
                    {
                        archive.CreateEntryFromFile(filePaths[i], Path.GetFileName(filePaths[i]));
                    }
                }
            }

Besides, you could refer to the following article. It gives you a very detailed guidance about ZipArchive and I think you could learn a lot of things.

http://www.codeproject.com/Articles/381661/Creating-Zip-Files-Easily-in-NET

Best Regards,

Weibo Zhang


Friday, June 19, 2015 9:54 AM

Weibo Zhang, I don't think you read my code closely enough. I am zipping a bunch of files as Streams and returning the new zip as a Stream.

I do not have all the filepaths for the files in the zip which your code assumes.


Friday, June 19, 2015 10:00 AM

Gerry Lowry, your suggestion helped me the most. I was not resetting the stream to the start and then copying.

Here is the new code (edit in bold):

     byte[] arrayByteReturn = null;

     using (var memoryStream = new MemoryStream())
     {
         using (var archive = new ZipArchive(memoryStream, ZipArchiveMode.Create, true))
         {
             foreach (string strFileName in arrayFileNames)
             {
                 strErrorFileName = strFileName;
                 var demoFile = archive.CreateEntry(strFileName);

                 using (var entryStream = demoFile.Open())
                 using (var streamWriter = new StreamWriter(entryStream))
                 {
                   Stream strFile= GetStream.OpenFile(strFileName);
**                   strFile.Seek(0, SeekOrigin.Begin);**
**                   strFile.CopyTo(entryStream);**
                   streamWriter.Write(strFile);
                 }
             }
         }
         arrayByteReturn = memoryStream.ToArray();
     }