EF Core - A second operation started on this context before a previous operation completed. Any instance members are not guaranteed to be thread safe

asp.net-core c# ef-core-2.1 entity-framework-core

Question

I am using EF Core 2.1 and I am trying to update multiple entities in one go by using Tasks (TPL):

public async Task UpdateAttendance(IEnumerable<MyEvents> events)
{
    try
    {
        var tasks = events.Select(async entity =>
        {
            await Task.Run(() => Context.Entry(entity).Property(x => x.Attendance).IsModified = true);
            await Context.SaveChangesAsync();
        });

        await Task.WhenAll(tasks);
    }
    catch (Exception ex)
    {
        throw new Exception(ex.Message ?? ex.InnerException.Message);
    }
}

But this throwing the below error.

A second operation started on this context before a previous operation completed. Any instance members are not guaranteed to be thread safe.

Startup.cs

services.AddScoped<IMyRepository, MyRepository>();

How do I address this?

1
1
2/23/2019 4:55:36 PM

Popular Answer

You can't do that. EF Core (as was EF 6 before) is not thread-safe.

You have to await a task before starting the next one

var tasks = events.Select(async entity =>
{
    await Task.Run(() => Context.Entry(entity).Property(x => x.Attendance).IsModified = true);
    await Context.SaveChangesAsync();
});

await Task.WhenAll(tasks);

Here you are starting multiple tasks in parallel and awaiting them. You will have to loop over it

foreach(var entity in events) 
{
    Context.Entry(entity).Property(x => x.Attendance).IsModified = true;
});
await Context.SaveChangesAsync();

It am not really sure why you want to save it event-by-event (hence, the example changed to do all the modified flags before calling SaveChangesAsync()), as its pretty inefficient. It makes more sense to update all of the properties, then run SaveChanges in the end, since EF Core will save all changed/tracked entities when you Save the Changes. Also easier to do a roll back when something goes wrong (Operation within SaveChangesAsync happens within a transaction scope)

2
2/23/2019 4:57:28 PM


Related Questions





Related

Licensed under: CC-BY-SA with attribution
Not affiliated with Stack Overflow
Licensed under: CC-BY-SA with attribution
Not affiliated with Stack Overflow