幸运数字-结算

This commit is contained in:
khalil
2025-04-29 16:55:06 +08:00
parent 27ae2cf61f
commit 12878ba35b
4 changed files with 152 additions and 6 deletions

View File

@@ -10,6 +10,7 @@ import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
@@ -57,4 +58,13 @@ public class LuckyNumberActRoundService extends ServiceImpl<LuckyNumberActRoundM
.stream()
.collect(Collectors.toMap(LuckyNumberActRound::getDate, v -> v));
}
public boolean saveLuckyNumber(String date, Integer partitionId, int luckyNumber) {
return update(Wrappers.<LuckyNumberActRound>lambdaUpdate()
.set(LuckyNumberActRound::getLuckyNumber, luckyNumber)
.set(LuckyNumberActRound::getUpdateTime, new Date())
.eq(LuckyNumberActRound::getDate, date)
.eq(LuckyNumberActRound::getPartitionId, partitionId)
.isNull(LuckyNumberActRound::getLuckyNumber));
}
}

View File

@@ -14,6 +14,7 @@ import com.accompany.business.vo.activity.LuckyNumberActRoundVo;
import com.accompany.common.constant.Constant;
import com.accompany.common.status.BusiStatus;
import com.accompany.common.utils.DateTimeUtil;
import com.accompany.common.utils.RandomUtil;
import com.accompany.core.enumeration.BillObjTypeEnum;
import com.accompany.core.enumeration.PartitionEnum;
import com.accompany.core.exception.ServiceException;
@@ -34,10 +35,7 @@ import org.springframework.util.StringUtils;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.time.*;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.*;
import java.util.stream.Collectors;
@Slf4j
@@ -255,6 +253,81 @@ public class LuckyNumberActService {
return vo;
}
@Transactional(rollbackFor = Exception.class)
public void settlement(String date, Integer partitionId) {
LuckyNumberActRound round = roundService.getOrDefault(date, partitionId);
if (null != round.getLuckyNumber()){
throw new ServiceException(BusiStatus.SERVERBUSY);
}
int luckyNumber = RandomUtil.randomByRange(1, 99);
//todo log
if (!roundService.saveLuckyNumber(date, partitionId, luckyNumber)){
//todo log
throw new ServiceException(BusiStatus.SERVERBUSY);
}
if (BigDecimal.ZERO.compareTo(round.getJackpot()) >= 0){
return;
}
List<LuckyNumberActInputRecord> inputRecordList = playerRecordService.list(Wrappers.<LuckyNumberActInputRecord>lambdaQuery()
.eq(LuckyNumberActInputRecord::getDate, date)
.eq(LuckyNumberActInputRecord::getPartitionId, partitionId)
.eq(LuckyNumberActInputRecord::getLuckyStatus, Constant.status.delete));
Set<Long> unluckyUidSet = inputRecordList.stream().map(LuckyNumberActInputRecord::getUid).collect(Collectors.toSet());
Map<Long, Integer> luckyerMap = new HashMap<>();
for (LuckyNumberActInputRecord record : inputRecordList){
List<Integer> numberList = record.getNumberList();
for (Integer number : numberList){
if (number.equals(luckyNumber)){
luckyerMap.put(record.getUid(), luckyerMap.getOrDefault(record.getUid(), 0) + 1);
//todo log
}
}
}
//修改不幸运儿状态
unluckyUidSet.removeAll(luckyerMap.keySet());
playerRecordService.update(Wrappers.<LuckyNumberActInputRecord>lambdaUpdate()
.set(LuckyNumberActInputRecord::getLuckyStatus, Constant.StatusV2.delete)
.set(LuckyNumberActInputRecord::getUpdateTime, new Date())
.eq(LuckyNumberActInputRecord::getDate, date)
.in(LuckyNumberActInputRecord::getUid, unluckyUidSet)
.eq(LuckyNumberActInputRecord::getPartitionId, partitionId)
.eq(LuckyNumberActInputRecord::getLuckyStatus, Constant.StatusV2.invalid));
if (!CollectionUtils.isEmpty(luckyerMap)){
int totalInputNum = luckyerMap.values().stream().mapToInt(Integer::intValue).sum();
BigDecimal everyOutput = round.getJackpot().divide(BigDecimal.valueOf(totalInputNum), 5, RoundingMode.HALF_DOWN);
Map<Long, BigDecimal> outputMap = luckyerMap.entrySet().stream().collect(Collectors.toMap(Map.Entry::getKey, entry -> {
Integer outputNum = entry.getValue();
return BigDecimal.valueOf(outputNum).multiply(everyOutput).setScale(2, RoundingMode.HALF_DOWN);
}));
//todo log
for (Map.Entry<Long, BigDecimal> entry : outputMap.entrySet()){
boolean success = playerRecordService.update(Wrappers.<LuckyNumberActInputRecord>lambdaUpdate()
.set(LuckyNumberActInputRecord::getOutput, entry.getValue())
.set(LuckyNumberActInputRecord::getLuckyStatus, Constant.StatusV2.valid)
.set(LuckyNumberActInputRecord::getUpdateTime, new Date())
.eq(LuckyNumberActInputRecord::getDate, date)
.eq(LuckyNumberActInputRecord::getUid, entry.getKey())
.eq(LuckyNumberActInputRecord::getPartitionId, partitionId)
.eq(LuckyNumberActInputRecord::getLuckyStatus, Constant.StatusV2.invalid));
//todo log
}
}
//下一轮
String nextRoundDate = DateTimeUtil.convertDate(DateTimeUtil.addDays(DateTimeUtil.convertStrToDate(round.getDate()), 1), DateTimeUtil.DEFAULT_DATE_PATTERN);
roundService.updateJackpot(nextRoundDate, partitionId, round.getJackpot());
}
private LuckyNumberActConfig getConfig() {
String configStr = sysConfService.getSysConfValueById(Constant.SysConfId.LUCKY_NUMBER_ACT_CONFIG);
if (!StringUtils.hasText(configStr)){
@@ -262,5 +335,4 @@ public class LuckyNumberActService {
}
return JSON.parseObject(configStr, LuckyNumberActConfig.class);
}
}

