【问题标题】:MVC 3 - The ObjectContext instance has been disposed and can no longer be used for operations that require a connectionMVC 3 - ObjectContext 实例已被释放,不能再用于需要连接的操作
【发布时间】:2011-09-18 06:57:26
【问题描述】:

总的来说,我对 C# 和 MVC 非常陌生,我一直在创建自己的小博客站点作为测试项目。尽管到目前为止大多数事情都在工作,但我在从 LINQ 查询中选择多个列时遇到了问题。只有在偶然发现关于 SO 的问题后,我才意识到我可以使用生成的实体类作为强类型模型来处理这个问题。我需要这个,因为我一直在创建一个数据库层(这也是我以前没有使用过的东西)并且试图通过该层传递匿名类型不起作用。我理解为什么会这样,所以我很满意我正朝着正确的方向前进。

但是,这种方法似乎给我带来了另一个问题。我尝试了一个简单的测试来从我的类别表中检索 2 列:CategoryID 和 Name。我最初尝试了以下方法:

using (MyEntities db = new MyEntities())
{
    var model = from c in db.Categories
                select new Category { CategoryID = c.CategoryID, Name = c.Name };

    return View(model);
}

当我尝试迭代视图中的模型时,这给了我 ObjectContext is disposed 错误。在阅读this question 之后,我尝试将 return 语句移到 using 块之外并在模型上调用 AsEnumerable(),如下所示:

IEnumerable<Category> model;

using (MyEntities db = new MyEntities())
{
    model = from c in db.Categories
            select new Category { CategoryID = c.CategoryID, Name = c.Name };
}

return View(model.AsEnumerable());

但是,当我尝试迭代视图中的模型时,这仍然给我同样的 ObjectContext is disposed 错误。所以现在我不明白为什么我会收到错误。我什至尝试完全删除 using 指令,但这给了我一个不同的错误:

“无法在 LINQ to Entities 查询中构造实体或复杂类型 'MyProjectModel.Category'。”

如果有帮助,以下是我认为的相关代码:

@model IEnumerable<MyProject.Models.Category>

@foreach (var category in Model)
{
    <p>@category.Name</p>
}

有人能告诉我我缺少什么吗?

谢谢。

【问题讨论】:

    标签: c# asp.net-mvc-3 dispose objectcontext


    【解决方案1】:

    在控制器中渴望并在处理之前调用.ToList(),以便在您离开using块之前立即安排查询的执行(因为之后为时已晚,上下文消失了):

    using (MyEntities db = new MyEntities())
    {
        var model = 
            from c in db.Categories
            select new Category 
            { 
                CategoryID = c.CategoryID, 
                Name = c.Name 
            };
        return View(model.ToList()); // <-- .ToList() here
    }
    

    现在,虽然这将解决您的特定问题,但开发人员或依赖注入框架通常会在 BeginRequest 事件中实例化 DbContext,将其存储在 HttpContext.Items 中,以便在整个执行过程中可用整个请求和EndRequest 方法内,从HttpContext 检索并处置它。


    更新:

    此外,使用仅包含您希望在此特定视图中使用的属性的视图模型也是一个好习惯:

    public class CategoryViewModel
    {
        public int Id { get; set; }
        public string Name { get; set; }
    }
    

    然后在你的行动中:

    public ActionResult Index()
    {
        using (MyEntities db = new MyEntities())
        {
            var model = 
                from c in db.Categories
                select new CategoryViewModel
                { 
                    Id = c.CategoryID, 
                    Name = c.Name 
                };
            return View(model.ToList());
        }
    }
    

    在视图中:

    @model IEnumerable<MyProject.Models.CategoryViewModel>
    
    @foreach (var category in Model)
    {
        <p>
            Id: @category.Id 
            Name: @category.Name
        </p>
    }
    

    【讨论】:

    • .ToList() (略)快
    • 嗨 Darin,感谢您的回复,但这给了我无法在 LINQ to Entities 查询中构造复杂类型,错误。我不知道这是否有所不同,但 Category 类是作为我的实体模型的一部分为我自动生成的。
    • @johnh,我真的不熟悉 LINQ to Entities,但无论如何,请在 return View(db.Categories.ToList()); 块内直接尝试这样的 return View(db.Categories.ToList());
    • @SLaks,是的,没错。感谢您指出了这一点。答案已更新。
    • @johnh,请查看我的更新答案以及详细示例。
    猜你喜欢
    • 2012-07-17
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多