How to handle Entity Framework lifetime in a long-running process?

277 Views Asked by At

I am making a data extraction tool (.NET Core console app) that will process tens of thousands of files and write extracted data to a database. There are only insertions to the DB, no reads or updates. I intend to run multiple instances, all writing to the same table.

I am using Autofac for DI, and injecting the EF DB Context into a class that loops through the files and writes to the DB.

I want to keep the DB Context lifetime short, but am not sure how to do that with DI. Is there some kind of "refresh" operation to effectively renew the DBContext? Or should I inject a DBContextFactory and get a new DBContext for each file processed? (And if so, what does the factory look like? Does it explicitly construct a new DBContext?)

1

There are 1 best solutions below

0
On BEST ANSWER

If you're holding on to the injected instance of DbContext and using it in a loop, then clearly the lifetime of DbContext cannot be short.

As you suggest, use a Context Builder in the DI. Here's an example that creates a context of type T using SQLServer:

public class DbContextBuilder<T> where T : DbContext
{
    public readonly T Context;
    public DbContextBuilder(string connectionStringName)
    {
        IConfigurationBuilder cfgBuilder = new ConfigurationBuilder();
        cfgBuilder.AddJsonFile("appsettings.json");
        IConfiguration cfg = cfgBuilder.Build();

        DbContextOptionsBuilder<T> optsBuilders = new DbContextOptionsBuilder<T>();
        optsBuilders.UseSqlServer(cfg.GetConnectionString(connectionStringName));
        Context = (T)Activator.CreateInstance(typeof(T), optsBuilders.Options);
    }
}

and in each loop:

foreach (var file in files)
{
    using (DbContext ctx = new DbContextBuilder<DbContext>("{name of conn string in appsettings}").Context)
    {
        // Do you writes for the current file
    }
}