Hello,
we are currently evaluating the usability of Entity Framework Core Code First in a Blazor Server application.
We try to migrate from a Database First approach where we created a DbContext instance (by a IDbContextFactory) per database operation.
Example:
public class ReleaseService
{
...
public Release LoadRelease(int userId, int releaseId)
{
using (var context = _contextFactory.CreateDbContext())
{
return context.Database.SqlQuery<Release>(
@$"rel.SelRelease
@person_id={userId},
@release_id={releaseId}
")
.AsEnumerable()
.FirstOrDefault();
}
}
}
Our Blazor Server application currently uses cascading parameters where the MainLayout.razor cascades down certain class objects to child pages / components.
The most central entity is a User (entity). Therefore, we load it once in MainLayout.OnInitialized and cascade (pass) it down to child components.
Now, let’s consider following succession in our application:
- load
User entity in MainLayout.OnInitialized
- navigate to any application page
- in an edit page load another entity, let’s say a
Request entity
- edit some properties of the
Request entity and save it; also set Request.UpdatedByUser during save
Question
Which approach would be better?
a) long-living DbContext (lifetime: Scoped)
We create the DbContext in MainLayout.OnInitialized, do NOT close it here but cascade (pass) it down to every child component.
Once the user navigates to the edit page, we reuse the DbContext, manipulate Request entity and save the changes to database.
Consequence: The DbContext instance will live for the whole browser session of the current user.
b) DbContext per operation
After loading the User entity in MainLayout.OnInitialized we directly close the DbContext.
Once the user navigates to the edit page, we create a new DbContext instance for our edit operation.
In this new DbContext instance we reload the User entity for having it in EF Core tracker.
We manipulate the Request entity by the edit page. On “Save” click we also set Request.UpdatedByUser and then save all changes to database.
Consequence: The secondly created DbContext instance will be closed only when the user navigates away from the edit page, more precisely: once the edit component with the “Save” functionality is destroyed.