|
@@ -1,9 +1,15 @@
|
|
|
package com.webchat.service.lottery;
|
|
|
|
|
|
import com.webchat.common.constants.LotteryConstants;
|
|
|
+import com.webchat.common.constants.WebConstant;
|
|
|
+import com.webchat.common.enums.WalletTransEventEnum;
|
|
|
import com.webchat.common.exception.BusinessException;
|
|
|
+import com.webchat.common.util.ListUtil;
|
|
|
import com.webchat.domain.vo.request.lottery.LotteryActivityStatusUpdateVO;
|
|
|
import com.webchat.domain.vo.response.lottery.LotteryActivityVO;
|
|
|
+import com.webchat.domain.vo.response.lottery.LotteryDrawBulkResponseVO;
|
|
|
+import com.webchat.domain.vo.response.lottery.LotteryDrawOneResponseVO;
|
|
|
+import com.webchat.service.UserWalletService;
|
|
|
import com.webchat.service.queue.LotteryOrderQueue;
|
|
|
import com.webchat.service.queue.dto.LotteryOrderQueueDTO;
|
|
|
import lombok.extern.slf4j.Slf4j;
|
|
@@ -12,6 +18,7 @@ import org.springframework.beans.factory.annotation.Autowired;
|
|
|
import org.springframework.stereotype.Service;
|
|
|
import org.springframework.util.Assert;
|
|
|
|
|
|
+import java.math.BigDecimal;
|
|
|
import java.util.ArrayList;
|
|
|
import java.util.List;
|
|
|
import java.util.Map;
|
|
@@ -38,6 +45,8 @@ public class LotteryService {
|
|
|
private LotteryItemService lotteryItemService;
|
|
|
@Autowired
|
|
|
private LotteryCacheService lotteryCacheService;
|
|
|
+ @Autowired
|
|
|
+ private UserWalletService userWalletService;
|
|
|
|
|
|
/**
|
|
|
* 幸运抽奖
|
|
@@ -46,19 +55,60 @@ public class LotteryService {
|
|
|
* @param userId 当前登录用户id
|
|
|
* @return 中奖商品id
|
|
|
*/
|
|
|
- public Long luckDraw(String lotteryActivityId, String userId) {
|
|
|
+ public LotteryDrawOneResponseVO luckDraw(String lotteryActivityId, String userId) {
|
|
|
|
|
|
+ // 查询活动配置
|
|
|
+ LotteryActivityVO activity = lotteryActivityService.getLotteryActivityDetailFromCache(lotteryActivityId);
|
|
|
+ /**
|
|
|
+ * 校验活动状态及用户钱包余额
|
|
|
+ */
|
|
|
+ this.validateUserJoinLotteryCondition(userId, activity, 1);
|
|
|
/**
|
|
|
* 1、抽奖
|
|
|
*/
|
|
|
Long lotteryItemId = this.doLotteryDraw(lotteryActivityId);
|
|
|
-
|
|
|
+ /**
|
|
|
+ * 扣减钱包余额
|
|
|
+ */
|
|
|
+ boolean free = activity.getMoney() == null || activity.getMoney().compareTo(new BigDecimal("0")) == 0;
|
|
|
+ BigDecimal lastWalletBalance = null;
|
|
|
+ if (!free) {
|
|
|
+ // 实时钱包余额扣减
|
|
|
+ try {
|
|
|
+ lastWalletBalance = userWalletService.doTrans(WalletTransEventEnum.JOIN_LOTTERY,
|
|
|
+ userId,
|
|
|
+ WebConstant.SYSTEM_WALLET_ID, activity.getMoney());
|
|
|
+ } catch (Exception e) {
|
|
|
+ // 钱包扣除异常
|
|
|
+ // rollback
|
|
|
+ // TODO
|
|
|
+ }
|
|
|
+ }
|
|
|
/**
|
|
|
* 2、处理中奖订单
|
|
|
*/
|
|
|
this.handleLotteryOrder(userId, lotteryActivityId, lotteryItemId);
|
|
|
|
|
|
- return lotteryItemId;
|
|
|
+ return LotteryDrawOneResponseVO.of(lastWalletBalance, lotteryItemId);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 校验是否满足抽奖要求
|
|
|
+ *
|
|
|
+ * @param userId
|
|
|
+ * @param activity
|
|
|
+ */
|
|
|
+ private void validateUserJoinLotteryCondition(String userId, LotteryActivityVO activity, int times) {
|
|
|
+ Assert.notNull(activity, "活动不存在");
|
|
|
+ Assert.isTrue(LotteryConstants.LotteryActivityStatus.RUNNING.getStatus().equals(activity.getStatus()), "非进行中活动!");
|
|
|
+ BigDecimal money = activity.getMoney();
|
|
|
+ boolean free = money == null || money.compareTo(new BigDecimal("0")) == 0;
|
|
|
+ if (free) {
|
|
|
+ // 免费抽奖
|
|
|
+ return;
|
|
|
+ }
|
|
|
+ BigDecimal balance = userWalletService.getUserWalletBalanceFromCache(userId);
|
|
|
+ Assert.isTrue(balance.compareTo(money.multiply(new BigDecimal(times))) >=0, "钱包余额不足!");
|
|
|
}
|
|
|
|
|
|
/**
|
|
@@ -69,7 +119,13 @@ public class LotteryService {
|
|
|
* @param times
|
|
|
* @return
|
|
|
*/
|
|
|
- public synchronized List<Long> luckDraw(String lotteryActivityId, String userId, int times) {
|
|
|
+ public LotteryDrawBulkResponseVO luckDraw(String lotteryActivityId, String userId, int times) {
|
|
|
+ // 查询活动配置
|
|
|
+ LotteryActivityVO activity = lotteryActivityService.getLotteryActivityDetailFromCache(lotteryActivityId);
|
|
|
+ /**
|
|
|
+ * 校验活动状态及用户钱包余额
|
|
|
+ */
|
|
|
+ this.validateUserJoinLotteryCondition(userId, activity, times);
|
|
|
List<Long> result = new Vector<>();
|
|
|
/**
|
|
|
* 这里下简单实现,这种做法不是很好,并发量大下可能容易出问题
|
|
@@ -79,18 +135,25 @@ public class LotteryService {
|
|
|
this.handleLotteryOrder(userId, lotteryActivityId, lotteryItemId);
|
|
|
result.add(lotteryItemId);
|
|
|
}
|
|
|
- return result;
|
|
|
- }
|
|
|
-
|
|
|
- /**
|
|
|
- * 最新一期活动抽奖
|
|
|
- * @param userId
|
|
|
- * @return
|
|
|
- */
|
|
|
- public Long luckDrawLastActivity(String userId) {
|
|
|
- String activityId = lotteryCacheService.getLastLotteryActivityIdFromCache();
|
|
|
- Assert.isTrue(StringUtils.isNotBlank(activityId), "未查询到最新一期的抽奖活动");
|
|
|
- return this.luckDraw(activityId, userId);
|
|
|
+ /**
|
|
|
+ * 扣减钱包余额
|
|
|
+ */
|
|
|
+ boolean free = activity.getMoney() == null || activity.getMoney().compareTo(new BigDecimal("0")) == 0;
|
|
|
+ BigDecimal lastWalletBalance = null;
|
|
|
+ if (!free) {
|
|
|
+ // 实时钱包余额扣减
|
|
|
+ try {
|
|
|
+ lastWalletBalance = userWalletService.doTrans(WalletTransEventEnum.JOIN_LOTTERY,
|
|
|
+ userId,
|
|
|
+ WebConstant.SYSTEM_WALLET_ID,
|
|
|
+ activity.getMoney().multiply(new BigDecimal(times)));
|
|
|
+ } catch (Exception e) {
|
|
|
+ // 钱包扣除异常
|
|
|
+ // rollback
|
|
|
+ // TODO
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return LotteryDrawBulkResponseVO.of(lastWalletBalance, result);
|
|
|
}
|
|
|
|
|
|
/**
|
|
@@ -131,6 +194,8 @@ public class LotteryService {
|
|
|
for (int i = 0; i < stock; i++) {
|
|
|
itemPool.add(itemId);
|
|
|
}
|
|
|
+ // 打散奖池
|
|
|
+ ListUtil.shuffle(itemPool);
|
|
|
}
|
|
|
|
|
|
/**
|