Шаблон репозитория.NET Общая методология запроса

Я использую шаблон репозитория, у меня есть базовый репозиторий, и я использую Entity Framework и веб-API; мой вопрос - я хочу, чтобы мои клиенты могли запрашивать любые данные динамически; что-то вроде выражений запросов и выборки xml, используемых в Dynamics CRM; Я попробовал шаблон спецификации, но этого недостаточно, поскольку я хочу разрешить клиентскому коду упорядочивать данные с разными столбцами, например, Name asc Address desc, а также разрешить разбиение на страницы для возвращаемого результата, поэтому мои требования к методу

  1. Общий фильтр, который не зависит от технологии ORM, так как я могу изменить Entity Framework в будущем
  2. Методология общей сортировки; разрешить множественную сортировку столбцов, например, имя asc адрес desc
  3. Клиент определяет возвращаемые столбцы или все столбцы, например columnSet, как "Адрес, Имя и Идентификатор" или возвращает всю запись
  4. Разрешить разбиение на страницы, например, индекс страницы и размер страницы
  5. Порог поддержки на количество возвращаемых записей, так как большой результат может повлиять на производительность

это мой первоначальный метод, но я не знаю, лучше это или нет

IList<TEntity> AllMatching(ISpecification<TEntity> specification = null,
                Func<IQueryable<TEntity>, IOrderedQueryable<TEntity>> orderBy = null,
                IList<Expression<Func<TEntity, object>>> includes = null,
                int? pageIndex = null, int? pageCount = null);

1 ответ

Решение

Вы можете начать делать это:

 public IQueryable<TEntity> Select(
 Expression<Func<TEntity, bool>> filter = null,
 Func<IQueryable<TEntity>, IOrderedQueryable<TEntity>> orderBy = null,
 IList<Expression<Func<TEntity, object>>> includes = null,
 int? page = null,
 int? pageSize = null)
 {
        IQueryable<TEntity> query = _dbSet;

        if (includes != null)
        {
            query = includes.Aggregate(query, (current, include) => current.Include(include));
        }
        if (orderBy != null)
        {
            query = orderBy(query);
        }
        if (filter != null)
        {
            query = query.AsExpandable().Where(filter);
        }
        if (page != null && pageSize != null)
        {
            query = query.Skip((page.Value - 1)*pageSize.Value).Take(pageSize.Value);
        }
        return query;
 }

Как видите, он почти делает все, что вам нужно, поэтому, если вы хотите сделать то же самое в своем Repository реализации, вы должны использовать пакет nuget LinqKit.

Если вы хотите выбрать определенные столбцы, вы можете создать другой метод, как показано ниже:

IEnumerable<TResult> AllMatching<TResult>(
Expression<Func<TEntity, TResult>> columns,
Expression<Func<TEntity, bool>> filter = null,
Func<IQueryable<TEntity>, IOrderedQueryable<TEntity>> orderBy = null,
IList<Expression<Func<TEntity, object>>> includes = null,
int? pageIndex = null,
int? pageCount = null)
{
  var query=Select(filter,orderby,includes,page,pageSize);
  return  query.Select(columns);

}
Другие вопросы по тегам