xiaoyong931011
2022-11-29 efbff9ca8ef6bdf2966f80fe05984ed45b1b8519
20221124
12 files modified
3 files added
316 ■■■■■ changed files
src/main/java/cc/mrbird/febs/dapp/dto/TransferDto.java 4 ●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/entity/DappFundFlowEntity.java 22 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/entity/DappSystemProfit.java 25 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/enumerate/DataDictionaryEnum.java 11 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/enumerate/LevelProfitEnum.java 47 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/mapper/DappSystemProfitDao.java 7 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/service/DappSystemService.java 4 ●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/service/impl/DappMemberServiceImpl.java 2 ●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/service/impl/DappSystemServiceImpl.java 77 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/service/impl/DappWalletServiceImpl.java 33 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/rabbit/QueueConstants.java 4 ●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/rabbit/QueueEnum.java 4 ●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/rabbit/RabbitConfiguration.java 38 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/rabbit/consumer/ChainConsumer.java 16 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/rabbit/producer/ChainProducer.java 22 ●●●●● patch | view | raw | blame | history
src/main/java/cc/mrbird/febs/dapp/dto/TransferDto.java
@@ -13,7 +13,9 @@
@Data
@ApiModel(value = "TransferDto", description = "转账接口参数类")
public class TransferDto {
// 第一次{金额 amount: val, 手续费fee: 0, txHash: '', 1-买入type: 1, 钱包buyType: 2}
// 成功{type: 1, txHash: result.transactionHash, id: res.data, flag: 'success', buyType: 2}
// 失败{type: 1, id: res.data, flag: 'fail', buyType: 2}
    @ApiModelProperty(value = "1-买入 2-卖出", example = "1")
    private Integer type;
src/main/java/cc/mrbird/febs/dapp/entity/DappFundFlowEntity.java
@@ -33,6 +33,15 @@
        this.fee = fee;
    }
//    public DappFundFlowEntity(Long memberId, BigDecimal amount, Integer type, Integer status, BigDecimal fee,Long systemProfitId) {
//        this.memberId = memberId;
//        this.amount = amount;
//        this.type = type;
//        this.status = status;
//        this.fee = fee;
//        this.systemProfitId = systemProfitId;
//    }
    public DappFundFlowEntity(Long memberId, BigDecimal amount, Integer type, Integer status, BigDecimal fee, String fromHash) {
        this.memberId = memberId;
        this.amount = amount;
@@ -42,12 +51,23 @@
        this.fromHash = fromHash;
    }
    public DappFundFlowEntity(Long memberId, BigDecimal amount, Integer type, Integer status, BigDecimal fee, String fromHash,Long systemProfitId) {
        this.memberId = memberId;
        this.amount = amount;
        this.type = type;
        this.status = status;
        this.fee = fee;
        this.fromHash = fromHash;
        this.systemProfitId = systemProfitId;
    }
    private Long memberId;
    private BigDecimal amount;
    /**
     * 类型 1-买入 2-矩阵收益 3-直推收益 4-保险池 5-提现 6-手续费充值 7-手续费扣除 8-结算 9-冻结 10-冻结释放 11-产矿 12-手续费返利
     * 类型 1-加入动能 2-技术方收益 3-直推收益 4-层级收益 5-剩余层级收益 6-手续费充值 7-手续费扣除 8-结算 9-冻结 10-冻结释放 11-产矿 12-手续费返利
     */
    private Integer type;
