我是第一次使用实体框架,我想知道我是否在最佳实践中使用.

我在我的业务逻辑中创建了一个单独的类,它将处理实体上下文.我的问题是,在我看过的所有视频中,他们通常将上下文包装在Using语句中以确保其关闭,但显然我不能在我的业务逻辑中这样做,因为在我可以实际使用上下文之前,上下文将被关闭.

我现在做的可以吗?下面是几个示例:

    public IEnumerable<Article> GetLatestArticles(bool Authorised) 
    {
        var ctx = new ArticleNetEntities();
        return ctx.Articles.Where(x => x.IsApproved == Authorised).OrderBy(x => x.ArticleDate);
    }

    public IEnumerable<Article> GetArticlesByMember(int MemberId, bool Authorised)
    {
        var ctx = new ArticleNetEntities();
        return ctx.Articles.Where(x => x.MemberID == MemberId && x.IsApproved == Authorised).OrderBy(x => x.ArticleDate);
    }

我只想确定我正在建造的东西不会在很多人使用的时候就会死掉?

推荐答案

这实际上取决于如何公开存储库/数据存储.

不确定你所说的"上下文将被关闭,因此我不能做业务逻辑"是什么意思.使用using语句执行业务逻辑inside.或者,如果您的业务逻辑在另一个类中,那么让我们继续.:)

有些人从他们的存储库返回具体的集合,在这种情况下,您可以将上下文包装在using语句中:

public class ArticleRepository
{
   public List<Article> GetArticles()
   {
      List<Article> articles = null;

      using (var db = new ArticleNetEntities())
      {
         articles = db.Articles.Where(something).Take(some).ToList();
      }
   }
}

这样做的好处是满足良好的连接实践——尽可能晚地打开,尽可能早地关闭.

您可以将所有业务逻辑封装在using语句中.

缺点-您的存储库会意识到业务逻辑,这是我个人不喜欢的,并且您最终会 for each 特定场景使用不同的方法.

second option-new将上下文作为存储库的一部分,并使其实现IDisposable.

public class ArticleRepository : IDisposable
{
   ArticleNetEntities db;

   public ArticleRepository()
   {
      db = new ArticleNetEntities();
   }

   public List<Article> GetArticles()
   {
      List<Article> articles = null;
      db.Articles.Where(something).Take(some).ToList();
   }

   public void Dispose()
   {
      db.Dispose();
   }

}

然后:

using (var repository = new ArticleRepository())
{
   var articles = repository.GetArticles();
}

或者third-option(我最喜欢的),用dependency injection.将所有上下文工作与您的存储库分离,并让DI容器处理资源的处置:

public class ArticleRepository
{
   private IObjectContext _ctx;

   public ArticleRepository(IObjectContext ctx)
   {
      _ctx = ctx;
   }

   public IQueryable<Article> Find()
   {
      return _ctx.Articles;
   }
}

您 Select 的DI容器将向存储库的实例化中注入具体的ObjectContext,并配置一个生命周期(Singleton、HttpContext、ThreadLocal等),然后根据该配置对其进行处理.

我对它进行了设置,这样每个HTTP请求都会得到一个新的上下文.当请求完成时,我的DI容器将自动处理上下文.

我还在这里使用工作单元模式,允许多个存储库使用一个对象上下文.

您可能还注意到,我更喜欢从我的存储库返回IQueryable(而不是具体的列表).要强大得多(但如果你不理解其中的含义,那就有风险).我的服务层在IQueryable上执行业务逻辑,然后将具体集合返回给UI.

这是我迄今为止最强大的选项,因为它允许一个简单的存储库,工作单元管理上下文,服务层管理业务逻辑,DI容器处理资源/对象的生命周期/处置.

如果你想知道更多的信息,请告诉我--因为有相当多的信息,甚至比这个令人惊讶的冗长的答案还要多.:)

Asp.net相关问答推荐

Visual Studio发布的网站得到错误类型JObject is not defined when page is load on server"''"

从组件属性调用异步方法的正确方法

如何在 ASP.NET RadioButtonList 中的项目之间添加空格

如何正确配置 IHttpModule?

.Net Framework:w3wp.exe 中的异常

在 ASP.Net 中使用自定义 RoleProvider 时如何允许多个角色查看页面

某些黑客能否从用户那里窃取 Web 浏览器 cookie 并在网站上使用该名称登录?

ASP.NET 如何将控件呈现为 HTML?

ASP.NET MVC4 jquery/javascript 包的使用

使用 jQuery.ajax() 时如何处理错误?

使用 Lucene.NET 索引 .PDF、.XLS、.DOC、.PPT

Web Api 请求内容在操作过滤器中为空

如何将 Web 应用程序项目转换为类库项目

在生产中使用 LocalDb 是否正常?

IIS Express 安装目录在哪里?

使用 VirtualPathProvider 从 DLL 加载 ASP.NET MVC 视图

如何在 ASP.Net MVC 3 中返回 HttpNotFound() 的视图?

将对象传递给 HTML 属性

DateTime.Parse 和 Convert.ToDateTime 之间有什么区别?

ModelClientValidationRule 冲突