GroupsRelationChangeServiceImpl.java 6.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172
  1. package com.cyksj.service.relation.impl;
  2. import com.baomidou.mybatisplus.core.toolkit.Wrappers;
  3. import com.cyksj.common.constant.Constant;
  4. import com.cyksj.common.exception.BusinessRuntimeException;
  5. import com.cyksj.dto.RedisKey;
  6. import com.cyksj.mapper.GoodsDonSkuMapper;
  7. import com.cyksj.mapper.GroupsMapper;
  8. import com.cyksj.mapper.GroupsRelationMapper;
  9. import com.cyksj.mapper.OrderDonMapper;
  10. import com.cyksj.model.entity.*;
  11. import com.cyksj.redis.RedisService;
  12. import com.cyksj.service.groups.GroupsFuncService;
  13. import com.cyksj.service.order.OrderDonTicketRecordService;
  14. import com.cyksj.service.relation.GroupRelationClearService;
  15. import com.cyksj.service.relation.GroupsRelationChangeService;
  16. import lombok.RequiredArgsConstructor;
  17. import lombok.extern.slf4j.Slf4j;
  18. import org.springframework.stereotype.Service;
  19. import org.springframework.transaction.annotation.Transactional;
  20. /**
  21. * 项目名: yhlxj2
  22. * 文件名: GroupsRelationChangeServiceImpl
  23. * 创建者: JavaZou
  24. * 创建时间:2024/10/28 14:15
  25. */
  26. @Service
  27. @RequiredArgsConstructor
  28. @Slf4j
  29. public class GroupsRelationChangeServiceImpl implements GroupsRelationChangeService {
  30. private final GroupsRelationMapper relationMapper;
  31. private final RedisService redisService;
  32. private final GroupsMapper groupsMapper;
  33. private final GroupsFuncService groupsFuncService;
  34. private final GoodsDonSkuMapper skuMapper;
  35. private final OrderDonMapper orderDonMapper;
  36. private final GroupRelationClearService relationClearService;
  37. private final OrderDonTicketRecordService orderDonTicketRecordService;
  38. @Override
  39. @Transactional(rollbackFor = Throwable.class)
  40. public GroupsRelation changeTicket(Long userId, Long oriRelationId, Long itemGroupsId, Long skuId) {
  41. validateSameSku(oriRelationId, skuId);
  42. GroupsRelation relation = getRelationThisTrips(userId, itemGroupsId, 1);
  43. if (relation == null) {
  44. return relation;
  45. }
  46. validateSameSku(relation.getId(), skuId);
  47. syncGroupsRelation(oriRelationId, relation);
  48. return relation;
  49. }
  50. @Override
  51. @Transactional(rollbackFor = Throwable.class)
  52. public GroupsRelation getEmptyGroupsRelation(Long userId, Long oriRelationId, Long skuId) {
  53. validateSameSku(oriRelationId, skuId);
  54. return getEmptyGroupsRelationIfRetry(userId, oriRelationId, skuId, 1);
  55. }
  56. public GroupsRelation getEmptyGroupsRelationIfRetry(Long userId, Long oriRelationId, Long skuId, Integer retryNum) {
  57. GroupsTrips groupsTrips = groupsMapper.selectOne(Wrappers.lambdaQuery(GroupsTrips.class)
  58. .eq(GroupsTrips::getStatus, GroupsTrips.Status.waiting)
  59. .eq(GroupsTrips::getSkuId, skuId)
  60. .gt(GroupsTrips::getAvailableNum, 0)
  61. .orderByAsc(GroupsTrips::getAvailableNum)
  62. .last("limit 1"));
  63. GroupsRelation relation = null;
  64. if (groupsTrips != null) {
  65. relation = relationMapper.selectOne(Wrappers.lambdaQuery(GroupsRelation.class)
  66. .eq(GroupsRelation::getGroupsId, groupsTrips.getId())
  67. .eq(GroupsRelation::getStatus, GroupsRelation.Status.none)
  68. .eq(GroupsRelation::getUserId, 0)
  69. .apply("not exists (select 1 from order_don_ticket_record ticket where ticket.active_relation_id = groups_relation.id)")
  70. .last("limit 1"));
  71. }
  72. if (relation == null) {
  73. //新增空车队
  74. GoodsDonSku sku = skuMapper.selectById(skuId);
  75. relation = groupsFuncService.createNewGroupsTrips(sku);
  76. }
  77. if (!redisService.setNx(RedisKey.GROUPS_RELATION_NUM_KEY + relation.getId(), userId, 60 * 2L)) {
  78. retryNum++;
  79. if (retryNum >= 7) {
  80. return null;
  81. }
  82. return getEmptyGroupsRelationIfRetry(userId, oriRelationId, skuId, retryNum);
  83. }
  84. Long groupsId = relation.getGroupsId();
  85. int count = groupsMapper.decrAvailableNum(groupsId);
  86. if (count == 0) {
  87. log.error("车位异常 groupId:{}", groupsId);
  88. groupsMapper.updateAvailableNum(groupsId);
  89. throw BusinessRuntimeException.getInstance("车位异常,请重试");
  90. }
  91. syncGroupsRelation(oriRelationId, relation);
  92. return relation;
  93. }
  94. /**
  95. * 寻找该车队空余车位
  96. */
  97. public GroupsRelation getRelationThisTrips(Long userId, Long groupsId, Integer retryNum) {
  98. //寻找快满编车队进行占座
  99. GroupsRelation relation = relationMapper.selectRandomOneRelationByGroupsId(groupsId);
  100. if (relation == null) {
  101. log.error("该车队人员已满,请选择另一车队");
  102. return null;
  103. }
  104. Long relationId = relation.getId();
  105. if (!redisService.setNx(RedisKey.GROUPS_RELATION_NUM_KEY + relationId, userId, 60 * 2L)) {
  106. if (retryNum == 7){
  107. log.error("该车队人员已满,请选择另一车队");
  108. return null;
  109. }
  110. retryNum++;
  111. return getRelationThisTrips(userId, groupsId, retryNum);
  112. }
  113. int count = groupsMapper.decrAvailableNum(relation.getGroupsId());
  114. if (count == 0) {
  115. log.error("车位异常 groupId:{}", groupsId);
  116. groupsMapper.updateAvailableNum(groupsId);
  117. log.error("车位异常");
  118. return null;
  119. }
  120. return relation;
  121. }
  122. public void syncGroupsRelation(Long oriRelationId, GroupsRelation newRelation) {
  123. OrderDonTicketRecord multiTicket = orderDonTicketRecordService.getActiveByRelationIdForUpdate(oriRelationId);
  124. if (multiTicket != null && multiTicket.getStatus() == OrderDonTicketRecord.Status.refunding) {
  125. throw BusinessRuntimeException.getInstance("订单退款处理中,暂不支持更换车票");
  126. }
  127. GroupsRelation oriRelation = relationMapper.selectByIdForUpdate(oriRelationId);
  128. newRelation.setStartTime(oriRelation.getStartTime());
  129. newRelation.setExpiryTime(oriRelation.getExpiryTime());
  130. newRelation.setStatus(oriRelation.getStatus());
  131. newRelation.setUserId(oriRelation.getUserId());
  132. newRelation.setYhsId(oriRelation.getYhsId());
  133. relationMapper.updateById(newRelation);
  134. oriRelation.setNewRelationId(newRelation.getId());
  135. relationClearService.clearTicket(oriRelation, UserTicketClearedRecord.Source.change_ticket);
  136. if (multiTicket != null) {
  137. return;
  138. }
  139. OrderDon orderDon = orderDonMapper.selectOne(Wrappers.lambdaQuery(OrderDon.class)
  140. .eq(OrderDon::getRelationId, oriRelationId)
  141. .eq(OrderDon::getUserId, newRelation.getUserId())
  142. .notIn(OrderDon::getStatus, Constant.noOrderStatus)
  143. .orderByDesc(OrderDon::getId)
  144. .last("limit 1"));
  145. if (orderDon != null) {
  146. orderDon.setRelationId(newRelation.getId());
  147. orderDonMapper.updateById(orderDon);
  148. }
  149. }
  150. private void validateSameSku(Long relationId, Long skuId) {
  151. Long relationSkuId = relationMapper.getGroupTripsSkuIdByRelationId(relationId);
  152. if (skuId == null || relationSkuId == null || !skuId.equals(relationSkuId)) {
  153. throw BusinessRuntimeException.getInstance("仅支持更换同规格车票");
  154. }
  155. }
  156. }