排序调整
本文档中引用的文件
- MyEntityNameController.cs
- MyEntityNameAppService.cs
- MyEntityName.cs
- IMyEntityNameAppService.cs
- MyEntityNameDto.cs
- CMSPluginEfCoreExtensions.MyEntityName.cs
目录
引言
本文档详细阐述了系统中 MyEntityName 实体排 序功能的实现机制。重点分析 Sort 字段在列表展示中的作用,解析 AdjustSortAsync 方法如何接收目标实体 ID 与目标排序值,重新计算相关实体的排序值,并确保排序的连续性与唯一性。同时讨论在高并发场景下可能引发的数据竞争问题及应对策略,并提供前端拖拽排序后的优化调用建议。
Section sources
实体排序字段的作用
MyEntityName 实体中的 Sort 字段(类型为 int)用于定义实体在列表中的显示顺序。该字段在数据库表中被映射为 sort 列,并作为默认排序依据,确保列表展示时具有稳定的顺序。
在查询接口 GetListAsync 中,若未指定排序规则,则默认按 Sort 字段升序排列,从而保证用户界面中列表项始终按照预设顺序展示。此字段的连续性和唯一性由业务逻辑维护,避免出现重复或空缺的排序值。
Diagram sources
Section sources
排序调整方法实现原理
AdjustSortAsync 方法是实现排序调整的核心逻辑,位于 MyEntityNameAppService 类中。其工作流程如下:
- 获取全部实体列表:首先从仓储中获取所有
MyEntityName实体,并按当前Sort值升序排列。 - 初始化连续排序:遍历列表,为每个实体分配从 1 开始的连续序号,确保排序值的连续性。
- 定位目标实体:根据传入的
id找到目标实体。 - 调整排序区间:
- 若目标排序为 1,则其他所有实体排序值整体加 1。
- 若原排序大于目标排序(向上移动),则位于目标位置及以上(不含自身)的实体排序 +1,其余 -1。
- 若原排序小于目标排序(向下移动),则位于目标位置以上(不含自身)的实体排序 +1,其余 -1。
- 设置目标排序值:将目标实体的
Sort设置为指定值。 - 批量更新数据库:调用
UpdateManyAsync一次性提交所有实体的排序变更。
此算法确保了排序的连续性(无空缺)和唯一性(无重复),并通过批量更新减少数据库交互次数。
Diagram sources
Section sources
并发环境下的数据竞争与应对策略
在高并发场景下,多个用户同时调整排序可能导致数据竞争问题。典型场景如下:
- 用户 A 和 B 同时加载相同列表
- 用户 A 将项目 1 移动到位置 3
- 用户 B 将项目 2 移动到位置 3
- 由于两者基于旧数据计算排序,最终结果可能出现重复排序值或顺序错乱
应对策略
1. 数据库行锁(推荐)
在 GetListAsync 查询时使用 FOR UPDATE 锁定相关记录,防止其他事务读取未提交数据。EF Core 可通过 ExecuteSqlRaw 或自定义 Dapper 查询实现。
2. 应用层分布式锁
使用 Redis 等中间件实现分布式锁,以实体集合为锁键,在 AdjustSortAsync 执行期间加锁,确保同一时间只有一个请求能修改排序。
3. 乐观并发控制
在 MyEntityName 实体中引入 ConcurrencyStamp 字段(已存在),每次更新时校验版本号。若版本不一致则抛出异常,前端提示用户刷新后重试。
当前实现未显式处理并发,建议在高并发场景下补充上述任一锁机制。
Section sources
前端调用建议与批量提交优化
为提升用户体验与系统性能,建议前端采用以下策略:
拖拽排序优化方案
- 本地预览:用户拖拽时,前端先在本地更新排序并实时渲染,提供即时反馈。
- 延迟提交:设置防抖(debounce)机制(如 500ms),避免频繁请求。
- 批量提交:若支持多项目排序,收集所有变更后一次性调用批量接口(可扩展
AdjustSortAsync支持批量)。 - 错误重试:若因并发冲突失败,提示用户“数据已变更,请刷新后重试”。
接口扩展建议
可新增批量调整接口:
Task AdjustSortBatchAsync(List<(Guid id, int sort)> items);
减少网络往返,提升性能。
Section sources
结论
MyEntityName 实体的排序功能通过 Sort 字段实现,AdjustSortAsync 方法确保了排序的连续性与唯一性。当前实现逻辑清晰,但在高并发场景下存在数据竞争风险,建议引入数据库行锁或分布式锁机制。前端应采用防抖与批量提交策略优化用户体验。未来可扩展批量接口以进一步提升性能。