.NET에서 프로그래밍 방식으로 압축 파일을 분리합니다

StackOverflow https://stackoverflow.com/questions/836736

  •  08-07-2019
  •  | 
  •  

문제

방향으로 감금 된 파일을 프로그래밍으로 풀려고 노력하고 있습니다.

나는 사용 시도했다 System.IO.Compression.GZipStream .NET의 클래스이지만 앱이 실행되면 (실제로 단위 테스트)이 예외가 발생합니다.

System.io.InValidDataException : GZIP 헤더의 마법 번호가 올바르지 않습니다. GZIP 스트림을 통과하고 있는지 확인하십시오 ..

나는 이제 그것을 알고있다 .zip 파일은 a와 같지 않습니다 .gz 파일, 그리고 그 GZip 동일하지 않습니다 Zip.

그러나 Zipped 파일을 수동으로 두 번 클릭 한 다음 "모든 파일 추출"-버튼을 클릭하여 파일을 추출 할 수 있으므로 코드에서도이를 수행하는 방법이 있어야한다고 생각합니다.

따라서 나는 사용하려고 노력했다 Process.Start() ZIPPER 파일의 경로를 입력으로. 이로 인해 내 앱이 Zipped 파일의 내용을 보여주는 창을 열게됩니다. 모두 괜찮지 만 앱은 "모든 파일 추출"-버튼을 클릭하기 위해 서버가없는 서버에 설치됩니다.

그렇다면 내 앱을 ZIPPER 파일에서 파일을 추출하도록하려면 어떻게해야합니까?

아니면 다른 방법이 있습니까? 타사 라이브러리 나 앱을 다운로드하지 않고 코드로 수행하는 것이 좋습니다. 보안 부서는 그것에 대해 너무 화려하지 않습니다 ...

도움이 되었습니까?

해결책

우리는 사용했습니다 Sharpziplib 많은 프로젝트에서 성공적으로. 나는 그것이 타사 도구라는 것을 알고 있지만 소스 코드가 포함되어 있으며 여기에서 바퀴를 재창조하기로 선택하면 통찰력을 제공 할 수 있습니다.

다른 팁

와 함께 .NET 4.5 이제 .NET 프레임 워크를 사용하여 파일을 압축 할 수 있습니다.

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 네임 스페이스 및 System.IO.Compression.FileSystem.

무료 및 외부 DLL 파일이 없습니다. 모든 것이 하나의 CS 파일에 있습니다. 하나의 다운로드는 CS 파일 일뿐입니다. 다른 다운로드는 매우 쉽게 이해하기 쉬운 예입니다. 오늘 시도해 보았고 설정이 얼마나 간단한 지 믿을 수 없습니다. 그것은 첫 번째 시도, 오류가없고 아무것도 없었습니다.

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

dotnetzip 라이브러리를 사용하십시오 http://www.codeplex.com/dotnetzip

지퍼 파일 조작을위한 클래스 라이브러리 및 도구 세트. vb, c# 또는 .NET 언어를 사용하여 ZIP 파일을 쉽게 작성, 추출 또는 업데이트하십시오 ...

DotNetZip은 전체 .NET 프레임 워크를 사용하여 PC에서 작동하며 .NET Compact 프레임 워크를 사용하는 모바일 장치에서도 실행됩니다. VB, C#또는 .NET 언어 또는 스크립팅 환경에서 Zip 파일을 작성하고 읽으십시오 ...

당신이 원하는 것이 더 나은 deflatestream 또는 gzipstream 클래스라면 .NET BCL을 구축 한 것들을 대체 할 수 있습니다. dotnetzip의 deflatestream 및 gzipstream은 zlib의 .NET 포트를 기반으로 독립형 어셈블리로 제공됩니다. 이 스트림은 압축 수준을 지원하고 내장 클래스보다 훨씬 더 나은 성능을 제공합니다. 세트를 완성하기위한 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을 사용합니다. Microsoft는 압축 알고리즘 만 제공하므로 Zip 파일 아카이브 형식에 대한 좀 더 많은 정보가 필요합니다.

zipfldr.dll을 사용해 볼 수도 있습니다. Microsoft의 압축 라이브러리입니다 (보내기 메뉴에서 압축 폴더). COM 라이브러리 인 것처럼 보이지만 문서화되지 않은 것입니다. 실험을 통해 당신을 위해 일할 수 있습니다.

에서 여기 :

.gz의 확장이있는 파일에 작성된 압축 된 gzipstream 객체는 많은 일반적인 압축 도구를 사용하여 압축을 억제 할 수 있습니다. 그러나이 클래스는 본질적으로 .zip 아카이브에서 파일을 추가하거나 파일을 추출하는 기능을 제공하지 않습니다.

이것을 사용하여 여러 파일을 지퍼 또는 압축 해제하는 데 사용합니다. REGEX 물건은 필요하지 않지만 날짜 스탬프를 변경하고 원치 않는 밑줄을 제거하는 데 사용합니다. compress >> zippath 문자열에서 빈 문자열을 사용하여 필요한 경우 모든 파일에 무언가를 접두사합니다. 또한 나는 보통 내가하고있는 일에 따라 compress () 또는 demompress ()를 언급합니다.

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);
            }
        }


    }
}

deflatestream을 사용하여 .NET 3.5 내에서 모두 할 수 있습니다. .NET 3.5에 부족한 것은 ZIPPER 파일을 구성하는 데 사용되는 파일 헤더 섹션을 처리하는 기능입니다. Pkware는이 정보를 게시했으며 사용되는 구조를 작성한 후 ZIP 파일을 처리하는 데 사용할 수 있습니다. 특히 번거롭지 않으며 타사 코드를 사용하지 않고 도구 구축에서 좋은 관행입니다.

한 줄의 답변은 아니지만 시간을 기꺼이하고 시간을 내면 완전히 가능합니다. 나는 몇 시간 안에 이것을하기 위해 수업을 작성했으며, 그로부터 얻은 것은 .NET 3.5 만 사용하여 파일을 지퍼 및 압축 할 수있는 능력입니다.

이것은 할 것입니다 System.IO.Compression.ZipFile.ExtractToDirectory(ZipName, ExtractToPath)

나는 발견했다 이 하나 (NUGET의 압축 패키지) 오늘, 나는 DotnetZip에서 단단한 버그에 부딪 쳤 기 때문에 지난 2 년 동안 DotnetZip에서 많은 일을하지 않았다는 것을 깨달았습니다.

압축 패키지는 마른 상태이며 나에게 일을했습니다. Dotnetzip이 가지고있는 버그가 없었습니다. 또한 실제 감압을 위해 Microsoft BCL에 의존하는 합리적으로 작은 파일이었습니다. 압축을 피우는 동안 진행 상황을 추적 할 수 있도록 필요한 조정을 쉽게 조정할 수있었습니다. 추천합니다.

Embed Ressources에서 :

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

지금까지 .iso 파일을 추출하여 서버에서 임시 경로로 복사하여 USB 스틱에서 추출하기 위해 CMD 프로세스를 사용했습니다. 최근에 나는 이것이 10GB 미만의 .iso와 완벽하게 작동한다는 것을 발견했습니다. 29GB와 같은 ISO의 경우이 방법은 어떻게 든 붙어 있습니다.

    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-unzip 공식 웹 사이트에서 unzip.exe를 다운로드하면됩니다.

 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; }
    }        
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top