You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何优化IAsyncEnumerable序列化后上传Azure Blob Storage的内存占用?

实现IAsyncEnumerable流式序列化并上传Azure Blob Storage

完全可以实现边序列化边上传的流式处理,大幅降低内存峰值。核心思路是把JSON序列化的输出直接导向Azure Blob的写入流,不需要经过内存缓存。

关键实现步骤

  1. 获取Blob写入流:通过Azure Blob SDK的BlobClient.OpenWriteAsync方法获取可异步写入的流,这个流直接连接到Blob存储,写入操作会实时上传数据。
  2. 异步序列化IAsyncEnumerable:使用System.Text.Json.JsonSerializer.SerializeAsync方法,它原生支持将IAsyncEnumerable序列化为流,会逐个处理元素,不会一次性加载所有记录到内存。
  3. 可选的异步转换:如果需要对记录做异步转换,借助System.Linq.Async包的扩展方法处理异步序列。

代码示例

using Azure.Storage.Blobs;
using System.Text.Json;
using System.Linq; // 同步转换用
// 异步转换需安装NuGet包System.Linq.Async,然后引用:using System.Linq.Async;

// 初始化Blob客户端
var blobClient = new BlobClient("<你的连接字符串>", "<容器名>", "<Blob文件名>");

// 打开Blob的可写流,设置覆盖已有文件
await using var blobWriteStream = await blobClient.OpenWriteAsync(overwrite: true);

// 从远程获取IAsyncEnumerable格式的记录
var remoteRecords = FetchRemoteRecordsAsync();

// 转换记录(同步转换示例)
var transformedRecords = remoteRecords.Select(record => new 
{
    Id = record.Id,
    ProcessedData = record.RawData.ToUpper()
});

// 异步转换示例(需System.Linq.Async)
// var transformedRecords = remoteRecords.Select(async record => new 
// {
//     Id = record.Id,
//     ProcessedData = await ProcessRawDataAsync(record.RawData)
// });

// 流式序列化到Blob流,完成边序列化边上传
await JsonSerializer.SerializeAsync(blobWriteStream, transformedRecords, new JsonSerializerOptions
{
    WriteIndented = false, // 关闭缩进减少文件体积,按需调整
    DefaultIgnoreCondition = System.Text.Json.Serialization.JsonIgnoreCondition.WhenWritingNull
});

// 确保所有数据都被写入并上传
await blobWriteStream.FlushAsync();

注意事项

  • 若使用异步转换,必须安装System.Linq.Async NuGet包,它提供了针对IAsyncEnumerable的LINQ扩展方法。
  • 序列化过程中,内存仅保留当前处理的单条记录和JSON序列化的缓冲区,内存峰值会维持在很低的水平。
  • 可以通过JsonSerializerOptions调整序列化行为,比如忽略空值、设置日期格式等,优化输出结果。

内容的提问来源于stack exchange,提问作者ctyar

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.24 13:42:43