Распакуйте файлы программно in.net



Я пытаюсь программно распаковать архивный файл.



Я пробовал использовать System.IO.Compression.GZipStream класс в .NET, но когда мое приложение работает (на самом деле модульный тест) я получаю это исключение:




System.IO.InvalidDataException: магическое число в заголовке GZip неверно. Убедитесь, что вы проходите в потоке GZip..




теперь я понимаю, что a .zip файл не совпадает с и GZip - это не то же самое как Zip.



однако, поскольку я могу извлечь файл, вручную дважды щелкнув сжатый файл, а затем нажав кнопку "Извлечь все файлы", я думаю, что должен быть способ сделать это и в коде.



поэтому я попытался использовать Process.Start() С путем к архивному файлу в качестве входных данных. Это приводит к тому, что мое приложение открывает окно, отображающее содержимое в сжатом файле. Это все нормально, но приложение будет установлено на сервере без каких-либо вокруг, чтобы нажать кнопку " Извлечь все файлы"-кнопка.



Итак, как я могу получить мое приложение для извлечения файлов в архивированных файлах?



или есть другой способ сделать это? Я предпочитаю делать это в коде, без загрузки каких-либо сторонних библиотек или приложений; отдел безопасности не слишком увлекается этим...

356   14  

14 ответов:

мы использовали SharpZipLib успешно на многих проектах. Я знаю, что это сторонний инструмент, но исходный код включен и может дать вам некоторое представление, если вы решили изобретать велосипед.

С .NET 4.5 теперь вы можете распаковать файлы с помощью .NET framework:

using System;
using System.IO;

namespace ConsoleApplication
{
  class Program
  {
    static void Main(string[] args)
    {
      string startPath = @"c:\example\start";
      string zipPath = @"c:\example\result.zip";
      string extractPath = @"c:\example\extract";

      System.IO.Compression.ZipFile.CreateFromDirectory(startPath, zipPath);
      System.IO.Compression.ZipFile.ExtractToDirectory(zipPath, extractPath);
    }
  }
}

приведенный выше код был взят непосредственно из документации Microsoft:http://msdn.microsoft.com/en-us/library/ms404280 (v=vs. 110). aspx

ZipFile содержится в сборке System.IO.Compression.FileSystem. (Спасибо nateirvin...см. комментарий ниже)

Для .Net 4.5+

не всегда желательно записывать несжатый файл на диск. В качестве ASP.Net разработчик, мне придется возиться с разрешениями на предоставление прав для моего приложения для записи в файловую систему. Работая с потоками в памяти, я могу обойти все это и читать файлы напрямую:

using (ZipArchive archive = new ZipArchive(postedZipStream))
{
    foreach (ZipArchiveEntry entry in archive.Entries)
    {
         var stream = entry.Open();
         //Do awesome stream stuff!!
    }
}

кроме того, вы все еще можете записать распакованный файл на диск, вызвав ExtractToFile():

using (ZipArchive archive = ZipFile.OpenRead(pathToZip))
{
    foreach (ZipArchiveEntry entry in archive.Entries)
    {
        entry.ExtractToFile(Path.Combine(destination, entry.FullName));
    }
} 

для использования ZipArchive - класс, вам нужно будет добавить ссылку System.IO.Compression пространство имен.

бесплатно, и никаких внешних DLL файлов. Все в одном файле CS. Одна загрузка-это просто файл CS, другая загрузка-очень простой для понимания пример. Просто попробовал это сегодня, и я не могу поверить, насколько простой была установка. Он работал с первой попытки, никаких ошибок, ничего.

https://github.com/jaime-olivares/zipstorer

используйте библиотеку DotNetZip в http://www.codeplex.com/DotNetZip

библиотеку классов и набор инструментов для работы с zip-файлами. Используйте VB, C# или любой язык .NET, чтобы легко создавать, извлекать или обновлять zip-файлы...

DotNetZip работает на ПК с полной .NET Framework, а также работает на мобильных устройствах, использующих .NET Compact Framework. Создание и чтение zip-файлов в VB, C#, любом языке .NET или любой среде сценариев...

