|
@@ -3,15 +3,19 @@ package com.chuanghai.ihotel.service.impl;
|
|
|
import com.baomidou.mybatisplus.core.toolkit.IdWorker;
|
|
import com.baomidou.mybatisplus.core.toolkit.IdWorker;
|
|
|
import com.chuanghai.ihotel.common.exception.BizCodeEnume;
|
|
import com.chuanghai.ihotel.common.exception.BizCodeEnume;
|
|
|
import com.chuanghai.ihotel.common.exception.RRException;
|
|
import com.chuanghai.ihotel.common.exception.RRException;
|
|
|
|
|
+import com.chuanghai.ihotel.component.PayComponent;
|
|
|
import com.chuanghai.ihotel.config.JXNXSPayConfig;
|
|
import com.chuanghai.ihotel.config.JXNXSPayConfig;
|
|
|
|
|
+import com.chuanghai.ihotel.config.RabbitMQConfig;
|
|
|
import com.chuanghai.ihotel.constant.TimeConstant;
|
|
import com.chuanghai.ihotel.constant.TimeConstant;
|
|
|
import com.chuanghai.ihotel.controller.request.ConfrimOrderRequest;
|
|
import com.chuanghai.ihotel.controller.request.ConfrimOrderRequest;
|
|
|
import com.chuanghai.ihotel.controller.request.SubmitOrderRequest;
|
|
import com.chuanghai.ihotel.controller.request.SubmitOrderRequest;
|
|
|
|
|
+import com.chuanghai.ihotel.dto.EventMessageDTO;
|
|
|
import com.chuanghai.ihotel.dto.LockRoomDTO;
|
|
import com.chuanghai.ihotel.dto.LockRoomDTO;
|
|
|
import com.chuanghai.ihotel.entity.HotelUserEntity;
|
|
import com.chuanghai.ihotel.entity.HotelUserEntity;
|
|
|
import com.chuanghai.ihotel.entity.RoomEntity;
|
|
import com.chuanghai.ihotel.entity.RoomEntity;
|
|
|
import com.chuanghai.ihotel.entity.RoomTypeEntity;
|
|
import com.chuanghai.ihotel.entity.RoomTypeEntity;
|
|
|
import com.chuanghai.ihotel.entity.SystemSettingEntity;
|
|
import com.chuanghai.ihotel.entity.SystemSettingEntity;
|
|
|
|
|
+import com.chuanghai.ihotel.enums.EventMessageTypeEnum;
|
|
|
import com.chuanghai.ihotel.enums.OrderBillStatuEnum;
|
|
import com.chuanghai.ihotel.enums.OrderBillStatuEnum;
|
|
|
import com.chuanghai.ihotel.enums.OrderStatuEnum;
|
|
import com.chuanghai.ihotel.enums.OrderStatuEnum;
|
|
|
import com.chuanghai.ihotel.enums.UserIdentityTypeEnum;
|
|
import com.chuanghai.ihotel.enums.UserIdentityTypeEnum;
|
|
@@ -25,9 +29,12 @@ import com.chuanghai.ihotel.util.CommonUtil;
|
|
|
import com.chuanghai.ihotel.vo.ConfirmOrderVO;
|
|
import com.chuanghai.ihotel.vo.ConfirmOrderVO;
|
|
|
import com.chuanghai.ihotel.vo.LoginUserVO;
|
|
import com.chuanghai.ihotel.vo.LoginUserVO;
|
|
|
import com.chuanghai.ihotel.vo.OrderSubmitVO;
|
|
import com.chuanghai.ihotel.vo.OrderSubmitVO;
|
|
|
|
|
+import lombok.extern.slf4j.Slf4j;
|
|
|
|
|
+import org.springframework.amqp.rabbit.core.RabbitTemplate;
|
|
|
import org.springframework.beans.BeanUtils;
|
|
import org.springframework.beans.BeanUtils;
|
|
|
import org.springframework.beans.factory.annotation.Autowired;
|
|
import org.springframework.beans.factory.annotation.Autowired;
|
|
|
import org.springframework.context.annotation.Lazy;
|
|
import org.springframework.context.annotation.Lazy;
|
|
|
|
|
+import org.springframework.stereotype.Component;
|
|
|
import org.springframework.stereotype.Service;
|
|
import org.springframework.stereotype.Service;
|
|
|
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
|
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
|
|
import com.baomidou.mybatisplus.core.metadata.IPage;
|
|
import com.baomidou.mybatisplus.core.metadata.IPage;
|
|
@@ -40,6 +47,8 @@ import com.chuanghai.ihotel.dao.HotelOrderDao;
|
|
|
import com.chuanghai.ihotel.entity.HotelOrderEntity;
|
|
import com.chuanghai.ihotel.entity.HotelOrderEntity;
|
|
|
import com.chuanghai.ihotel.service.HotelOrderService;
|
|
import com.chuanghai.ihotel.service.HotelOrderService;
|
|
|
import org.springframework.transaction.annotation.Transactional;
|
|
import org.springframework.transaction.annotation.Transactional;
|
|
|
|
|
+import org.springframework.util.StringUtils;
|
|
|
|
|
+import sun.plugin2.message.EventMessage;
|
|
|
|
|
|
|
|
import javax.validation.constraints.Min;
|
|
import javax.validation.constraints.Min;
|
|
|
import javax.validation.constraints.NotNull;
|
|
import javax.validation.constraints.NotNull;
|
|
@@ -47,8 +56,10 @@ import java.math.BigDecimal;
|
|
|
import java.time.LocalDate;
|
|
import java.time.LocalDate;
|
|
|
import java.time.LocalDateTime;
|
|
import java.time.LocalDateTime;
|
|
|
import java.time.temporal.ChronoUnit;
|
|
import java.time.temporal.ChronoUnit;
|
|
|
|
|
+import java.time.temporal.TemporalAccessor;
|
|
|
|
|
+import java.util.Map;
|
|
|
|
|
|
|
|
-
|
|
|
|
|
|
|
+@Slf4j
|
|
|
@Service("hotelOrderService")
|
|
@Service("hotelOrderService")
|
|
|
public class HotelOrderServiceImpl extends ServiceImpl<HotelOrderDao, HotelOrderEntity> implements HotelOrderService {
|
|
public class HotelOrderServiceImpl extends ServiceImpl<HotelOrderDao, HotelOrderEntity> implements HotelOrderService {
|
|
|
|
|
|
|
@@ -63,7 +74,13 @@ public class HotelOrderServiceImpl extends ServiceImpl<HotelOrderDao, HotelOrder
|
|
|
@Autowired
|
|
@Autowired
|
|
|
private RoomService roomService;
|
|
private RoomService roomService;
|
|
|
@Autowired
|
|
@Autowired
|
|
|
|
|
+ private PayComponent payComponent;
|
|
|
|
|
+ @Autowired
|
|
|
private JXNXSPayConfig jxnxsPayConfig;
|
|
private JXNXSPayConfig jxnxsPayConfig;
|
|
|
|
|
+ @Autowired
|
|
|
|
|
+ private RabbitTemplate rabbitTemplate;
|
|
|
|
|
+ @Autowired
|
|
|
|
|
+ private RabbitMQConfig rabbitMQConfig;
|
|
|
|
|
|
|
|
@Override
|
|
@Override
|
|
|
public PageUtils queryPage(PageParam pageParam) {
|
|
public PageUtils queryPage(PageParam pageParam) {
|
|
@@ -76,6 +93,14 @@ public class HotelOrderServiceImpl extends ServiceImpl<HotelOrderDao, HotelOrder
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
@Override
|
|
@Override
|
|
|
|
|
+ public HotelOrderEntity findByOrderNo(String orderNo) {
|
|
|
|
|
+ QueryWrapper<HotelOrderEntity> queryWrapper = new QueryWrapper<>();
|
|
|
|
|
+ queryWrapper.eq("order_no", orderNo);
|
|
|
|
|
+ queryWrapper.last("limit 1");
|
|
|
|
|
+ return this.getOne(queryWrapper);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ @Override
|
|
|
public ConfirmOrderVO confirmOrder(ConfrimOrderRequest request) {
|
|
public ConfirmOrderVO confirmOrder(ConfrimOrderRequest request) {
|
|
|
SystemSettingEntity systemSetting = systemSettingService.get();
|
|
SystemSettingEntity systemSetting = systemSettingService.get();
|
|
|
|
|
|
|
@@ -128,6 +153,36 @@ public class HotelOrderServiceImpl extends ServiceImpl<HotelOrderDao, HotelOrder
|
|
|
return vo;
|
|
return vo;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+ @Override
|
|
|
|
|
+ public void orderPaySuccess(Long orderId, String orderNo, String realPayAmount, LocalDateTime payTime) {
|
|
|
|
|
+ HotelOrderEntity order = null;
|
|
|
|
|
+ if (orderId != null) {
|
|
|
|
|
+ order = this.getById(orderId);
|
|
|
|
|
+ } else {
|
|
|
|
|
+ if (StringUtils.hasText(orderNo)) {
|
|
|
|
|
+ order = this.findByOrderNo(orderNo);
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ if (order == null) {
|
|
|
|
|
+ log.warn("修改订单状态:订单【{}】不存在", orderId);
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+ if (OrderStatuEnum.WAIT_PAY.getCode().equalsIgnoreCase(order.getOrderStatu())) {
|
|
|
|
|
+ if (Math.abs(order.getPayAmount().subtract(new BigDecimal(realPayAmount)).doubleValue()) < 0.01) {
|
|
|
|
|
+ // 订单最终支付金额验证成功
|
|
|
|
|
+ if (payTime == null) {
|
|
|
|
|
+ order.setPayTime(LocalDateTime.now());
|
|
|
|
|
+ } else {
|
|
|
|
|
+ order.setPayTime(payTime);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ order.setOrderStatu(OrderStatuEnum.FINISH_PAY.getCode());
|
|
|
|
|
+ this.updateById(order);
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
@Transactional
|
|
@Transactional
|
|
|
@Override
|
|
@Override
|
|
|
public OrderSubmitVO submitOrder(String userToken, SubmitOrderRequest request) {
|
|
public OrderSubmitVO submitOrder(String userToken, SubmitOrderRequest request) {
|
|
@@ -199,10 +254,84 @@ public class HotelOrderServiceImpl extends ServiceImpl<HotelOrderDao, HotelOrder
|
|
|
hotelOrder.setDeleteFlag("1"); // 0删除、1正常
|
|
hotelOrder.setDeleteFlag("1"); // 0删除、1正常
|
|
|
this.save(hotelOrder);
|
|
this.save(hotelOrder);
|
|
|
|
|
|
|
|
- // 发送mq信息 TODO
|
|
|
|
|
|
|
+ // 发送延迟消息
|
|
|
|
|
+ EventMessageDTO eventMessage = EventMessageDTO.builder()
|
|
|
|
|
+ .eventMessageType(EventMessageTypeEnum.PRODUCT_ORDER_NEW.name())
|
|
|
|
|
+ .accountNo(loginUserVO.getCardNumber())
|
|
|
|
|
+ .bizId(orderId)
|
|
|
|
|
+ .build();
|
|
|
|
|
|
|
|
|
|
+ rabbitTemplate.convertAndSend(rabbitMQConfig.getOrderEventExchange(), rabbitMQConfig.getOrderCloseDelayRoutingKey(), eventMessage);
|
|
|
|
|
+
|
|
|
|
|
+ // 返回支付参数
|
|
|
String payUrl = String.format(jxnxsPayConfig.getPayUrl(), hotelOrder.getOrderNo(), request.getPayAmount());
|
|
String payUrl = String.format(jxnxsPayConfig.getPayUrl(), hotelOrder.getOrderNo(), request.getPayAmount());
|
|
|
return OrderSubmitVO.builder().orderId(hotelOrder.getId()).payUrl(payUrl).build();
|
|
return OrderSubmitVO.builder().orderId(hotelOrder.getId()).payUrl(payUrl).build();
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+ @Override
|
|
|
|
|
+ public void handleOrderMessage(EventMessageDTO eventMessageDTO) {
|
|
|
|
|
+ String messageType = eventMessageDTO.getEventMessageType();
|
|
|
|
|
+ try {
|
|
|
|
|
+ if(EventMessageTypeEnum.PRODUCT_ORDER_NEW.name().equalsIgnoreCase(messageType)) {
|
|
|
|
|
+ // 关单消息
|
|
|
|
|
+ this.closeOrder(eventMessageDTO);
|
|
|
|
|
+ }
|
|
|
|
|
+ } catch (Exception e) {
|
|
|
|
|
+ log.error("订单消费者消费失败:{}", eventMessageDTO);
|
|
|
|
|
+ throw new RRException(BizCodeEnume.MQ_CONSUME_EXCEPTION);
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ @Override
|
|
|
|
|
+ public void closeOrder(EventMessageDTO eventMessageDTO) {
|
|
|
|
|
+ Long orderId = eventMessageDTO.getBizId();
|
|
|
|
|
+ String cardNumber = eventMessageDTO.getAccountNo();
|
|
|
|
|
+ HotelOrderEntity orderEntity = this.getById(orderId);
|
|
|
|
|
+ if (orderEntity == null) {
|
|
|
|
|
+ log.warn("关单:订单【{}】不存在", orderId);
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 判断订单状态
|
|
|
|
|
+ if (!orderEntity.getOrderStatu().equalsIgnoreCase(OrderStatuEnum.WAIT_PAY.getCode())) {
|
|
|
|
|
+ log.info("关单:订单不是初始状态待支付:{}", eventMessageDTO);
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 未支付,向第三方支付平台查询状态
|
|
|
|
|
+ Map<String, String> map = payComponent.queryOrderStatus(orderEntity.getOrderNo());
|
|
|
|
|
+ log.info("关单:订单支付状态查询结果,【{}】", map);
|
|
|
|
|
+
|
|
|
|
|
+ String payStatus = map.get("status");
|
|
|
|
|
+ if ("1".equalsIgnoreCase(payStatus)) { // 已经完成支付
|
|
|
|
|
+ String amount = map.get("trade_amount");
|
|
|
|
|
+ String payTimeStr = map.get("trade_pay_time");
|
|
|
|
|
+ LocalDateTime payTime = LocalDateTime.parse(payTimeStr, TimeConstant.DEFAULT_DTF);
|
|
|
|
|
+ String realPayAmount = new BigDecimal(amount).divide(new BigDecimal(100)).setScale(2, BigDecimal.ROUND_UP).toString(); // 分转成元
|
|
|
|
|
+ this.orderPaySuccess(orderId, orderEntity.getOrderNo(), realPayAmount, payTime);
|
|
|
|
|
+ } else { // 未支付,取消订单
|
|
|
|
|
+ this.cancelOrder(cardNumber, orderId);
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ @Override
|
|
|
|
|
+ public boolean cancelOrder(String userFlag, Long orderId) {
|
|
|
|
|
+ HotelOrderEntity orderEntity = this.getById(orderId);
|
|
|
|
|
+ if (orderEntity == null) {
|
|
|
|
|
+ log.warn("取消订单:订单【{}】不存在", orderId);
|
|
|
|
|
+ return false;
|
|
|
|
|
+ }
|
|
|
|
|
+ if (!orderEntity.getUserFlag().equalsIgnoreCase(userFlag)) {
|
|
|
|
|
+ log.warn("取消订单:操作越权,非法取消订单,订单原用户【】,操作用户【】", orderEntity.getUserFlag(), userFlag);
|
|
|
|
|
+ throw new RRException(BizCodeEnume.PERMISSION_DENIED, "不能取消非自己的订单");
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ orderEntity.setOrderStatu(OrderStatuEnum.CANCEL.getCode());
|
|
|
|
|
+ this.updateById(orderEntity);
|
|
|
|
|
+
|
|
|
|
|
+ // 释放库存
|
|
|
|
|
+ roomRealtimeStatuService.releaseByBizId(orderEntity.getId());
|
|
|
|
|
+ return true;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
}
|
|
}
|