2010-09-20 23 views
16

deseo saber si hay alguna manera de evitar tener un [Content_Types] .xml archivo dentro del archivo zip durante el uso de .NET ZipPackage clase.cómo evitar [Content_Types] .xml en la clase de .NET ZipPackage

+0

¿Cuál es su razón para usar 'ZipPackage'? Si desea crear un archivo zip a partir de documentos existentes, es mejor que use 'GZipStream' y clases relacionadas en el espacio de nombres' System.IO.Compression'. – shahkalpesh

+5

@shahkalpesh: GZipStream es solo para archivos individuales. –

+0

@Henk: Deseo crear un archivo ".zip" para un solo documento. ¿Es posible crear un archivo ".zip" usando GZipStream? –

Respuesta

10

Paquetes postales no son archivos (normal) Zip. Deben seguir una estructura impuesta y contener ese archivo Content_Types.xml en la raíz. ZipPackage = ZipArchive + Structure.

Si desea crear (y especialmente si desea leer) archivos Zip normales, necesitará una biblioteca adicional, no hay soporte en el BCL.

Ver SharpZipLib (GPL) y DotNetZip

+0

¿Qué haces? significa por "normal"? ¿No es posible crear un archivo ".zip" usando lo que está dentro de .NET Framework? –

+1

@Kushal: Paquete = Archivo Zip + Estructura. Para que pueda leer un paquete Zip con WinZip, pero no puede leer (todos) los archivos Zip con ZipPackage –

+0

Solo deseo comprimir un solo archivo. Pero no puedo deshacerme del archivo .xml que se integra con el paquete. –

3

Si no llama al método .Flush(), no habrá tal archivo

+0

Esta es una excelente respuesta a esta pregunta, y esta técnica funcionó para mí. Si crea su 'ZipPackage' con una secuencia de memoria, agregue sus partes, y luego copie la secuencia antes de eliminar el' ZipPackage' (que llama '.Flush()'), entonces el archivo zip resultante contiene solo las partes agregadas y no " [Context_Types] .xml ". –

+0

@DLeh Disculpa, ¿a qué te refieres? Este es exactamente el método para evitar que el archivo se haya agregado al archivo comprimido. – Yiping

+0

@MattKlein Gracias.Encontré esto por accidente (olvidé deshacerme). Pero parece estar funcionando. – Yiping

1

Sí se puede crear paquetes postales sin el contenido XML adicional archivo añadió

Inspirado por este enlace: Using System.IO.Packaging to generate a ZIP file

Usando anterior descubrimiento mencionado por Yiping puede avoi d el archivo extra xml agregado al paquete. Guardar corriente postal de la corriente de memoria a un archivo zip físico antes de archivo zip se cierra de esta manera:

public static void AddFilesToZip(string zipFilename, List<String> filesToAdd) 
{ 
    using (var memStream = new MemoryStream()) 
    { 
     using (Package zip = System.IO.Packaging.Package.Open(memStream, FileMode.Create)) 
     { 

      foreach (var fileToAdd in filesToAdd) 
      { 
       string destFilename = ".\\" + Path.GetFileName(fileToAdd); 
       Uri uri = PackUriHelper.CreatePartUri(new Uri(destFilename, UriKind.Relative)); 

       //Existing parts not likely in fresh memory stream 
       if (zip.PartExists(uri)) 
       { 
        zip.DeletePart(uri); 
       } 

       PackagePart part = zip.CreatePart(uri, "", CompressionOption.Normal); 

       using (FileStream fileStream = new FileStream(fileToAdd, FileMode.Open, FileAccess.Read)) 
       { 

        using (Stream dest = part.GetStream()) 
        { 
         CopyStream(fileStream, dest); 
        } 
       } 
      } 

      //The zip Package will add an XML content type file to memeory stream when it closes 
      //so before it closes we save the memorystream to physical zip file. 
      using (FileStream zipfilestream = new FileStream(zipFilename, FileMode.Create, FileAccess.Write)) 
      { 
       memStream.Position = 0; 
       CopyStream(memStream, zipfilestream); 
      } 

      //Thats it. Zip file saved to file. Things added by package after this point will be to meory stream finally disposed. 
     } 
    } 
} 
+0

Tengo esto funcionando, gracias. La parte importante es memStream.Position = 0; sin esto obtendrás un zip vacío. – apc

+1

¿De dónde viene 'CopyStream'? Probé tu código, pero cuando extraigo el contenido de .zip, dice que el .zip está dañado. –

0

Hombre, esto me ha ayudado mucho! ¡Rock! Tuve que usar esto porque mi viejo marco (3.5). Sólo para complementar, véase más adelante la implementación de la función CopyStream:

private void CopyStream(Stream source, Stream target) 
    { 
     const int bufSize = 0x1000; 
     byte[] buf = new byte[bufSize]; 
     int bytesRead = 0; 
     while ((bytesRead = source.Read(buf, 0, bufSize)) > 0) 
      target.Write(buf, 0, bytesRead); 
    } 
0

También puede establecer ámbito privado _contentTypeHelper de System.IO.Packaging.Package a null (usando DynamicObject).

Cuestiones relacionadas