The ObjectContext instance has been deleted and can no longer be used
I've seen this question asked a million times, but every suggestion I've come across seems to be covered already.
I have an entity structure in my MVC solution and I have a "repository" that is trying to get a collection of MyObject
s:
public static List<MyObject> GetMyObjects()
{
using (var context = new MyEntities())
{
return context.MyObjects.Include("Contact").OrderByDescending(o => o.Date).ToList();
}
}
I am calling this method as part of a controller action that tries to serialize it:
public JsonResult All()
{
return Json(MyRepository.GetMyObjects(), JsonRequestBehavior.AllowGet);
}
And I am getting the following error:
The ObjectContext instance has been deleted and can no longer be used for operations that require a connection.
I don't know where to enable this option, I appreciate the relational arrays of "lazy-load" entities if and when needed, and I appreciate that trying to serialize the entire collection will actually try to load these (outside of the using statement), but I have "Include".
What i tried
I tried 'include', I also didn't guarantee that no other associations are part of the class MyObject
(i.e. I don't need to write others Include()
).
source to share
To avoid this, you have several options. Do not declare your navigation properties as virtual
or disable the Lazy Loading behavior in your context. Spoof loading is enabled by default and is achieved by instantiating derived proxy types and then overriding properties virtual
to add a boot hook. So, if you want to work with a serializer, I recommend disabling lazy loading:
public class YourContext : DbContext
{
public YourContext()
{
this.Configuration.LazyLoadingEnabled = false;
}
}
These links will help you better understand what I am explaining in my answer:
If you remove the keyword virtual
from the navigation properties, the POCO object does not meet the requirements described in the second link, so EF will not create a proxy class to lazily load your navigation properties. But if you turned off lazy loading, even if your navigation properties are virtual
, they won't be loaded into any object. It is a good idea to disable lazy loading when using a serializer. Most serializers work by accessing every property in an instance of a type.
As a third option, you can use the JsonIgnore attribute on the navigation properties, which you don't want to serialize as part of your entity, but as I said, the best option is to disable lazy loading.
source to share
When you use Include and use Lazy loading and terminate the dbContext in a Using statement, then as soon as it tries to get associated objects, the dbContext is already removed. You can try loading loading navigation property like this:
IQueryable<MyObjects> query = db.MyObjects.Include(m => m.Contact);
Or you can take the Using statement as it limits your lazy loading ...
source to share
I had the same problem and solved as below:
I created a new object and put in the values that I will use after getting the object from db.
Sample code:
var listFromDb= db.XTable.Where(x => x.Id > 5).ToList();
var list = new List<Package>();
foreach (var item in listFromDb)
{
var a = new Package()
{
AccountNo = item.AccountNo,
CreateDate = item.CreateDate,
IsResultCreated = item.IsResultCreated,
};
list.Add(a);
}
source to share