Если все, что вы хотите, это лучший класс DeflateStream или gzipstream, чтобы заменить тот, который встроен в .NET BCL, DotNetZip тоже имеет это. DotNetZip DeflateStream и GZipStream доступны в отдельной сборке, основанной на .NET-порту Zlib. Эти потоки поддерживают уровни сжатия и обеспечивают гораздо лучшую производительность, чем встроенные классы. Существует также ZlibStream для завершения набора (RFC 1950, 1951, 1952)...

String ZipPath = @"c:\my\data.zip";
String extractPath = @"d:\myunzips";
ZipFile.ExtractToDirectory(ZipPath, extractPath);

чтобы использовать класс ZipFile, необходимо добавить ссылку на сборку System.IO.Compression.FileSystem в проекте

стандартные zip-файлов обычно используют алгоритм deflate.

для извлечения файлов без использования сторонних библиотек используйте DeflateStream. Вам понадобится немного больше информации о формате архива zip-файлов, поскольку Microsoft предоставляет только алгоритм сжатия.

вы также можете попробовать использовать zipfldr.файл DLL. Это библиотека сжатия Microsoft (сжатые папки из меню "Отправить"). Похоже, это библиотека com, но она недокументирована. Вы можете быть в состоянии получить его работа на вас через эксперименты.

с здесь:

сжатые объекты GZipStream записываются к файлу с расширением .ГЗ может быть распакованы с использованием многих общих инструменты сжатия; однако этот класс по своей сути не обеспечивает функциональность для добавления файлов или извлечение файлов из .zip-архив.

Я использую это для zip или распаковать несколько файлов. Регулярное выражение не требуется, но я использую его, чтобы изменить штамп даты и удалить ненужные подчеркивания. Я использую пустую строку в строке Compress >> zipPath для префикса чего-то для всех файлов, если это необходимо. Кроме того, я обычно комментирую либо Compress (), либо Decompress() в зависимости от того, что я делаю.

using System;
using System.IO.Compression;
using System.IO;
using System.Text.RegularExpressions;

namespace ZipAndUnzip
{
    class Program
    {
        static void Main(string[] args)
        {
            var directoryPath = new DirectoryInfo(@"C:\your_path\");

            Compress(directoryPath);
            Decompress(directoryPath);
        }

        public static void Compress(DirectoryInfo directoryPath)
        {
            foreach (DirectoryInfo directory in directoryPath.GetDirectories())
            {
                var path = directoryPath.FullName;
                var newArchiveName = Regex.Replace(directory.Name, "[0-9]{8}", "20130913");
                newArchiveName = Regex.Replace(newArchiveName, "[_]+", "_");
                string startPath = path + directory.Name;
                string zipPath = path + "" + newArchiveName + ".zip";

                ZipFile.CreateFromDirectory(startPath, zipPath);
            }

        }

        public static void Decompress(DirectoryInfo directoryPath)
        {
            foreach (FileInfo file in directoryPath.GetFiles())
            {
                var path = directoryPath.FullName;
                string zipPath = path + file.Name;
                string extractPath = Regex.Replace(path + file.Name, ".zip", "");

                ZipFile.ExtractToDirectory(zipPath, extractPath);
            }
        }


    }
}

вы можете сделать все это в .NET 3.5 с помощью DeflateStream. То, чего не хватает в .NET 3.5, - это возможность обрабатывать разделы заголовка файла, которые используются для организации сжатых файлов. PKWare опубликовал эту информацию, которую можно использовать для обработки zip-файла после создания используемых структур. Это не особенно обременительно, и это хорошая практика в создании инструментов без использования стороннего кода.

Это не однострочный ответ, но он полностью выполним, если вы готовы и можете взять время на себя. Я написал класс, чтобы сделать это за пару часов, и то, что я получил от этого, - это возможность архивировать и распаковывать файлы, используя только .NET 3.5.

Я узнал о этот (распаковать пакет на NuGet) сегодня, так как я столкнулся с жесткой ошибкой в DotNetZip, и я понял, что на самом деле не было так много работы над DotNetZip за последние два года.

пакет распаковки скуден, и он сделал эту работу для меня - у него не было ошибки, которую имел DotNetZip. Кроме того, это был достаточно маленький файл, полагающийся на Microsoft BCL для фактической декомпрессии. Я мог бы легко внести коррективы, которые мне нужны (чтобы иметь возможность чтобы отслеживать прогресс во время распаковки). Я рекомендую его.

От Размещения Средства:

using (Stream _pluginZipResourceStream = Assembly.GetExecutingAssembly().GetManifestResourceStream(programName + "." + "filename.zip"))
{
    using (ZipArchive zip = new ZipArchive(_pluginZipResourceStream))
    {
        zip.ExtractToDirectory(Application.StartupPath);
    }
}

до сих пор я использовал процессы cmd для извлечения an .iso-файл, скопируйте его во временный путь с сервера и извлеките на USB-накопитель. Недавно я обнаружил, что это прекрасно работает .iso-это меньше, чем 10Gb. Для iso, такого как 29Gb, этот метод каким-то образом застревает.

