ASP.NET MVC – Proper Disposal of Database Context in Lazy Collections

asp.net-mvcentity-framework

I'm looking for a best practices kind of answer here.

Given that best practices for interacting with classes that implement IDisposable is via the Using statement – What is the best practice for using EF lazy loading with MVC?

Example controller method:

<HttpGet>
Public Function Schedule(ByVal id As Int64) As ActionResult

    Dim model As Schedule = Nothing
    Using database As dataContext = New dataContext
        model = (From s In database.Schedules Where s.ScheduleID = id Select s).FirstOrDefault
    End Using

    Return View(theSchedule)

End Function

This example makes lazy loading not work because the database [dataContext] is disposed by time the model arrives in the View.

So I guess the question is:
What are best practices for using lazy loading in MVC? How do you guarantee that your database context is disposed of properly and that you don't cause memory leaks?

Best Answer

In general, you don't need to use Using statements with Entity Framework data contexts. Lazy collections is one of the reasons why. So your code would simply be:

<HttpGet>
Public Function Schedule(ByVal id As Int64) As ActionResult

    Dim model As Schedule = Nothing
    Dim database As dataContext = New dataContext
    model = (From s In database.Schedules Where s.ScheduleID = id Select s).FirstOrDefault

    Return View(model)

End Function

Data contexts in Entity Framework are designed to open and close connections as needed, and they dispose of themselves automatically when the data context object is no longer required.

The default behavior of DbContext is that the underlying connection is automatically opened any time is needed and closed when it is no longer needed. E.g. when you execute a query and iterate over query results using “foreach”, the call to IEnumerable.GetEnumerator() will cause the connection to be opened, and when later there are no more results available, “foreach” will take care of calling Dispose on the enumerator, which will close the connection.

The only time you would have to be careful about IDisposable is if you Override the data context's default behaviors.

Further Reading

Do I always have to call Dispose on DBContext? Nope.
Managing DbContext the right way with Entity Framework 6: an in-depth guide

Related Topic