Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to refresh an Entity Framework Core DBContext?

When my table is updated by another party, the db context in dotnet core still return the old value, how can I force the Db context to refresh?

I've done research but I only found people use Reload method, which is not available in EF core, to force the context to refresh.

Some other solution suggests dispose the context after using, but I get error saying the DB context is created by dependency injection and I should not mess up with it.

like image 383
MiDaa Avatar asked Sep 13 '17 19:09

MiDaa


People also ask

How do I refresh EF context?

The best way to refresh entities in your context is to dispose your context and create a new one.

How do I update my EF core model after database change?

Right-click anywhere on the design surface, and select Update Model from Database... In the Update Wizard, select the Refresh tab and select your table then click Finish button.

How does DbContext change state of entity?

This can be achieved in several ways: setting the EntityState for the entity explicitly; using the DbContext. Update method (which is new in EF Core); using the DbContext. Attach method and then "walking the object graph" to set the state of individual properties within the graph explicitly.


1 Answers

Oh, this issue had me in knots for days.

I'm using Visual Studio 2017 with .Net Core 2.1, and my EF Core code looked something like this:

//  1.  Load a [User] record from our database  int chosenUserID = 12345; User usr = dbContext.Users.FirstOrDefault(s => s.UserID == chosenUserID);  //  2. Call a web service, which updates that [User] record HttpClient client = new HttpClient() await client.PostAsync("http://someUrl", someContent);  //  3. Attempt to load an updated copy of the [User] record User updatedUser = dbContext.Users.FirstOrDefault(s => s.UserID == chosenUserID); 

At step 3, it would simply set "updatedUser" to the original version of the [User] record, rather than attempting to load in a fresh copy. So, if, after step 3, I modified that [User] record, I'd actually lose whatever settings the web service had applied to it.

I - eventually - found two solutions.

I could change the ChangeTracker settings. This worked, but I was concerned about the side-effects of doing this:

dbContext.ChangeTracker.QueryTrackingBehavior = Microsoft.EntityFrameworkCore.QueryTrackingBehavior.NoTracking; 

Or, I could slip in the following command, before attempting to reload the [User] record...

await dbContext.Entry(usr).ReloadAsync(); 

This seems to force .Net Core to reload that [User] record, and life is good again.

I hope this is useful...

Tracking down, and fixing this bug took me days....

There's also an excellent article describing the various ways to get around this caching issue here.

like image 170
Mike Gledhill Avatar answered Sep 29 '22 03:09

Mike Gledhill