合并和压缩 Azure Blob 存储中的多个大文件

Posted

技术标签:

【中文标题】合并和压缩 Azure Blob 存储中的多个大文件【英文标题】:Combine and Zip Multiple Large Files From Azure Blob Storage 【发布时间】:2022-01-18 22:23:55 【问题描述】:

我在 API 后面运行了一些代码,该 API 循环遍历 Azure Blob 存储上的文件列表,将它们压缩并将最终的 Zip 保存到同一个存储帐户。然后我提供一个指向 Zip 文件的链接供我的用户访问。

只要文件很小,此解决方案就可以正常工作。但是,有很多文件在 2-5 GB 范围内,一旦测试这些文件,我就会收到内存不足异常错误:

'数组尺寸超出支持范围。'

我已经看到 OneDrive 和 GoogleDrive 等系统非常快速地创建了这些文件,我渴望为我的用户创造这种体验。但是我也可以在存档准备好下载时通知用户,即使是几分钟后,因为我会收到他们的电子邮件。

以下是简化并在控制台应用程序中运行的代码版本:

using Microsoft.WindowsAzure.Storage;
using System.IO.Compression;


var account = CloudStorageAccount.Parse("ConnectionString");
var blobClient = account.CreateCloudBlobClient();
var container = blobClient.GetContainerReference("ContainerName");

var blob = container.GetBlockBlobReference("ZipArchive.zip");
using (var stream = await blob.OpenWriteAsync())
using (var zip = new ZipArchive(stream, ZipArchiveMode.Create))

    var files = new string[] 
        "files/psds/VeryLargePsd_1.psd",
        "files/psds/VeryLargePsd_2.psd",
        "files/psds/VeryLargePsd_3.psd",
        "files/zips/VeryLargeZip_1.zip",
        "files/zips/VeryLargeZip_2.zip"
    ;
   
    foreach (var file in files)
    
        var sourceBlob = container.GetBlockBlobReference(file);
        var index = file.LastIndexOf('/') + 1;
        var fileName = file.Substring(index, file.Length - index);
        var entry = zip.CreateEntry(fileName, CompressionLevel.Optimal);

        await sourceBlob.FetchAttributesAsync();
        byte[] imageBytes = new byte[sourceBlob.Properties.Length];
        await sourceBlob.DownloadToByteArrayAsync(imageBytes, 0);

        using (var zipStream = entry.Open())
            zipStream.Write(imageBytes, 0, imageBytes.Length);
    

【问题讨论】:

【参考方案1】:

正如您提到的,它适用于小文件和大文件时会引发错误。

解决方法

1) 上传小块的大文件,然后压缩。

更多详情请参考这个 SO 线程:Upload a zip file in small chunks to azure cloud blob storage

2) 本教程展示了您部署一个将大量随机数据上传到 Azure 存储帐户的应用程序:Upload large amounts of random data in parallel to Azure storage

3)上传大文件,你可以使用Microsoft Azure Storage Data Movement Library以获得更好的性能。 Microsoft Azure 存储数据移动库专为高性能上传、下载和复制 Azure 存储 Blob 和文件而设计

【讨论】:

感谢您的信息,但是我的方案需要一个包含非常大文件的庞大库。用户提交从目录中选择文件的请求以下载它们。因此,可以随时请求各种各样的压缩文件组合。 zip 是根据请求生成的,而不是上传过程的一部分。我想我可能需要让 VM 从事件中获取这些请求,将每个文件复制到它的本地硬盘驱动器,将它们压缩到 VM 上,然后将压缩文件推回 Azure。然后可以在准备好时将链接发送给请求者。如果这可行,我会更新。

以上是关于合并和压缩 Azure Blob 存储中的多个大文件的主要内容,如果未能解决你的问题,请参考以下文章

从未以任何格式压缩的 azure blob 存储下载文件夹

使用文件流压缩文件并上传到 Azure Blob 存储

Ionic Zip 密码设置在 azure blob 存储中,并为 zip 文件夹而不是文件设置最佳压缩

如何在不写入文件的情况下压缩流并将其上传到 Azure Blob 存储?

从 Azure blob 存储下载所有文件,对其进行压缩并以 JAVA 格式上传 zip 文件

将多个 Blob 上传到 Azure 存储