Construire un ZIP dans la mémoire est utile lorsque vous avez besoin de diffuser un téléchargement, de transférer des bytes à un autre service, ou de stocker un archive dans une base de données sans toucher le disque. Aspose.ZIP pour .NET expose une API propre pour créer des archives Zip en utilisant des flux, choisissez les paramètres de compression et sauvegardez le résultat dans un MemoryStream ou directement à la réponse HTTP.

Ce guide fournit un code complet et correct que vous pouvez ajouter à une application de console ou à un projet ASP.NET Core.

Principaux

  • .NET 6 ou plus tard
  • Nouveau : Aspose.Zip
dotnet add package Aspose.Zip

Les noms utilisés :

using Aspose.Zip;                 // Archive, ArchiveEntry
using Aspose.Zip.Saving;          // DeflateCompressionSettings, CompressionLevel

Démarrage rapide : créer un ZIP entièrement dans la mémoire

Cet exemple ajoute des entrées d’une ligne et un fichier sur le disque, sauvegarde l’archive à un MemoryStreamet expose l’array de byte résultant.

// File: Program.cs
using System;
using System.IO;
using System.Text;
using Aspose.Zip;
using Aspose.Zip.Saving;

class Program
{
    static void Main()
    {
        // Prepare output buffer
        using var zipBuffer = new MemoryStream();

        // Choose compression (Deflate is the standard ZIP method)
        var deflate = new DeflateCompressionSettings(CompressionLevel.Normal);
        var entrySettings = new ArchiveEntrySettings(deflate);

        using (var archive = new Archive())
        {
            // 1) Add a text file from memory
            using (var ms = new MemoryStream(Encoding.UTF8.GetBytes("Hello from Aspose.ZIP in memory.")))
            {
                archive.CreateEntry("docs/readme.txt", ms, entrySettings);
            }

            // 2) Add a file from disk (streamed; not fully loaded in RAM)
            var sourcePath = "report.pdf"; // ensure it exists
            if (File.Exists(sourcePath))
            {
                using var fs = File.OpenRead(sourcePath);
                archive.CreateEntry("reports/2025/report.pdf", fs, entrySettings);
            }

            // 3) Save the ZIP to our in-memory buffer
            archive.Save(zipBuffer);
        }

        // Use the ZIP bytes as needed (send over network, write to DB, etc.)
        byte[] zipBytes = zipBuffer.ToArray();
        Console.WriteLine($"ZIP size: {zipBytes.Length} bytes");
    }
}
  • Les points clés *
  • new Archive() Créer un ZIP vide.
  • CreateEntry(entryName, stream, entrySettings) Ajouter un fichier à partir de ** tout flux lisible**.
  • archive.Save(stream) écrire l’archive à votre courant choisi (mémorisation, réseau, corps de réponse).

Ajouter un arbre entier sans écrire des fichiers temp

Walk a directory recursivement, préserver les voies relatives, et écrire l’archive finale à la mémoire.

using System.IO;
using Aspose.Zip;
using Aspose.Zip.Saving;

static class InMemoryZipper
{
    public static byte[] ZipFolderToBytes(string sourceFolder, CompressionLevel level = CompressionLevel.Normal)
    {
        if (!Directory.Exists(sourceFolder))
            throw new DirectoryNotFoundException(sourceFolder);

        var deflate = new DeflateCompressionSettings(level);
        var entrySettings = new ArchiveEntrySettings(deflate);

        using var buffer = new MemoryStream();
        using (var archive = new Archive())
        {
            var root = Path.GetFullPath(sourceFolder);
            foreach (var filePath in Directory.GetFiles(root, "*", SearchOption.AllDirectories))
            {
                var rel = Path.GetRelativePath(root, filePath).Replace(Path.DirectorySeparatorChar, '/');
                using var fs = File.OpenRead(filePath);
                archive.CreateEntry(rel, fs, entrySettings);
            }

            archive.Save(buffer);
        }
        return buffer.ToArray();
    }
}

ASP.NET Core : téléchargement ZIP sans disque I/O

Ce point de fin construit un ZIP dans la mémoire à partir de plusieurs sources et le retourne avec le type de contenu correct et un nom de fichier téléchargé.

// File: Program.cs (minimal API)
using System.Text;
using Aspose.Zip;
using Aspose.Zip.Saving;

var builder = WebApplication.CreateBuilder(args);
var app = builder.Build();