@@ -68,4 +88,6 @@
    private BigDecimal newestPrice;
    private BigDecimal targetAmount;
    private Long systemProfitId;
}
src/main/java/cc/mrbird/febs/dapp/entity/DappSystemProfit.java
New file
@@ -0,0 +1,25 @@
package cc.mrbird.febs.dapp.entity;
import cc.mrbird.febs.common.entity.BaseEntity;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
import java.math.BigDecimal;
@Data
@TableName("dapp_system_profit")
public class DappSystemProfit extends BaseEntity {
    private Long memberId;
    private BigDecimal amount;
    //1:入列 2:出列
    private Integer state;
    public DappSystemProfit() {}
    public DappSystemProfit(Long memberId, BigDecimal amount) {
        this.memberId = memberId;
        this.amount = amount;
    }
}
src/main/java/cc/mrbird/febs/dapp/enumerate/DataDictionaryEnum.java
@@ -4,6 +4,17 @@
@Getter
public enum DataDictionaryEnum {
    // 会员代理等级
    BIG_BOSS("MEMBER_LEVEL","BIG_BOSS"),
    BOSS("MEMBER_LEVEL","BOSS"),
    AGENT("MEMBER_LEVEL","AGENT"),
    MEMBER("MEMBER_LEVEL","MEMBER"),
    // 层级奖励比率
    LEVEL_PROFIT("SYSTEM_SETTING","LEVEL_PROFIT"),
    // 直推奖励比率
    DIRECT_PROFIT("SYSTEM_SETTING","DIRECT_PROFIT"),
    // 技术方收取BNB数量
    SYSTEM_PROFIT("SYSTEM_SETTING","SYSTEM_PROFIT"),
    // 每日返利的产矿百分比
    REBATE_PERCENT("SYSTEM_SETTING","REBATE_PERCENT"),
    // 分给推荐三人的终身VIP会员手续费
src/main/java/cc/mrbird/febs/dapp/enumerate/LevelProfitEnum.java
New file
@@ -0,0 +1,47 @@
package cc.mrbird.febs.dapp.enumerate;
import lombok.Getter;
import java.math.BigDecimal;
@Getter
public enum LevelProfitEnum {
    /**
     *层级奖励,最多十层
     profit : 层级收益率
     memberCnt : 获取层级收益的最少推荐人数
      */
    YI("YI", 2,1),
    ER("ER", 2,2),
    SAN("SAN", 2,3),
    SI("SI", 2,4),
    WU("WU", 2,5),
    LIU("LIU", 4,6),
    QI("QI", 4,7),
    BA("BA", 4,8),
    JIU("JIU", 4,9),
    SHI("SHI", 4,10)
    ;
    private String type;
    private Integer profit;
    private Integer memberCnt;
    LevelProfitEnum(String type, Integer profit,Integer memberCnt) {
        this.type = type;
        this.profit = profit;
        this.memberCnt = memberCnt;
    }
    public BigDecimal getProfit(int memberCnt) {
        for (LevelProfitEnum value : LevelProfitEnum.values()) {
            if (value.memberCnt == memberCnt) {
                return new BigDecimal(value.profit).multiply(new BigDecimal(0.01)).setScale(BigDecimal.ROUND_DOWN, 2);
            }
        }
        return BigDecimal.ZERO;
    }
}
src/main/java/cc/mrbird/febs/dapp/mapper/DappSystemProfitDao.java
New file
@@ -0,0 +1,7 @@
package cc.mrbird.febs.dapp.mapper;
import cc.mrbird.febs.dapp.entity.DappSystemProfit;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
public interface DappSystemProfitDao extends BaseMapper<DappSystemProfit> {
}
src/main/java/cc/mrbird/febs/dapp/service/DappSystemService.java
@@ -24,4 +24,8 @@
    void resetMatrix();
    void feeDistribute(String data);
    //层级奖励分发消息
    void levelProfit(Long id);
    //计算是否有人出局
    void memberOut(Long id);
}
src/main/java/cc/mrbird/febs/dapp/service/impl/DappMemberServiceImpl.java
@@ -277,7 +277,7 @@
    @Override
    public DappMemberEntity insertMember(String address, String refererId) {
        return insertMember(address, refererId, "BSC", "normal");
        return insertMember(address, refererId, "BSC", DataDictionaryEnum.MEMBER.getCode());
    }
    @Override
src/main/java/cc/mrbird/febs/dapp/service/impl/DappSystemServiceImpl.java
@@ -9,6 +9,7 @@
import cc.mrbird.febs.dapp.dto.SystemDto;
import cc.mrbird.febs.dapp.entity.*;
import cc.mrbird.febs.dapp.enumerate.DataDictionaryEnum;
import cc.mrbird.febs.dapp.enumerate.LevelProfitEnum;
import cc.mrbird.febs.dapp.mapper.*;
import cc.mrbird.febs.dapp.service.DappSystemService;
import cc.mrbird.febs.dapp.service.DappWalletService;
@@ -19,7 +20,9 @@
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.date.DateUnit;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
@@ -47,6 +50,7 @@
    private final DappAchieveMemberTreeDao dappAchieveMemberTreeDao;
    private final DappWalletService dappWalletService;
    private final DataDictionaryCustomMapper dataDictionaryCustomMapper;
    private final DappSystemProfitDao dappSystemProfitDao;
    @Override
