|
@@ -1,35 +1,49 @@
|
|
|
package com.atguigu.tingshu.order.service.impl;
|
|
|
|
|
|
import cn.hutool.core.bean.BeanUtil;
|
|
|
+import cn.hutool.core.collection.CollUtil;
|
|
|
+import cn.hutool.core.date.DateUtil;
|
|
|
import cn.hutool.core.lang.Assert;
|
|
|
import cn.hutool.core.util.IdUtil;
|
|
|
+import com.atguigu.tingshu.account.AccountFeignClient;
|
|
|
import com.atguigu.tingshu.album.AlbumFeignClient;
|
|
|
import com.atguigu.tingshu.common.constant.RedisConstant;
|
|
|
+import com.atguigu.tingshu.common.execption.GuiguException;
|
|
|
+import com.atguigu.tingshu.common.result.Result;
|
|
|
+import com.atguigu.tingshu.common.util.AuthContextHolder;
|
|
|
import com.atguigu.tingshu.model.album.AlbumInfo;
|
|
|
+import com.atguigu.tingshu.model.album.TrackInfo;
|
|
|
+import com.atguigu.tingshu.model.order.OrderDerate;
|
|
|
+import com.atguigu.tingshu.model.order.OrderDetail;
|
|
|
import com.atguigu.tingshu.model.order.OrderInfo;
|
|
|
import com.atguigu.tingshu.model.user.VipServiceConfig;
|
|
|
import com.atguigu.tingshu.order.helper.SignHelper;
|
|
|
+import com.atguigu.tingshu.order.mapper.OrderDerateMapper;
|
|
|
+import com.atguigu.tingshu.order.mapper.OrderDetailMapper;
|
|
|
import com.atguigu.tingshu.order.mapper.OrderInfoMapper;
|
|
|
+import com.atguigu.tingshu.order.service.OrderDetailService;
|
|
|
import com.atguigu.tingshu.order.service.OrderInfoService;
|
|
|
import com.atguigu.tingshu.user.client.UserFeignClient;
|
|
|
+import com.atguigu.tingshu.vo.account.AccountDeductVo;
|
|
|
import com.atguigu.tingshu.vo.order.OrderDerateVo;
|
|
|
import com.atguigu.tingshu.vo.order.OrderDetailVo;
|
|
|
import com.atguigu.tingshu.vo.order.OrderInfoVo;
|
|
|
import com.atguigu.tingshu.vo.order.TradeVo;
|
|
|
import com.atguigu.tingshu.vo.user.UserInfoVo;
|
|
|
+import com.atguigu.tingshu.vo.user.UserPaidRecordVo;
|
|
|
+import com.baomidou.mybatisplus.core.toolkit.IdWorker;
|
|
|
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
|
|
import lombok.extern.slf4j.Slf4j;
|
|
|
import org.springframework.beans.factory.annotation.Autowired;
|
|
|
import org.springframework.data.redis.core.RedisTemplate;
|
|
|
+import org.springframework.data.redis.core.script.DefaultRedisScript;
|
|
|
import org.springframework.stereotype.Service;
|
|
|
|
|
|
import java.math.BigDecimal;
|
|
|
import java.math.RoundingMode;
|
|
|
-import java.util.ArrayList;
|
|
|
-import java.util.Date;
|
|
|
-import java.util.List;
|
|
|
-import java.util.Map;
|
|
|
+import java.util.*;
|
|
|
import java.util.concurrent.TimeUnit;
|
|
|
+import java.util.stream.Collectors;
|
|
|
|
|
|
import static com.atguigu.tingshu.common.constant.SystemConstant.*;
|
|
|
|
|
@@ -50,6 +64,18 @@ public class OrderInfoServiceImpl extends ServiceImpl<OrderInfoMapper, OrderInfo
|
|
|
@Autowired
|
|
|
private RedisTemplate redisTemplate;
|
|
|
|
|
|
+ @Autowired
|
|
|
+ private OrderDetailMapper orderDetailMapper;
|
|
|
+
|
|
|
+ @Autowired
|
|
|
+ private OrderDetailService orderDetailService;
|
|
|
+
|
|
|
+ @Autowired
|
|
|
+ private OrderDerateMapper orderDerateMapper;
|
|
|
+
|
|
|
+ @Autowired
|
|
|
+ private AccountFeignClient accountFeignClient;
|
|
|
+
|
|
|
|
|
|
|
|
|
* 对购买商品(VIP会员、专辑、声音)封装订单结算页所需要数据
|
|
@@ -149,17 +175,42 @@ public class OrderInfoServiceImpl extends ServiceImpl<OrderInfoMapper, OrderInfo
|
|
|
orderDetailVoList.add(orderDetailVo);
|
|
|
|
|
|
|
|
|
- if(originalAmount.compareTo(orderAmount) == 1){
|
|
|
+ if (originalAmount.compareTo(orderAmount) == 1) {
|
|
|
OrderDerateVo orderDerateVo = new OrderDerateVo();
|
|
|
orderDerateVo.setDerateType(ORDER_DERATE_ALBUM_DISCOUNT);
|
|
|
orderDerateVo.setDerateAmount(derateAmount);
|
|
|
- orderDerateVo.setRemarks("专辑限时减免:"+derateAmount);
|
|
|
+ orderDerateVo.setRemarks("专辑限时减免:" + derateAmount);
|
|
|
orderDerateVoList.add(orderDerateVo);
|
|
|
}
|
|
|
- }
|
|
|
+ } else if (ORDER_ITEM_TYPE_TRACK.equals(itemType)) {
|
|
|
+
|
|
|
+
|
|
|
+ Long trackId = tradeVo.getItemId();
|
|
|
+ List<TrackInfo> waitBuyTrackList = albumFeignClient.getWaitBuyTrackList(trackId, tradeVo.getTrackCount()).getData();
|
|
|
+ Assert.notNull(waitBuyTrackList, "不存在待结算商品");
|
|
|
+
|
|
|
+
|
|
|
+ Long albumId = waitBuyTrackList.get(0).getAlbumId();
|
|
|
+ AlbumInfo albumInfo = albumFeignClient.getAlbumInfo(albumId).getData();
|
|
|
+ Assert.notNull(albumInfo, "声音所属专辑:{}不存在", albumId);
|
|
|
+ BigDecimal price = albumInfo.getPrice();
|
|
|
|
|
|
-
|
|
|
+
|
|
|
+ originalAmount = price.multiply(BigDecimal.valueOf(tradeVo.getTrackCount()));
|
|
|
+ orderAmount = originalAmount;
|
|
|
|
|
|
+
|
|
|
+ orderDetailVoList = waitBuyTrackList
|
|
|
+ .stream()
|
|
|
+ .map(trackInfo -> {
|
|
|
+ OrderDetailVo orderDetailVo = new OrderDetailVo();
|
|
|
+ orderDetailVo.setItemId(trackInfo.getId());
|
|
|
+ orderDetailVo.setItemName("声音:" + trackInfo.getTrackTitle());
|
|
|
+ orderDetailVo.setItemUrl(trackInfo.getCoverUrl());
|
|
|
+ orderDetailVo.setItemPrice(price);
|
|
|
+ return orderDetailVo;
|
|
|
+ }).collect(Collectors.toList());
|
|
|
+ }
|
|
|
|
|
|
|
|
|
|
|
@@ -188,4 +239,154 @@ public class OrderInfoServiceImpl extends ServiceImpl<OrderInfoMapper, OrderInfo
|
|
|
return orderInfoVo;
|
|
|
}
|
|
|
|
|
|
+
|
|
|
+ * 提交订单
|
|
|
+ *
|
|
|
+ * @param orderInfoVo
|
|
|
+ * @return {orderNo:订单编号}
|
|
|
+ */
|
|
|
+ @Override
|
|
|
+ public String submitOrder(Long userId, OrderInfoVo orderInfoVo) {
|
|
|
+
|
|
|
+
|
|
|
+ String tradeKey = RedisConstant.ORDER_TRADE_NO_PREFIX + userId;
|
|
|
+
|
|
|
+ String script = "if redis.call(\"get\",KEYS[1]) == ARGV[1]\n" +
|
|
|
+ "then\n" +
|
|
|
+ " return redis.call(\"del\",KEYS[1])\n" +
|
|
|
+ "else\n" +
|
|
|
+ " return 0\n" +
|
|
|
+ "end";
|
|
|
+ DefaultRedisScript<Boolean> redisScript = new DefaultRedisScript<>(script, Boolean.class);
|
|
|
+
|
|
|
+ Boolean flag = (Boolean) redisTemplate.execute(redisScript, Arrays.asList(tradeKey), orderInfoVo.getTradeNo());
|
|
|
+ if (!flag) {
|
|
|
+
|
|
|
+ throw new GuiguException(500, "流水号验证失败");
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ Map<String, Object> map = BeanUtil.beanToMap(orderInfoVo);
|
|
|
+
|
|
|
+ map.remove("payWay");
|
|
|
+
|
|
|
+ SignHelper.checkSign(map);
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ OrderInfo orderInfo = this.saveOrderInfo(orderInfoVo);
|
|
|
+
|
|
|
+
|
|
|
+ String payWay = orderInfoVo.getPayWay();
|
|
|
+
|
|
|
+ if (ORDER_PAY_ACCOUNT.equals(payWay)) {
|
|
|
+
|
|
|
+
|
|
|
+ AccountDeductVo accountDeductVo = new AccountDeductVo();
|
|
|
+ accountDeductVo.setOrderNo(orderInfo.getOrderNo());
|
|
|
+ accountDeductVo.setUserId(orderInfo.getUserId());
|
|
|
+ accountDeductVo.setAmount(orderInfo.getOrderAmount());
|
|
|
+ accountDeductVo.setContent(orderInfo.getOrderTitle());
|
|
|
+
|
|
|
+ Result result = accountFeignClient.checkAndDeduct(accountDeductVo);
|
|
|
+
|
|
|
+ if (!result.getCode().equals(200)) {
|
|
|
+ throw new GuiguException(result.getCode(), result.getMessage());
|
|
|
+ }
|
|
|
+
|
|
|
+ orderInfo.setOrderStatus(ORDER_STATUS_PAID);
|
|
|
+ baseMapper.updateById(orderInfo);
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ UserPaidRecordVo userPaidRecordVo = new UserPaidRecordVo();
|
|
|
+ userPaidRecordVo.setOrderNo(orderInfo.getOrderNo());
|
|
|
+ userPaidRecordVo.setUserId(orderInfo.getUserId());
|
|
|
+ userPaidRecordVo.setItemType(orderInfo.getItemType());
|
|
|
+ List<OrderDetailVo> orderDetailVoList = orderInfoVo.getOrderDetailVoList();
|
|
|
+ if (CollUtil.isNotEmpty(orderDetailVoList)) {
|
|
|
+ List<Long> itemIdList = orderDetailVoList.stream().map(OrderDetailVo::getItemId)
|
|
|
+ .collect(Collectors.toList());
|
|
|
+ userPaidRecordVo.setItemIdList(itemIdList);
|
|
|
+
|
|
|
+ result = userFeignClient.savePaidRecord(userPaidRecordVo);
|
|
|
+
|
|
|
+ if (!result.getCode().equals(200)) {
|
|
|
+ throw new GuiguException(result.getCode(), result.getMessage());
|
|
|
+ }
|
|
|
+
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if (ORDER_PAY_WAY_WEIXIN.equals(payWay)) {
|
|
|
+
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ return orderInfo.getOrderNo();
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ * 保存订单及相关信息
|
|
|
+ *
|
|
|
+ * @param orderInfoVo
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ @Override
|
|
|
+ public OrderInfo saveOrderInfo(OrderInfoVo orderInfoVo) {
|
|
|
+
|
|
|
+
|
|
|
+ OrderInfo orderInfo = BeanUtil.copyProperties(orderInfoVo, OrderInfo.class);
|
|
|
+
|
|
|
+
|
|
|
+ orderInfo.setUserId(AuthContextHolder.getUserId());
|
|
|
+
|
|
|
+ orderInfo.setOrderStatus(ORDER_STATUS_UNPAID);
|
|
|
+
|
|
|
+ List<OrderDetailVo> orderDetailVoList = orderInfoVo.getOrderDetailVoList();
|
|
|
+ if (CollUtil.isNotEmpty(orderDetailVoList)) {
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ orderInfo.setOrderTitle(orderDetailVoList.get(0).getItemName());
|
|
|
+ }
|
|
|
+
|
|
|
+ String orderNo = DateUtil.today().replaceAll("-", "") + IdWorker.getIdStr();
|
|
|
+ orderInfo.setOrderNo(orderNo);
|
|
|
+
|
|
|
+ baseMapper.insert(orderInfo);
|
|
|
+ Long orderId = orderInfo.getId();
|
|
|
+
|
|
|
+
|
|
|
+ if (CollUtil.isNotEmpty(orderDetailVoList)) {
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ List<OrderDetail> orderDetailList = orderDetailVoList.stream().map(orderDetailVo -> {
|
|
|
+ OrderDetail orderDetail = BeanUtil.copyProperties(orderDetailVo, OrderDetail.class);
|
|
|
+ orderDetail.setOrderId(orderId);
|
|
|
+ return orderDetail;
|
|
|
+ }).collect(Collectors.toList());
|
|
|
+ orderDetailService.saveBatch(orderDetailList);
|
|
|
+ }
|
|
|
+
|
|
|
+ List<OrderDerateVo> orderDerateVoList = orderInfoVo.getOrderDerateVoList();
|
|
|
+ if (CollUtil.isNotEmpty(orderDetailVoList)) {
|
|
|
+ orderDerateVoList
|
|
|
+ .stream()
|
|
|
+ .forEach(orderDerateVo -> {
|
|
|
+ OrderDerate orderDerate = BeanUtil.copyProperties(orderDerateVo, OrderDerate.class);
|
|
|
+ orderDerate.setOrderId(orderId);
|
|
|
+ orderDerateMapper.insert(orderDerate);
|
|
|
+ });
|
|
|
+ }
|
|
|
+ return orderInfo;
|
|
|
+ }
|
|
|
+
|
|
|
}
|