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

InsertManyAsync插入性能问题:9万条数据耗时约50分钟

批量插入9万条实体数据的性能优化方案

关键优化建议

  • 关闭变更追踪:你当前调用InsertManyAsync时第二个参数传了true,这会让EF Core为每个实体维护状态追踪,批量导入场景完全不需要这个功能,改成false能大幅减少内存占用和处理时间。
  • 调整批次大小:除了100/500/1000,试试2000-5000的批次(注意数据库的语句长度或数据包限制,比如SQL Server的max_allowed_packet),过大批次可能触发报错,需要根据数据库类型微调。
  • 统一事务管理:把所有批次包在一个大事务里提交,避免每个批次单独开启提交事务的开销——但要注意大事务会增加数据库日志压力,需结合数据库配置调整。
  • 改用原生数据库批量工具:如果ORM批量性能还是不达标,直接用数据库原生批量导入功能:
    • SQL Server:用SqlBulkCopy
    • MySQL:用MySqlBulkCopy或LOAD DATA INFILE
    • PostgreSQL:用COPY命令
      原生工具的性能比ORM批量插入高一个数量级,9万条数据通常能在几分钟内完成。
  • 临时禁用约束与索引:插入前关闭非必要的外键约束、非聚集索引和触发器,插入完成后再重新启用——这些校验逻辑会在每批次插入时额外消耗资源。
  • 简化实体映射:确保批量插入的实体没有加载不必要的导航属性,EF Core处理复杂关联会增加额外开销。

调整后的示例代码(关闭追踪+大事务)

int batchSize = 2000;
int totalCount = nichoInvoices.Count();
int i = 1;

var batches = nichoInvoices.Batch(batchSize);

using var transaction = await _invManager.InvoiceRepository.Database.BeginTransactionAsync();
try
{
    foreach (var batch in batches)
    {
        Logger.LogInformation($"Seeding Invoices {Math.Min(i * batchSize, totalCount)}/{totalCount}");
        await _invManager.InvoiceRepository.InsertManyAsync(batch, false);
        i++;
    }
    await transaction.CommitAsync();
    Logger.LogInformation($"End Seeding Invoices");
}
catch (Exception ex)
{
    await transaction.RollbackAsync();
    Logger.LogError(ex, $"Seeding Invoices failed");
    throw;
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.23 18:32:48