@@ -282,4 +286,77 @@
            dappFundFlowDao.insert(profitFlow);
        });
    }
    @Override
    public void levelProfit(Long id) {
        DappSystemProfit dappSystemProfit = dappSystemProfitDao.selectById(id);
        if(ObjectUtil.isEmpty(dappSystemProfit)){
            return;
        }
        Long memberId = dappSystemProfit.getMemberId();
        //获取用户的上级用户信息
        DappMemberEntity dappMemberEntity = dappMemberDao.selectById(memberId);
        if(ObjectUtil.isEmpty(dappMemberEntity)){
            return;
        }
        String refererIds = dappMemberEntity.getRefererIds();
        if(StrUtil.isEmpty(refererIds)){
            return;
        }
        DataDictionaryCustom levelProfitSet = dataDictionaryCustomMapper.selectDicDataByTypeAndCode(DataDictionaryEnum.LEVEL_PROFIT.getType(), DataDictionaryEnum.LEVEL_PROFIT.getCode());
        BigDecimal levelProfit = new BigDecimal(StrUtil.isEmpty(levelProfitSet.getValue()) ? "0.3" : levelProfitSet.getValue());
        //投入金额减去技术方收益
        DataDictionaryCustom systemProfitSet = dataDictionaryCustomMapper.selectDicDataByTypeAndCode(DataDictionaryEnum.SYSTEM_PROFIT.getType(), DataDictionaryEnum.SYSTEM_PROFIT.getCode());
        BigDecimal systemProfit = new BigDecimal(StrUtil.isEmpty(systemProfitSet.getValue()) ? "0.05" : systemProfitSet.getValue());
        BigDecimal amount = dappSystemProfit.getAmount().subtract(systemProfit);
        //层级奖励总奖金
        BigDecimal levelProfitTotal = amount.multiply(levelProfit);
        //实发层级奖励 -- 如果还有剩余给技术方
        BigDecimal systemProfitTotal = BigDecimal.ZERO;
        //返回十层
        List<String> refererIdList = StrUtil.split(refererIds, ',');
        //i:计数层数,同时i也为对应层数应推广的人数,当达到对应的直推人数时,才能获取对应层级奖励
        for(int i = 0;i < 10; i++){
            if(systemProfitTotal.compareTo(levelProfitTotal) < 0){
                String inviteId = refererIdList.get(i);
                //获取每层用户的直推人数,判断能否获得这个层级的层级奖励
                DappMemberEntity refererMember = dappMemberDao.selectMemberInfoByInviteId(inviteId);
                //获取直推用户数量
                QueryWrapper<DappMemberEntity> objectQueryWrapper = new QueryWrapper<>();
                objectQueryWrapper.eq("referer_id",refererMember.getInviteId());
                Integer selectCount = dappMemberDao.selectCount(objectQueryWrapper);
                if(i > selectCount){
                    continue;
                }
                //获取对应层级奖励
                BigDecimal profit = LevelProfitEnum.YI.getProfit(i);
                BigDecimal memberLevelProfit = levelProfitTotal.multiply(profit);
                DappFundFlowEntity fundFlow = new DappFundFlowEntity(refererMember.getId(), memberLevelProfit, 4, 2, BigDecimal.ZERO,null,dappSystemProfit.getId());
                dappFundFlowDao.insert(fundFlow);
                systemProfitTotal = systemProfitTotal.add(memberLevelProfit);
            }
        }
        //如果还有剩余给技术方
        if(levelProfitTotal.compareTo(systemProfitTotal) > 0){
            BigDecimal avaProfit = levelProfitTotal.subtract(systemProfit);
            DappFundFlowEntity fundFlow = new DappFundFlowEntity(memberId, avaProfit, 5, 2, BigDecimal.ZERO,null,dappSystemProfit.getId());
            dappFundFlowDao.insert(fundFlow);
        }
    }
    @Override
    public void memberOut(Long id) {
        //获取当前是第几轮队列
        //判断当前是否符合出局条件
        //符合则出局,轮数+1
    }
    public static void main(String[] args) {
        String refererIds = "1,2,3,4,5," +
                            "6,7,8,9,10," +
                            "11,12,13,14,15";
        List<String> refererIdList = StrUtil.split(refererIds, ',');
        System.out.println(refererIdList);
    }
}
src/main/java/cc/mrbird/febs/dapp/service/impl/DappWalletServiceImpl.java
@@ -23,6 +23,8 @@
import cn.hutool.core.date.DateField;
import cn.hutool.core.date.DateUnit;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
@@ -59,6 +61,7 @@
    private final ChainProducer chainProducer;
    private final DappSystemDao dappSystemDao;
    private final DappSystemProfitDao dappSystemProfitDao;
    @Override
    public WalletInfoVo walletInfo() {
@@ -122,6 +125,11 @@
        return dappAccountMoneyChangeDao.selectInPage(change, page);
    }
    /**
     * // 第一次{amount: val, fee: 0, txHash: '', type: 1, buyType: 2}
     *       // 成功{type: 1, txHash: result.transactionHash, id: res.data, flag: 'success', buyType: 2}
     *       // 失败{type: 1, id: res.data, flag: 'fail', buyType: 2}
     */
    @Override
    public Long transfer(TransferDto transferDto) {
        DappMemberEntity member = LoginUserUtil.getAppUser();
@@ -163,9 +171,34 @@
            }
            if ("success".equals(transferDto.getFlag())) {
                //插入一条会员入列记录,即加入动能队列
                DappSystemProfit dappSystemProfit = new DappSystemProfit(member.getId(), transferDto.getAmount());
                dappSystemProfitDao.insert(dappSystemProfit);
                DappFundFlowEntity flow = dappFundFlowDao.selectById(transferDto.getId());
                flow.setFromHash(transferDto.getTxHash());
                flow.setSystemProfitId(dappSystemProfit.getId());
                dappFundFlowDao.updateById(flow);
                //直接拿走0.05个BNB放入技术方
                DataDictionaryCustom systemProfit = dataDictionaryCustomMapper.selectDicDataByTypeAndCode(DataDictionaryEnum.SYSTEM_PROFIT.getType(), DataDictionaryEnum.SYSTEM_PROFIT.getCode());
                String systemProfitStr = StrUtil.isEmpty(systemProfit.getValue()) ? "0.05" : systemProfit.getValue();
                DappFundFlowEntity systemProfitFlow = new DappFundFlowEntity(member.getId(), new BigDecimal(systemProfitStr), 2, 2, BigDecimal.ZERO, transferDto.getTxHash(),dappSystemProfit.getId());
                dappFundFlowDao.insert(systemProfitFlow);
                //直接返利30%给直接上级
                DappMemberEntity dappMemberEntity = dappMemberDao.selectById(member.getId());
                String refererId = dappMemberEntity.getRefererId();
                DappMemberEntity refererMember = dappMemberDao.selectMemberInfoByInviteId(refererId);
                DataDictionaryCustom directProfitSet = dataDictionaryCustomMapper.selectDicDataByTypeAndCode(DataDictionaryEnum.DIRECT_PROFIT.getType(), DataDictionaryEnum.DIRECT_PROFIT.getCode());
                BigDecimal directProfitStr = new BigDecimal(StrUtil.isEmpty(directProfitSet.getValue()) ? "0.3" : directProfitSet.getValue());
                BigDecimal directProfit = (transferDto.getAmount().subtract(new BigDecimal(systemProfitStr))).multiply(directProfitStr).setScale(BigDecimal.ROUND_DOWN, 2);
                DappFundFlowEntity fundFlow = new DappFundFlowEntity(refererMember.getId(), directProfit, 3, 2, BigDecimal.ZERO, transferDto.getTxHash(),dappSystemProfit.getId());
                dappFundFlowDao.insert(fundFlow);
                //层级奖励30%
                chainProducer.sendLevelProfitMsg(dappSystemProfit.getId());
                //发送一个消息,计算当前是否有人可以出局
            } else {
                DappFundFlowEntity flow = dappFundFlowDao.selectById(transferDto.getId());
                if (flow.getStatus() == 1) {
src/main/java/cc/mrbird/febs/rabbit/QueueConstants.java
@@ -5,6 +5,10 @@
 * @date 2022-05-31
 **/
public class QueueConstants {
    public static final String QUEUE_MEMBER_OUT = "queue_bnb_member_out";
    public static final String QUEUE_LEVEL_PROFIT = "queue_bnb_level_profit_transfer";
    public static final String ONLINE_TRANSFER = "queue_sdm_online_transfer";
    public static final String DISTRIB_PROFIT = "queue_sdm_distrib_profit";
    public static final String USER_BUY_REWARD = "queue_sdm_user_buy_reward";
src/main/java/cc/mrbird/febs/rabbit/QueueEnum.java
@@ -5,6 +5,10 @@
@Getter
public enum QueueEnum {
    //计算是否有人出局
    MEMBER_OUT("exchange_bnb_member_out", "route_key_bnb_member_out", "queue_bnb_member_out"),
    //层级奖励
    LEVEL_PROFIT("exchange_bnb_level_profit_transfer", "route_key_bnb_level_profit_transfer", "queue_bnb_level_profit_transfer"),
    ONLINE_TRANSFER("exchange_sdm_online_transfer", "route_key_sdm_online_transfer", "queue_sdm_online_transfer"),
    DISTRIB_PROFIT("exchange_sdm_distrib_profit", "route_key_sdm_distrib_profit", "queue_sdm_distrib_profit"),
src/main/java/cc/mrbird/febs/rabbit/RabbitConfiguration.java
@@ -101,4 +101,42 @@
        return BindingBuilder.bind(feeDistributeQueue()).to(feeDistributeExchange()).with(QueueEnum.DISTRIB_PROFIT.getRoute());
    }
    // === 手续费分发 end ===
    // === 层级奖励分发 start ===
    @Bean
    public DirectExchange levelProfitExchange() {
        return new DirectExchange(QueueEnum.LEVEL_PROFIT.getExchange());
    }
    @Bean
    public Queue levelProfitQueue() {
        return new Queue(QueueEnum.LEVEL_PROFIT.getQueue());
    }
    @Bean
    public Binding levelProfitBind() {
        return BindingBuilder.bind(levelProfitQueue()).to(levelProfitExchange()).with(QueueEnum.LEVEL_PROFIT.getRoute());
    }
    // === 层级奖励分发 end ===
    // === 计算是否有人出局 start ===
    @Bean
    public DirectExchange memberOutExchange() {
        return new DirectExchange(QueueEnum.MEMBER_OUT.getExchange());
    }
    @Bean
    public Queue memberOutQueue() {
        return new Queue(QueueEnum.MEMBER_OUT.getQueue());
    }
    @Bean
    public Binding memberOutBind() {
        return BindingBuilder.bind(memberOutQueue()).to(memberOutExchange()).with(QueueEnum.MEMBER_OUT.getRoute());
    }
    // === 计算是否有人出局 end ===
}
src/main/java/cc/mrbird/febs/rabbit/consumer/ChainConsumer.java
@@ -44,4 +44,20 @@
    public void feeDistribute(String data) {
        dappSystemService.feeDistribute(data);
    }
    /**层级奖励分发消息
     * @param id
     */
    @RabbitListener(queues = QueueConstants.QUEUE_LEVEL_PROFIT)
    public void levelProfit(Long id) {
        dappSystemService.levelProfit(id);
    }
    /**计算是否有人出局分发消息
     * @param id
     */
    @RabbitListener(queues = QueueConstants.QUEUE_MEMBER_OUT)
    public void memberOut(Long id) {
        dappSystemService.memberOut(id);
    }
}
src/main/java/cc/mrbird/febs/rabbit/producer/ChainProducer.java
@@ -1,6 +1,7 @@
package cc.mrbird.febs.rabbit.producer;
import cc.mrbird.febs.rabbit.QueueEnum;
import cn.hutool.core.date.DateUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.amqp.rabbit.connection.CorrelationData;
import org.springframework.amqp.rabbit.core.RabbitTemplate;
@@ -60,4 +61,25 @@
        CorrelationData correlationData = new CorrelationData(UUID.randomUUID().toString());
        rabbitTemplate.convertAndSend(QueueEnum.DISTRIB_PROFIT.getExchange(), QueueEnum.DISTRIB_PROFIT.getRoute(), id, correlationData);
    }
    /**
     * 层级奖励分发消息
     *
     * 会员ID
     * @param id
     */
    public void sendLevelProfitMsg(Long id) {
        log.info("层级奖励分发消息:{}", id);
        CorrelationData correlationData = new CorrelationData(UUID.randomUUID().toString());
        rabbitTemplate.convertAndSend(QueueEnum.LEVEL_PROFIT.getExchange(), QueueEnum.LEVEL_PROFIT.getRoute(), id, correlationData);
    }
    /**
     * 计算是否有人出局分发消息
     */
    public void sendMemberOutMsg(Long id) {
        log.info("计算是否有人出局:{}", DateUtil.now());
        CorrelationData correlationData = new CorrelationData(UUID.randomUUID().toString());
        rabbitTemplate.convertAndSend(QueueEnum.LEVEL_PROFIT.getExchange(), QueueEnum.LEVEL_PROFIT.getRoute(), id, correlationData);
    }
}