【问题标题】:How should I expose the total record count and IEnumable collection of paged records from my service layer method?我应该如何从我的服务层方法中公开总记录数和分页记录的 IEnumable 集合?
【发布时间】:2011-09-19 01:27:06
【问题描述】:

我首先使用带有代码的 EF4,并且有一个用于持久性的存储库和一个与之交互的服务层。我有一个服务层方法,它在我的存储库上调用一个 IQueryable 方法并返回一个包含实体的 IEnumerable。我还需要返回总记录数,以便计算分页链接。

我应该如何从我的服务方法中返回 int 和 IEnumerable?

  • 在方法上使用 out 参数计算总行数
  • 创建一个包含总行数作为属性的单独类
  • 将分页 LINQ 查询移出服务层(从服务层的存储库中公开 IQueryable)
  • 在服务层上创建一个完全独立的方法,该方法只针对计数执行新查询。

所有这些都应该有效,但哪一个最干净?

更新:以下是对架构的一些说明。如果这是错误的,那么请告诉我更好的方法(例如 - 在表示层而不是服务层进行分页等)

回购层:

返回 DbSet 的 IQueryable,从表现层抽象出对 db 的访问

服务层:

对 IQueryable 执行 LINQ 查询以过滤并根据需要使用 skip 和 take 获取页面项目并返回 IEnumerable(在返回时还将设置为 List 以避免任何 DbContext 生命周期问题)

表示层:

调用Service层上的方法(getPagedResults(filters, pageNumber, pageSize))

从外观上看,我还需要添加一个单独的方法来获得总结果。希望在一个电话中完成这一切。

我不希望将所有记录都带回演示文稿,然后页面...似乎效率低下。

【问题讨论】:

  • 如果您已经返回IEnumerable<T>,是否有某些特定原因您不只是在IEnumerable 上使用.Count()?您只是将子集呈现给前端吗?前端不应该负责分页吗?
  • 你返回的IEnumerable,它包含所有的项目吗? (与 count 将返回的项目数量相同)
  • @AllenG - 我在服务层本身进行分页,然后将列表返回给 UI/Codebehind 消费者。这样我就可以避免我的 Dbcontext 生命周期出现任何问题。此外,我不必将所有记录发送到前端,然后进行分页.. 将直接在服务层查询中获取我需要的记录。
  • @Magnus - 我试图避免发送所有项目......只需通过对从 repo 返回的 IQueryable 进行查询来获取我需要的项目。
  • 更新问题以添加更多信息。

标签: c# asp.net entity-framework pagination repository


【解决方案1】:

你可以这样做

public class Repository<TEntity>
{
   public IEnumerable<TEntity> GetCollection(Expression<Func<TEntity, bool>> filter, 
      int pageSize, int pageIndex)
   {
      return YourDbSet.Where(filter).OrderBy(sortExpression).Skip(pageSize * pageIndex).Take(pageSize);
   }

   public int Count(Expression<Func<TEntity, bool>> filter)
   {
      return YourDbSet.Where(filter).Count();
   }
}

然后你可以写一个扩展方法来使用这两种方法

public static Pagination<TEntity> GetPagination<TEntity>(this Repository<TEntity> repository, 
   Expression<Func<TEntity, bool>> filter, int pageSize, int pageIndex)
{
   var entities = repository.GetCollection(filter, pageSize, pageIndex);
   var count = repository.Count(filter);

   return new Pagination(entities, pageSize, pageIndex + 1, count);
}

这样您就可以独立地重用GetCollectionCount 方法。 您可以动态构建 where 条件。看看我的answer

【讨论】:

  • 我还在学习,所以尽量坚持具体的实现,直到我了解泛型为止。
  • @Developr 因为您使用的是 IQueryable,所以您已经在使用泛型。通用参数由编译器推断。所以你不必给他们
  • 这里是另一个问题的链接,展示了我的架构......非常简单而具体:stackoverflow.com/questions/6416506/…
【解决方案2】:

如果您返回的 Enumerable 包含所有项目,我会在从函数返回 if 之前对其执行 ToList()。 (然后你可以免费做Count) 如果函数返回总数的子集(使用Skiptake),我会添加一个单独的函数来获取总数。

【讨论】:

    猜你喜欢
    • 2022-01-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-04-01
    • 1970-01-01
    相关资源
    最近更新 更多