Glengamoi (Forum) · AspHeute · .NET Heute (RSS-Suche) · AspxFiles (Wiki) · .NET Blogs
ASP German Homepage Homepage
 

Liste

.NET 2.0 (1)
.NET Allgemein (16)
.NET Fu (5)
ADO.NET (11)
Aprilscherz (3)
ASP Grundlagen (44)
ASP Tricks (83)
ASP.NET (44)
ASPIntranet.de (5)
C# (28)
Datenbank (44)
Dokumentation (4)
IIS 6.0 (1)
Komponenten (29)
Optimierung (10)
Server (21)
Sicherheit (34)
Tee Off (6)
VB.NET (6)
WAP (8)
Web Services (11)
XML (9)

RSS 2.0 - Die neuesten fünf Artikel auf AspHeute.com


 

Suchen





 

English Articles
Chinese Articles
Unsere Autoren
 
Link zu AspHeute
Impressum
Werben
Anfragen

Eine Klasse für sich - die .NET Zip Library

Geschrieben von: Christoph Wille
Kategorie: .NET Allgemein

Das .NET Framework umfasst hunderte Klassen, doch etwas fehlt: es gibt keinerlei Klassen zur Komprimierung und Dekomprimierung von Zip Archiven. Diesem Fehlen kann aber mit der .NET Zip Library (#ziplib) abgeholfen werden - diese unterstützt sowohl das Zip als auch das GZip Format, ist gratis, und kommt mit C# Code inklusive.

Die #ziplib (SharpZipLib, ehemals NZipLib) kann von ic#code downgeloadet werden. Obwohl die Library selbst unter der GPL (GNU General Public License) vertrieben wird, darf man dank der Ausnahme die Library in Nicht-GPL Programmen einsetzen.

Verwendung in ASP.NET

Die Library ist als DLL Assembly kompiliert, und ist im verlinkten Download als Datei namens SharpZipLib.dll enthalten. Der erste Schritt ist also, sie in das bin Verzeichnis der Website zu verfrachten - dieser Vorgang wurde bereits im Artikel Eine Eurokonvertierungskomponente in C# erstellen beschrieben

Jetzt wo die Komponente dank XCOPY Deployment bereits registriert ist, kann sie auch schon verwendet werden. Dazu habe ich eine kleine ASP.NET Seite geschrieben, die den Inhalt eines Zip Archivs ausgibt: den Dateinamen, die Dateigröße, die komprimierte Größe. Der Sourcecode ist im Download des heutigen Artikels als ListZipContent.aspx enthalten:

<% @Page Language= "C#" %>
<% @Import Namespace="System.IO" %>
<% @Import Namespace="System.Text" %>
<% @Import Namespace="ICSharpCode.SharpZipLib.Zip" %>
<%
ZipInputStream s = new ZipInputStream(File.OpenRead("c:\\test.zip"));
ZipEntry theEntry = null;
StringBuilder strOutput = new StringBuilder();

while ((theEntry = s.GetNextEntry()) != null) 
{
  strOutput.Append("<tr><td>");
  strOutput.Append(theEntry.Name);
  strOutput.Append("</td><td>");
  strOutput.Append(theEntry.Size.ToString());
  strOutput.Append("</td><td>");
  strOutput.Append(theEntry.CompressedSize.ToString());
  strOutput.Append("</td></tr>\r\n");
}

s.Close(); // clean up the file resource immediately
%>

<table>
<tr><th>File name</th><th>Actual Size</th><th>Compressed Size</th></tr>
<%
  Response.Write(strOutput.ToString());
%>
</table>

Dieses Beispiel verwendet die Klassen aus dem ICSharpCode.SharpZipLib.Zip Namespace, deshalb muß ein entsprechendes Import Statement vorhanden sein. Eine genaue Beschreibung aller Namespaces und Klassen können Sie in der Hilfedatei Documentation.chm finden. Diese Dokumentation ist ähnlich zur .NET Framework Reference aufgebaut, das navigieren sollte also kein Problem sein.

In obigem Beispiel verwende ich die ZipInputStream Klasse, um auf eine bereits existierende (hardcodierte) Zip Datei zuzugreifen. Nach dem Öffnen des Archivs laufe ich mittels einer while Schleife alle Einträge (ZipEntry Klasse) durch, und puffere den generierten Tabelleninhalt in einem StringBuilder Objekt (siehe auch Artikel Die String Klasse in C#).

Die Ausgabe sieht wenig aufregend so aus, ist aber Beweis, daß es funktioniert wie geplant:

Dateien in Archiven betrachten

Jetzt haben wir eine Liste von Dateien - wie kommen wir aber an deren Inhalte? Sprich wie dekomprimieren wir die einzelnen Dateien? Hierzu ein modifiziertes Beispiel, das an der Kommandozeile läuft (ViewZipFile.cs):

using System;
using System.Text;
using System.IO;

using ICSharpCode.SharpZipLib.Zip;

class MainClass
{
  public static void Main(string[] args)
  {
    ZipInputStream s = new ZipInputStream(File.OpenRead(args[0]));
    ZipEntry theEntry;

    int nBytes = 2048;
    byte[] data = new byte[2048];

    while ((theEntry = s.GetNextEntry()) != null) 
    {
      Console.WriteLine(theEntry.Name);
      Console.Write("Eintrag anzeigen? (j/n)");

      if (Console.ReadLine() == "j") 
      {
        while((nBytes = s.Read(data, 0, data.Length))  > 0)
        {
           Console.Write(new ASCIIEncoding().GetString(data,0,nBytes));
        }
      }
      Console.WriteLine();
    }
    s.Close();
  }
}

Im Prinzip ist das Auslesen einer komprimierten Datei aus dem Zip Archiv nur der Read Befehl, den man von Streams sowieso schon kennt. Wir verarbeiten die erhaltenen Daten so, daß wir sie mittels ASCII Encoding an der Konsole ausgeben. Natürlich könnte man statt der Konvertierung die Daten in eine Datei auf der Festplatte schreiben.

Kompiliert wird diese Anwendung wie folgt (Annahme: NZipLib.dll liegt im gleichen Verzeichnis):

csc /target:exe /reference:SharpZipLib.dll ViewZipFile.cs

Der Aufruf erfolgt so:

viewzipfile c:\test.zip

Und schon kann man sich die Dateien im Zip Archiv ansehen.

Zip Archive erstellen

Auslesen ist ja leicht! Und wie steht's mit dem Erstellen eines Zip Archivs? Nun, sehen wir uns ein kleines Beispielprogramm an, das alle Dateien eines Unterverzeichnisses in eine Zip Datei schreibt (CreateZipFile):

using System;
using System.IO;

using ICSharpCode.SharpZipLib.Zip;

class MainClass
{
  public static void Main(string[] args)
  {
    // alle Dateien im angegebenen Ordner werden komprimiert
    string[] aFilenames = Directory.GetFiles(args[0]);
    
    // der Name der Zipdatei ist der zweite Parameter im Aufruf
    ZipOutputStream s = new ZipOutputStream(File.Create(args[1]));
    
    // Komprimierungslevel setzen: 0 [keine] - 9 [stärkste]
    s.SetLevel(5); 
    
    for (int i=0; i < aFilenames.Length; i++)
    {
      FileStream fs = File.OpenRead(aFilenames[i]);
      
      // im Normalfall allokiert man die Buffer im voraus
      // hier aus Klarheitsgründen pro Datei einmal
      byte[] buffer = new byte[fs.Length];
      fs.Read(buffer, 0, buffer.Length);

      // und jetzt schreiben wir einen ZipEntry & die Daten      
      ZipEntry entry = new ZipEntry(aFilenames[i]);
      s.PutNextEntry(entry);
      s.Write(buffer, 0, buffer.Length);
    }
    
    s.Finish();
    s.Close();
  }
}

Im Komprimierungsszenario arbeiten wir mit der ZipOutputStream Klasse, die uns bei der Erstellung des Archivs zur Seite steht. Im Prinzip ist alles ein umgekehrter Vorgang zum Entzippen: hier erstellen wir einen ZipEntry, und anstatt daß wir die Datei aus dem Archiv auslesen, schreiben wir sie in das Archiv.

Verwendet wird das Programm wie folgt:

createzipfile c:\verzeichnis c:\zipfile.zip

Ich denke daß das Erzeugen eines Archivs um nichts schwieriger ist als das Auslesen von Dateien aus einem Archiv.

Schlußbemerkung

Ich habe heute nur die Verwendung der Zip Klassen in der Library gezeigt. Allerdings werden die GZip Klassen völlig analog verwendet, da sie von denselben Basisklassen ableiten. Zip ahoi!

Download des Codes

Klicken Sie hier, um den Download zu starten.

Verwandte Artikel

Die String Klasse in C#
Directory Browsing a la .NET
Eine Eurokonvertierungskomponente in C# erstellen

Links zu anderen Sites

#ZipLib (SharpZipLib) Download

Wenn Sie jetzt Fragen haben...

Wenn Sie Fragen rund um die in diesem Artikel vorgestellte Technologie haben, dann schauen Sie einfach bei uns in den Community Foren der deutschen .NET Community vorbei. Die Teilnehmer helfen Ihnen gerne, wenn Sie sich zur im Artikel vorgestellten Technologie weiterbilden möchten.

Eine weitere sehr hilfreiche Resource ist das deutsche ASP.NET Wiki, das als zentrale Anlaufstelle für Tips, Tricks, Know How und alles Nützliche was man in seinem Alltag als (ASP).NET-Entwickler so braucht und entdeckt gedacht ist.

Haben Sie Fragen die sich direkt auf den Inhalt des Artikels beziehen, dann schreiben Sie dem Autor! Unsere Autoren freuen sich über Feedback zu ihren Artikeln. Ein einfacher Klick auf die Autor kontaktieren Schaltfläche (weiter unten) und schon haben Sie ein für diesen Artikel personalisiertes Anfrageformular.

 

Und zu guter Letzt möchten wir Sie bitten, den Artikel zu bewerten. Damit helfen Sie uns, die Qualität der Artikel zu verbessern - und anderen Lesern bei der Auswahl der Artikel, die sie lesen sollten.

Bewerten Sie diesen Artikel
 Sehr gut   Nicht genügend  
   1  2  3  4  5  
 

  
   Für Ausdruck optimierte Seite

©2000-2006 AspHeute.com
Alle Rechte vorbehalten. Der Inhalt dieser Seiten ist urheberrechtlich geschützt.
Eine Übernahme von Texten (auch nur auszugsweise) oder Graphiken bedarf unserer schriftlichen Zustimmung.