In this lesson, you will learn how to bypass the standard change-tracking overhead of EF Core to achieve high-speed data ingestion.
When you add thousands of entities using standard DbContext.AddRange(), EF Core performs a heavy "change tracking" dance. It instantiates an EntityEntry for every single object, snapshots its current values, and performs relationship checks. This is excellent for small business logic updates, but it becomes a massive performance bottleneck when you need to ingest 10,000+ rows.
The Problem with Default Tracking
Every time you call SaveChanges(), EF Core generates individual INSERT statements or small batches. If you are inserting 50,000 logs, the round-trip time between your application and the database will make the operation feel frozen. To solve this, we move away from the ChangeTracker.
Bulk Extensions
To handle bulk inserts efficiently, we leverage third-party libraries like EFCore.BulkExtensions. These libraries bypass the DbContext change tracker and interact directly with the database driver’s high-performance features, such as SQL Server’s SqlBulkCopy.
Here is how a typical bulk operation looks:
// Instead of context.Add(entity) and context.SaveChanges()
var largeList = new List<Product> { /* 50,000 items */ };
// This bypasses the overhead of the ChangeTracker
context.BulkInsert(largeList);
Why this is faster
- Bypasses Change Tracking: No
EntityEntryobjects are created, saving significant CPU and memory. - Reduced Round-trips: It packages the data into a single stream or batch execution, minimizing network latency.
- Database Native Features: It utilizes low-level APIs (like
SqlBulkCopyfor SQL Server) that are specifically optimized to stream rows into tables without the overhead of row-by-row transaction logging.
When choosing a strategy, consider if you need business logic validation. If your entities require complex validation or state management, you might need to process them in smaller batches of 1,000–5,000 using SaveChanges() rather than a raw bulk insert. If you simply need the data into the table as fast as possible, bulk extensions are the industry standard.
Key Takeaway: To maximize ingestion speed, avoid the overhead of the EF Core ChangeTracker and use specialized bulk-insertion libraries to stream data directly into the database.