View File

@@ -11,6 +11,8 @@ import com.accompany.common.status.BusiStatus;
import com.accompany.core.base.UidContextHolder;
import com.accompany.core.exception.ServiceException;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
@@ -50,6 +52,9 @@ public class LuckyNumberActController {
}
@ApiOperation(value = "投入")
@ApiImplicitParams({
@ApiImplicitParam(name = "number", value = "数字", required = true)
})
@Authorization
@PostMapping(value = "/input")
public BusiResult<Void> input(Integer number){
@@ -72,6 +77,9 @@ public class LuckyNumberActController {
}
@ApiOperation(value = "领取")
@ApiImplicitParams({
@ApiImplicitParam(name = "date", value = "日期", required = true)
})
@Authorization
@PostMapping(value = "/getJackpot")
public BusiResult<Void> getJackpot(String date){
@@ -85,8 +93,11 @@ public class LuckyNumberActController {
}
@ApiOperation(value = "历史轮次详情")
@ApiImplicitParams({
@ApiImplicitParam(name = "date", value = "日期", required = true)
})
@Authorization
@PostMapping(value = "/getHistoryRoundDetail")
@GetMapping(value = "/getHistoryRoundDetail")
public BusiResult<LuckyNumberActRoundHistoryDetailVo> getHistoryRoundDetail(String date){
if (!StringUtils.hasText(date)){
throw new ServiceException(BusiStatus.PARAMERROR);
@@ -97,4 +108,19 @@ public class LuckyNumberActController {
return BusiResult.success(detailVo);
}
@ApiOperation(value = "结算")
@ApiImplicitParams({
@ApiImplicitParam(name = "date", value = "日期", required = true),
@ApiImplicitParam(name = "partitionId", value = "分区id", required = true)
})
@PostMapping(value = "/settlement")
public BusiResult<Void> settlement(String date, Integer partitionId){
if (!StringUtils.hasText(date) || null == partitionId){
throw new ServiceException(BusiStatus.PARAMERROR);
}
actService.settlement(date, partitionId);
return BusiResult.success();
}
}

View File

@@ -0,0 +1,38 @@
package com.accompany.scheduler.task.activity;
import com.accompany.business.service.activity.LuckyNumberActService;
import com.accompany.common.utils.DateTimeUtil;
import com.accompany.core.enumeration.PartitionEnum;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import java.util.List;
@Component
@Slf4j
public class LuckyNumberActTask {
@Autowired
private LuckyNumberActService service;
@Scheduled(cron = "30 29 20 * * *", zone = "Asia/Manila")
public void settlementEn() {
List<PartitionEnum> partitionEnumList = List.of(PartitionEnum.ENGLISH, PartitionEnum.ENGLISH2);
for (PartitionEnum partitionEnum : partitionEnumList) {
String date = DateTimeUtil.getZonedTodayStr(partitionEnum.getZoneId());
service.settlement(date, partitionEnum.getId());
}
}
@Scheduled(cron = "30 29 20 * * *", zone = "Asia/Riyadh")
public void settlementAr() {
List<PartitionEnum> partitionEnumList = List.of(PartitionEnum.ARAB, PartitionEnum.TURKEY);
for (PartitionEnum partitionEnum: partitionEnumList){
String date = DateTimeUtil.getZonedTodayStr(partitionEnum.getZoneId());
service.settlement(date, partitionEnum.getId());
}
}
}