בניית ZIP בזיכרון הוא שימושי כאשר אתה צריך לזרום הורדה, להעביר ביטים לשירות אחר, או לאחסן ארכיון בבסיס נתונים בלי לגעת בדיסק. Aspose.ZIP עבור .NET מציג API נקי כדי ליצור קבצי Zip באמצעות זרמים, לבחור הגדרות הדחיסה, ולשמור את התוצאה על MemoryStream או ישירות לתגובה HTTP.
מדריך זה מספק את הקוד המלא, הנכון שניתן להדביק באפליקציה לקונסולה או בפרויקט ASP.NET Core.
דרישות
- .NET 6 או מאוחר יותר
- נוגט :
Aspose.Zip
dotnet add package Aspose.Zip
שמות ששימשו:
using Aspose.Zip; // Archive, ArchiveEntry
using Aspose.Zip.Saving; // DeflateCompressionSettings, CompressionLevel
התחלה מהירה: יצירת ZIP לחלוטין בזיכרון
דוגמה זו מוסיפה כניסות מתוך רצועה וקובץ על הדיסק, מאחסן את הארכיון ל MemoryStream, ומציגים את התוצאה של ביט אררי.
// 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");
}
}
- נקודות מפתח *
new Archive()יצירת ZIP ריק.CreateEntry(entryName, stream, entrySettings)להוסיף קובץ מ כל זרם קריא.archive.Save(stream)לכתוב את הארכיון לתוך הזרם הנבחר שלך (זיכרון, רשת, גוף התגובה).
הוסף עץ תיקיה שלם ללא כתיבת קבצי טמ
ללכת תיעוד חוזר, לשמור דרכים יחסיות, ולכתוב את הארכיון הסופי לזיכרון.
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: זרם הורדה ZIP ללא דיסק I/O
נקודת סיום זו בונה זיכרון ZIP ממקורות מרובים ומחזירה אותו עם סוג התוכן הנכון ושם הקובץ להורדה.
// 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();
“למה אני מגיע לכאן?”APIs מינימליים דורשים משכנתא ספציפית עבור ארכיונים גדולים מאוד, עדיף זרימה ישירה 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);
});
בחר את הגדרות הדחיסה
DeflateCompressionSettings בקרת מהירות נגד גודל:
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
עברו את ההגדרות דרך new ArchiveEntrySettings(deflate) אתה יכול לערבב את ההגדרות לפי כניסה אם יש צורך.
להוסיף כניסות מתוך זרמים בבטחה
- שימוש
File.OpenRead(path)כדי להעביר קבצים גדולים בלי להעלות אותם לחלוטין לתוך הזיכרון. - עבור תוכן שנוצר, לכתוב על
MemoryStreamאו אPipeWriter- תומך זרם והעביר אותו לCreateEntry. - יש זרמים לאחר כל
CreateEntryלחופש את המשאבים במהירות.
דוגמה לתוכן המיוצר:
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);
}
אימות וניהול שגיאות
- בדוק כניסות קיימות לפני הוספת ארכיון.
- יצירת הקב"ה בתוך
try/catchוהחזיר שגיאה ברורה HTTP עבור APIs האינטרנט. - רכיבה מקדימה (לדוגמה, יש להקפיד על קפיצה קפדנית)
/• התנהגות עקבית בין כלים.
מבחן ביצועים
- Choose
CompressionLevel.Lowעבור הורדות בזמן אמת כאשר מהירות חשובה יותר מאשר גודל. - הימנעות מהטעינה של כניסות מסיביות לחלוטין ל- RAM; זרם מהקבצים או זרימות ברשת.
- עבור קבצים רב-GB גדולים מאוד, זרם ישיר ל
HttpResponse.Bodyאו זרם מטרה אחר במקום בופר. - Dispose
Archiveכל ההכנסות זורמות באופן קבוע.
FAQ
**האם אני יכול להגן על הסיסמה בזיכרון?**Aspose.ZIP תומך בקבצים ZIP מוצפנים. TraditionalEncryptionSettings או AesEncryptionSettings דרך ArchiveEntrySettingsלהגיש בקשה לפי כניסה בעת התקשרות CreateEntry.
**האם אני יכול לעדכן את ה-ZIP הקיימים שהטעןתי בזיכרון?**כן, להעלות אותו לתוך Archiveלהוסיף או להסיר כתיבה, ולאחר מכן Save בחזרה אל זרם.
**האם זה עובד בשירות האפליקציה של Azure או במכולות?**כן. זיכרון וזרם Zipping עובד היטב בסביבות חול שבו גישה לדיסק מוגבלת.
סיכום
יצרת ארכיון ZIP ** לחלוטין בזיכרון** עם Aspose.ZIP עבור .NET, הוספת כניסות מהזרמים, הדחיסה מותאמת, והחזירה את הארגון מנקודת סיום ASP.NET Core ללא קבצים זמניים.