系列导航及源代码

需求

关于查询的另一个需求是要根据前端请求的排序字段进行对结果相应的排序。

目标

实现根据排序要求返回排序后的结果

原理与思路

要实现根据前端请求的进行相应排序,结合我们之前写好的Specification,可以比较简单地做到。

实现

我们还是用TodoItem请求来举例,再添加一个排序字段到查询请求中:

  • GetTodoItemsWithConditionQuery.cs
using AutoMapper;
using AutoMapper.QueryableExtensions;
using MediatR;
using TodoList.Application.Common.Interfaces;
using TodoList.Application.Common.Mappings;
using TodoList.Application.Common.Models;
using TodoList.Application.TodoItems.Specs;
using TodoList.Domain.Entities;
using TodoList.Domain.Enums; namespace TodoList.Application.TodoItems.Queries.GetTodoItems; public class GetTodoItemsWithConditionQuery : IRequest<PaginatedList<TodoItemDto>>
{
public Guid ListId { get; set; }
public bool? Done { get; set; }
public string? Title { get; set; }
public PriorityLevel? PriorityLevel { get; set; }
public string? SortOrder { get; set; } = "title_asc";
public int PageNumber { get; set; } = 1;
public int PageSize { get; set; } = 10;
} public class GetTodoItemsWithConditionQueryHandler : IRequestHandler<GetTodoItemsWithConditionQuery, PaginatedList<TodoItemDto>>
{
private readonly IRepository<TodoItem> _repository;
private readonly IMapper _mapper; public GetTodoItemsWithConditionQueryHandler(IRepository<TodoItem> repository, IMapper mapper)
{
_repository = repository;
_mapper = mapper;
} public async Task<PaginatedList<TodoItemDto>> Handle(GetTodoItemsWithConditionQuery request, CancellationToken cancellationToken)
{
var spec = new TodoItemSpec(request);
return await _repository
.GetAsQueryable(spec)
.ProjectTo<TodoItemDto>(_mapper.ConfigurationProvider)
.PaginatedListAsync(request.PageNumber, request.PageSize);
}
}

同时把原本写在查询中的条件整合到了TodoItemSpec中:

  • TodoItemSpec.cs
// 省略其他...
public TodoItemSpec(GetTodoItemsWithConditionQuery query) :
base(x => x.ListId == query.ListId
&& (!query.Done.HasValue || x.Done == query.Done)
&& (!query.PriorityLevel.HasValue || x.Priority == query.PriorityLevel)
&& (string.IsNullOrEmpty(query.Title) || x.Title!.Trim().ToLower().Contains(query.Title!.ToLower())))
{
if (string.IsNullOrEmpty(query.SortOrder))
return;
switch (query.SortOrder)
{
// 仅作有限的演示
default:
ApplyOrderBy(x => x.Title!);
break;
case "title_desc":
ApplyOrderByDescending(x =>x .Title!);
break;
case "priority_asc":
ApplyOrderBy(x => x.Priority);
break;
case "priority_desc":
ApplyOrderByDescending(x => x.Priority);
break;
}
}

验证

启动Api项目,执行查询TodoItem的请求:

  • 请求

  • 响应

总结

这样我们就完成了根据前端需求进行后端排序并返回结果的需求,下一篇文章我们将介绍查询中的最后一个不是很常用,但是在某些情况下很有用的概念:数据塑形。

最新文章

  1. DbMigration使用方法
  2. SQL性能学习汇总 00
  3. My97DatePickerBeta 日历插件
  4. 消息队列-rabbitMQ
  5. Angular系列----AngularJS入门教程02:静态模板(转载)
  6. HTML: margin重疊現象的說明
  7. 动态调用DLL函数有时正常,有时报Access violation的异常
  8. Codeforces 486D D. Valid Sets
  9. webuploader 实现图片批量上传
  10. 【49】java内部类剖析
  11. Thread之九:stop
  12. 【原创】大叔问题定位分享(10)提交spark任务偶尔报错 org.apache.spark.SparkException: A master URL must be set in your configuration
  13. [Android] Android 使用 Greendao 操作 db sqlite(1)-- 直接在MainActivity中调用
  14. C#基础:委托之Action&lt;T&gt;和Func&lt;T&gt;的用法
  15. Spring BPP中优雅的创建动态代理Bean
  16. Spring钩子方法和钩子接口的使用详解
  17. 伪分布式hadoop启动后jps查不到namenode的解决办法
  18. linux 搭建rap记录
  19. ABP的配置 请求类型
  20. vmware中的 CentOS7 虚机磁盘动态扩容

热门文章

  1. Linux学习 - 变量测试与内容替换
  2. Linux学习 - 文件特殊权限
  3. spring 事务处理中,同一个类中:A方法(无事务)调B方法(有事务),事务不生效问题
  4. 【Spring Framework】Spring IOC详解及Bean生命周期详细过程
  5. Linux上Zookeeper集群搭建
  6. 记一次单机Nginx调优,效果立竿见影
  7. Go modules基础精进,六大核心概念全解析(上)
  8. Redis增加测试数据
  9. IT服务生命周期
  10. Android App加固原理与技术历程