    public void ExtractArchive()
    {
        try
        {

            try
            {
                Directory.Delete(copyISOLocation.OutputPath, true); 
            }
            catch (Exception e) when (e is IOException || e is UnauthorizedAccessException)
            {
            }

            Process cmd = new Process();
            cmd.StartInfo.FileName = "cmd.exe";
            cmd.StartInfo.RedirectStandardInput = true;
            cmd.StartInfo.RedirectStandardOutput = true;
            cmd.StartInfo.CreateNoWindow = true;
            cmd.StartInfo.UseShellExecute = false;
            cmd.StartInfo.WindowStyle = ProcessWindowStyle.Normal;

            //stackoverflow
            cmd.StartInfo.Arguments = "-R";

            cmd.Disposed += (sender, args) => {
                Console.WriteLine("CMD Process disposed");
            };
            cmd.Exited += (sender, args) => {
                Console.WriteLine("CMD Process exited");
            };
            cmd.ErrorDataReceived += (sender, args) => {
                Console.WriteLine("CMD Process error data received");
                Console.WriteLine(args.Data);
            };
            cmd.OutputDataReceived += (sender, args) => {
                Console.WriteLine("CMD Process Output data received");
                Console.WriteLine(args.Data);
            };

            //stackoverflow


            cmd.Start();

            cmd.StandardInput.WriteLine("C:");
            //Console.WriteLine(cmd.StandardOutput.Read());
            cmd.StandardInput.Flush();

            cmd.StandardInput.WriteLine("cd C:\\"Program Files (x86)\"\7-Zip\");
            //Console.WriteLine(cmd.StandardOutput.ReadToEnd());
            cmd.StandardInput.Flush();

            cmd.StandardInput.WriteLine(string.Format("7z.exe x -o{0} {1}", copyISOLocation.OutputPath, copyISOLocation.TempIsoPath));
            //Console.WriteLine(cmd.StandardOutput.ReadToEnd());
            cmd.StandardInput.Flush();
            cmd.StandardInput.Close();
            cmd.WaitForExit();
            Console.WriteLine(cmd.StandardOutput.ReadToEnd());
            Console.WriteLine(cmd.StandardError.ReadToEnd());

можно использовать Info-распакуйте командная строка cod.вам нужно только скачать распаковать.exe от Info-распакуйте официальный сайт.

 internal static void Unzip(string sorcefile)
    {
        try
        {
            AFolderFiles.AFolderFilesDelete.DeleteFolder(TempBackupFolder); // delete old folder   
            AFolderFiles.AFolderFilesCreate.CreateIfNotExist(TempBackupFolder); // delete old folder   
           //need to Command command also to export attributes to a excel file
            System.Diagnostics.Process process = new System.Diagnostics.Process();
            System.Diagnostics.ProcessStartInfo startInfo = new System.Diagnostics.ProcessStartInfo();
            startInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden; // window type
            startInfo.FileName = UnzipExe;
            startInfo.Arguments = sorcefile + " -d " + TempBackupFolder;
            process.StartInfo = startInfo;
            process.Start();
            //string result = process.StandardOutput.ReadToEnd();
            process.WaitForExit();
            process.Dispose();
            process.Close();
        }
        catch (Exception ex){ throw ex; }
    }        

Comments

    Ничего не найдено.