app.MapGet("/download-zip", () =>
{
    using var buffer = new MemoryStream();
    var deflate = new DeflateCompressionSettings(CompressionLevel.Normal);
    var settings = new ArchiveEntrySettings(deflate);

    using (var archive = new Archive())
    {
        // Add dynamic content (for example, a CSV generated on the fly)
        using (var ms = new MemoryStream(Encoding.UTF8.GetBytes("id,name\n1,Alice\n2,Bob\n")))
            archive.CreateEntry("data/users.csv", ms, settings);

        // Add a static file from disk if available
        var logo = "wwwroot/logo.png";
        if (File.Exists(logo))
        {
            using var fs = File.OpenRead(logo);
            archive.CreateEntry("assets/logo.png", fs, settings);
        }

        archive.Save(buffer);
    }

    buffer.Position = 0; // rewind for reading
    return Results.File(
        fileContents: buffer.ToArray(),
        contentType: "application/zip",
        fileDownloadName: $"bundle-{DateTime.UtcNow:yyyyMMdd-HHmmss}.zip");
});

app.Run();

** Pourquoi ToArray() ici ?**Les APIs minimales nécessitent une charge de paiement concrète. Pour les archives très grandes, préférez le streaming directement à HttpResponse.Body:

app.MapGet("/stream-zip", async (HttpContext ctx) =>
{
    ctx.Response.ContentType = "application/zip";
    ctx.Response.Headers.ContentDisposition = $"attachment; filename=\"bundle.zip\"";

    var deflate = new DeflateCompressionSettings(CompressionLevel.Normal);
    var settings = new ArchiveEntrySettings(deflate);

    using var archive = new Archive();

    // Add entries...
    using var ms = new MemoryStream(Encoding.UTF8.GetBytes("hello"));
    archive.CreateEntry("hello.txt", ms, settings);

    // Stream directly to the client without buffering full ZIP in RAM
    await archive.SaveAsync(ctx.Response.Body);
});

Choisissez les paramètres de compression

DeflateCompressionSettings Contrôle de vitesse vs taille :

var fastest = new DeflateCompressionSettings(CompressionLevel.Low);      // fastest, larger files
var balanced = new DeflateCompressionSettings(CompressionLevel.Normal);  // default balance
var smallest = new DeflateCompressionSettings(CompressionLevel.High);    // slowest, smallest files

Passez les paramètres via new ArchiveEntrySettings(deflate) Lorsque vous créez des entrées, vous pouvez mélanger les paramètres par entrée si nécessaire.

Ajoutez les entrées des courants en toute sécurité

  • Utiliser File.OpenRead(path) Pour diffuser de grands fichiers sans les charger complètement dans la mémoire.
  • Pour le contenu généré, écrivez à un MemoryStream ou a PipeWriter- soutenir le courant et le transférer à CreateEntry.
  • Il y a des flux après chaque CreateEntry Les ressources gratuites rapidement.

Exemple de contenu généré :

using System.IO;
using Aspose.Zip;
using Aspose.Zip.Saving;

static void AddLargeGeneratedEntry(Archive archive, string name)
{
    // simulate a big stream produced incrementally
    using var temp = new FileStream(Path.GetTempFileName(), FileMode.Create, FileAccess.ReadWrite, FileShare.None, 81920, FileOptions.DeleteOnClose);
    using var writer = new StreamWriter(temp);
    for (int i = 0; i < 200_000; i++) writer.WriteLine($"row-{i},value-{i}");
    writer.Flush();
    temp.Position = 0;

    var settings = new ArchiveEntrySettings(new DeflateCompressionSettings(CompressionLevel.Normal));
    archive.CreateEntry(name, temp, settings);
}

Validation et traitement d’erreurs

  • Vérifiez les entrées existantes avant d’ajouter à l’archive.
  • Création dans la try/catch et retourner une erreur HTTP claire pour les APIs Web.
  • Résultats de l’inscription avec des traces d’entrée (/Pour un comportement cohérent partout dans les outils.

Liste de contrôle des performances

  • Choose CompressionLevel.Low Pour les téléchargements en temps réel lorsque la vitesse compte plus que la taille.
  • Évitez de charger des entrées massives complètement dans la RAM; le courant des fichiers ou des courants réseau.
  • Pour les archives multi-GB très grandes, en streaming directement à HttpResponse.Body ou un autre flux cible au lieu de buffler.
  • Dispose Archive Toutes les entrées sont déterministes.

FAQ

** Puis-je protéger le mot de passe dans la mémoire ZIP ?**Aspose.ZIP soutient les archives ZIP cryptées. TraditionalEncryptionSettings ou AesEncryptionSettings via ArchiveEntrySettingsAppliquer par entrée lors de l’appel CreateEntry.

** Puis-je mettre à jour un ZIP existant que j’ai chargé dans la mémoire ?**Oui, il faut le charger dans un Archiveajouter ou supprimer les entrées, puis Save Retour à un courant.

** Cela fonctionne-t-il dans Azure App Service ou dans les conteneurs ?**Oui. In-mémory et streaming zipping fonctionne bien dans les environnements sandboxed où l’accès au disque est limité.

Résumé

Vous avez créé un fichier ZIP totalement en mémoire avec Aspose.ZIP pour .NET, ajouté les entrées des courants, ajusté la compression, et retourné l’archive d’un point de fin ASP.NET Core sans fichiers temporaires.

More in this category