5

Given a path to a file, how can I validate that the file is a password-protected zip file?

i.e., how would I implement this function?

bool IsPasswordProtectedZipFile(string pathToFile)

I don't need to unzip the file -- I just need to verify that it's a ZIP and has been protected with some password.

Thanks

frankadelic
  • 20,543
  • 37
  • 111
  • 164
  • see this question: [how to zip and unzip using password in c# program](http://stackoverflow.com/questions/1607858/how-to-zip-and-unzip-using-password-in-c-program) – manji Oct 28 '09 at 21:38

4 Answers4

8

Using SharpZipLib, the following code works. And by works I mean entry.IsCrypted returns true or false based on whether or not there is a password for the first entry in the zip file.

var file = @"c:\testfile.zip";
FileStream fileStreamIn = new FileStream(file, FileMode.Open, FileAccess.Read);
ZipInputStream zipInStream = new ZipInputStream(fileStreamIn);
ZipEntry entry = zipInStream.GetNextEntry();
Console.WriteLine("IsCrypted: " + entry.IsCrypted);

There's a simple tutorial on using SharpZipLib on CodeProject.

Thus a simple implementation looks something like:

public static bool IsPasswordProtectedZipFile(string path)
{
    using (FileStream fileStreamIn = new FileStream(path, FileMode.Open, FileAccess.Read))
    using (ZipInputStream zipInStream = new ZipInputStream(fileStreamIn))
    {
        ZipEntry entry = zipInStream.GetNextEntry();
        return entry.IsCrypted;
    }
}

Note there's no real error handling or anything...

Nader Shirazie
  • 10,736
  • 2
  • 37
  • 43
  • Thanks - the key point I'm realizing now is that I need to look at the individual entries inside the ZIP, since they can be encrypted individually. The password doesn't apply to the whole ZIP file. DotNetZip at codeplex has similar capability, also. – frankadelic Oct 29 '09 at 05:39
  • Yes, exactly. And because of that, you may for example, want to scan through the entire archive looking for _any_ entries that have a password, rather than just the first... – Nader Shirazie Oct 29 '09 at 08:15
3

In ZIP archives, the password is not placed on the file, but on the individual entries within the file. A zip can contain some entries encrypted and some not. Here's some example code to check for encryption on entries in DotNetZip:

int encryptedEntries = 0;
using (var zip = ZipFile.Read(nameOfZipFile)) 
{
    // check a specific, named entry: 
    if (zip["nameOfEntry.doc"].UsesEncryption)
       Console.WriteLine("Entry 'nameOfEntry.doc' uses encryption"); 

    // check all entries: 
    foreach (var e in zip)
    {
       if (e.UsesEncryption)
       {
           Console.WriteLine("Entry {0} uses encryption", e.FileName); 
           encryptedEntries++; 
       }
    }
}

if (encryptedEntries > 0) 
    Console.WriteLine("That zip file uses encryption on {0} entrie(s)", encryptedEntries); 

If you'd prefer, you can use LINQ:

private bool ZipUsesEncryption(string archiveToRead)
{
    using (var zip = ZipFile.Read(archiveToRead))
    {
        var selection = from e in zip.Entries
            where e.UsesEncryption
            select e;

        return selection.Count > 0;
    }
}
Cheeso
  • 189,189
  • 101
  • 473
  • 713
1

At this point in the .NET Framework maturity you will need to use a 3rd party tool. There are many commercial libraries that can be Googled. I'm suggesting one free one from Microsoft's Codeplex website DotNetZip. The front page states "the library supports zip passwords".

John K
  • 28,441
  • 31
  • 139
  • 229
0

There is no 100% correct way to check if all zip entries is encrypted. every entry in a zipfile is independent and could has its own password/encrypted method.

for most cases, zipfile is zipped by some software, these software will ensure every entry in a zipfile has a common password and encrypted method.

So, using the first zipentry(not a directory) to check if that zipfile is encrypted can cover most cases.

Mr rain
  • 983
  • 5
  • 13
  • 27