201743-修复Mex模块挂单成交但没有订单记录的bug.md 3.7 KB

修复Mex模块挂单成交但没有订单记录的bug

任务时间

  • 开始时间:2025-06-20 17:33:53
  • 完成时间:2025-06-20 17:43:00
  • 耗时:约10分钟

问题描述

Mex模块存在bug:有挂单成交的,但是没有订单记录。具体表现为:

  • 订单状态已更新为COMPLETED(已完成)
  • 但对应的成交记录表(mex_transactions)中没有相应的记录
  • 导致数据不一致,影响交易记录的完整性

问题分析

通过代码分析发现问题根源在于撮合逻辑的执行顺序:

原有问题逻辑

  1. 更新订单状态为COMPLETED
  2. 更新仓库库存
  3. 创建成交记录
  4. 执行资金/物品流转

问题所在

如果在步骤4(资金/物品流转)中出现异常,由于订单状态已经在步骤1中更新为COMPLETED,但成交记录可能因为异常而没有正确保存,导致数据不一致。

解决方案

1. 调整撮合逻辑执行顺序

修改executeUserBuyItemOrderMatchexecuteUserSellItemOrderMatch方法:

新的执行顺序:

  1. 先执行资金/物品流转(验证业务逻辑)
  2. 资金和物品流转成功后,更新订单状态
  3. 更新仓库库存
  4. 创建成交记录
  5. 验证成交记录是否创建成功

2. 添加成交记录创建验证

// 验证成交记录是否创建成功
if (!$transaction || !$transaction->id) {
    throw new \Exception('成交记录创建失败');
}

3. 创建修复命令

创建FixMissingTransactionRecordsCommand命令来处理历史数据不一致问题:

  • 检测已完成但缺失成交记录的订单
  • 提供预览模式(--dry-run)
  • 支持批量修复历史数据

4. 完善模型关联关系

MexOrder模型添加关联关系方法:

  • buyTransactions() - 获取作为买单的成交记录
  • sellTransactions() - 获取作为卖单的成交记录

修复结果

历史数据修复

发现并修复了2个数据不一致的订单:

  • 订单ID 80:用户39071的卖出订单
  • 订单ID 83:用户39072的卖出订单

验证结果

已完成订单总数: 2
缺失成交记录的已完成订单数: 0
✅ 数据一致性检查通过

孤立的成交记录数: 0
✅ 成交记录关联检查通过

涉及文件

核心修复文件

  • app/Module/Mex/Logic/MexMatchLogic.php - 修复撮合逻辑
  • app/Module/Mex/Models/MexOrder.php - 添加关联关系
  • app/Module/Mex/Commands/FixMissingTransactionRecordsCommand.php - 修复命令
  • app/Module/Mex/Providers/MexServiceProvider.php - 注册修复命令

测试文件

  • app/Module/Mex/Tests/MexMatchLogicBugFixTest.php - 单元测试
  • app/Module/Mex/Tests/manual_test_bug_fix.php - 手动测试脚本

技术要点

1. 事务一致性

确保订单状态更新和成交记录创建在同一个事务中,避免数据不一致。

2. 异常处理

在资金/物品流转失败时,不更新订单状态,保持数据一致性。

3. 数据验证

添加成交记录创建的验证逻辑,确保关键数据的完整性。

4. 向后兼容

修复命令可以处理历史数据,不影响现有业务流程。

预防措施

1. 代码层面

  • 调整了撮合逻辑的执行顺序
  • 添加了更严格的数据验证
  • 完善了异常处理机制

2. 监控层面

  • 提供了数据一致性检查脚本
  • 可定期运行修复命令检查数据完整性

3. 测试层面

  • 创建了专门的测试用例
  • 验证了修复逻辑的有效性

总结

本次修复解决了Mex模块中挂单成交但没有订单记录的关键bug,通过调整执行顺序、添加验证逻辑和提供修复工具,确保了数据的一致性和完整性。修复后的系统更加稳定可靠,避免了类似问题的再次发生。