Pu Zhibing
2024-09-26 22a9b4588c8eeefdb9e16fda9125af8c0b846b49
ruoyi-service/ruoyi-order/src/main/java/com/ruoyi/order/service/impl/TChargingOrderServiceImpl.java
@@ -33,6 +33,7 @@
import com.ruoyi.integration.api.vo.GetPlatformStopChargingReply;
import com.ruoyi.order.api.dto.SettlementConfirmAdd;
import com.ruoyi.order.api.feignClient.AccountingStrategyDetailOrderClient;
import com.ruoyi.order.api.feignClient.AccountingStrategyOrderClient;
import com.ruoyi.order.api.feignClient.ChargingOrderAccountingStrategyClient;
import com.ruoyi.order.api.model.*;
import com.ruoyi.order.api.query.ChargingOrderQuery;
@@ -47,11 +48,8 @@
import com.ruoyi.order.service.TChargingOrderService;
import com.ruoyi.order.service.TOrderEvaluateService;
import com.ruoyi.order.service.*;
import com.ruoyi.other.api.domain.TCoupon;
import com.ruoyi.other.api.domain.TGoods;
import com.ruoyi.other.api.domain.*;
import com.ruoyi.order.vo.ChargingOrderListInfoVO;
import com.ruoyi.other.api.domain.TIntegralRule;
import com.ruoyi.other.api.domain.TVip;
import com.ruoyi.other.api.feignClient.*;
import com.ruoyi.payment.api.feignClient.AliPaymentClient;
import com.ruoyi.payment.api.feignClient.WxPaymentClient;
@@ -153,6 +151,9 @@
   @Resource
   private AccountingStrategyDetailOrderClient accountingStrategyDetailOrderClient;
   @Resource
   private AccountingStrategyOrderClient accountingStrategyOrderClient;
   @Resource
   private AccountingStrategyClient accountingStrategyClient;
@@ -183,6 +184,12 @@
   
   @Resource
   private VipClient vipClient;
   @Resource
   private UserTagClient userTagClient;
   @Resource
   private AppUserTagClient appUserTagClient;
   //计数器
   private Map<String, Integer> counter_map = new HashMap<>();
@@ -433,7 +440,28 @@
      chargingOrder.setRechargePaymentStatus(1);
      chargingOrder.setRechargeAmount(addChargingOrder.getPaymentAmount());
      chargingOrder.setAppCouponId(addChargingOrder.getAppUserCouponId());
      if(null != appUser.getVipId()){
      chargingOrder.setVipDiscount(new BigDecimal(10));
      chargingOrder.setVipDiscountAmount(BigDecimal.ZERO);
      Site site = siteClient.getSiteByIds(Arrays.asList(tChargingGun.getSiteId())).getData().get(0);
      Integer accountingStrategyId = tChargingGun.getAccountingStrategyId();
      if(null == accountingStrategyId){
         //查询站点上面的计费策略
         accountingStrategyId = site.getAccountingStrategyId();
      }
      TAccountingStrategy accountingStrategy = accountingStrategyClient.getAccountingStrategyById(accountingStrategyId).getData();
      //直营站点才可以享受会员折扣
      if(null != appUser.getVipId() && 1 == site.getBusinessCategory()){
         TVip vip = vipClient.getInfo(appUser.getVipId()).getData();
         BigDecimal discount = null;
         if(1 == vip.getType()){
            //普通会员折扣使用积分策略上的折扣,且有最高优惠金额
            discount = accountingStrategy.getDiscount();
         }else{
            //内部会员使用会员信息设置的折扣,没有最高优惠金额
            discount = vip.getDiscount();
         }
         GetAppUserVipDetail getAppUserVipDetail = new GetAppUserVipDetail();
         getAppUserVipDetail.setAppUserId(appUser.getId());
         getAppUserVipDetail.setVipId(appUser.getVipId());
@@ -441,24 +469,13 @@
         if(null != vipDetail){
            Integer chargeNum = vipDetail.getChargeNum();
            if(0 > chargeNum){
               chargingOrder.setVipDiscount(vipDetail.getDiscount());
               BigDecimal discountAmount = addChargingOrder.getPaymentAmount().multiply((new BigDecimal(10)
                     .subtract(vipDetail.getDiscount())).divide(new BigDecimal(10))).setScale(4, BigDecimal.ROUND_HALF_EVEN);
               chargingOrder.setVipDiscountAmount(discountAmount);
               chargingOrder.setVipDiscount(discount);
            }
         }
      }
      this.save(chargingOrder);
      //添加订单的计费策略
      Integer accountingStrategyId = tChargingGun.getAccountingStrategyId();
      if(null == accountingStrategyId){
         //查询站点上面的计费策略
         Site site = siteClient.getSiteByIds(Arrays.asList(tChargingGun.getSiteId())).getData().get(0);
         accountingStrategyId = site.getAccountingStrategyId();
      }
      TAccountingStrategy accountingStrategy = accountingStrategyClient.getAccountingStrategyById(accountingStrategyId).getData();
      List<TAccountingStrategyDetail> strategyDetailList = accountingStrategyDetailClient.getListByAccountingStrategyId(accountingStrategyId).getData();
      AccountingStrategyOrder accountingStrategyOrder = new AccountingStrategyOrder();
      BeanUtils.copyProperties(accountingStrategy, accountingStrategyOrder);
@@ -532,42 +549,85 @@
      
      //根据当前充值的金额和计费模板算出充电的金额
      BigDecimal rechargeAmount = chargingOrder.getRechargeAmount();
      //计算充电金额,会员需要将折扣金额加入到充电总金额中
      TChargingGun chargingGun = chargingGunClient.getChargingGunById(chargingOrder.getChargingGunId()).getData();
      AccountingStrategyDetailOrder strategyDetail = accountingStrategyDetailOrderClient.getNowAccountingStrategyDetailOrder(chargingOrder.getId()).getData();
      //总单价
      BigDecimal totalUnitPrice = strategyDetail.getServiceCharge().add(strategyDetail.getElectrovalence());
      //计算能充电的度数
      BigDecimal degrees = rechargeAmount.divide(totalUnitPrice);
      BigDecimal rechargeAmount1 = new BigDecimal(rechargeAmount.toString());
      Long now = System.currentTimeMillis();
      //根据支付金额,获取出使用的计费策略明细
      //计算电费金额和服务费
      BigDecimal serviceCharge = strategyDetail.getServiceCharge().multiply(degrees);
      BigDecimal electrovalence = strategyDetail.getElectrovalence().multiply(degrees);
      //再处理会员折扣
      BigDecimal discount = BigDecimal.ZERO;
      BigDecimal serviceCharge = BigDecimal.ZERO;
      BigDecimal electrovalence = BigDecimal.ZERO;
      BigDecimal discountAmount = BigDecimal.ZERO;
      BigDecimal discount = chargingOrder.getVipDiscount();
      //先根据额定功率计算出每秒充电度数,然后计算出支付金额能充多少度电
      TChargingGun tChargingGun = chargingGunClient.getChargingGunById(chargingOrder.getChargingGunId()).getData();
      BigDecimal s_degrees = tChargingGun.getRatedPower().divide(new BigDecimal(3600));
      TAppUser appUser = appUserClient.getUserById(chargingOrder.getAppUserId()).getData();
      if(null != appUser.getVipId()){
         GetAppUserVipDetail getAppUserVipDetail = new GetAppUserVipDetail();
         getAppUserVipDetail.setAppUserId(chargingOrder.getAppUserId());
         getAppUserVipDetail.setVipId(appUser.getVipId());
         TAppUserVipDetail data = appUserVipDetailClient.getAppUserVipDetail(getAppUserVipDetail).getData();
         if(data.getChargeNum() > 0){
            discount = serviceCharge.multiply(data.getDiscount().divide(new BigDecimal(10)));
            data.setChargeNum(data.getChargeNum() - 1);
            appUserVipDetailClient.updateAppUserVipDetail(data);
      List<AccountingStrategyDetailOrder> list = accountingStrategyDetailOrderClient.getAllAccountingStrategyDetailOrder(chargingOrder.getId()).getData();
      for (AccountingStrategyDetailOrder accountingStrategyDetailOrder : list) {
         AccountingStrategyOrder accountingStrategyOrder = accountingStrategyOrderClient.getAccountingStrategyOrderById(accountingStrategyDetailOrder.getAccountingStrategyOrderId()).getData();
         Integer start = Integer.valueOf(accountingStrategyDetailOrder.getStartTime().replaceAll(":", ""));
         String[] split = accountingStrategyDetailOrder.getEndTime().split(":");
         if(now >= start){
            Calendar calendar = Calendar.getInstance();
            calendar.set(Calendar.HOUR_OF_DAY, Integer.valueOf(split[0]));
            calendar.set(Calendar.MINUTE, Integer.valueOf(split[1]));
            //到此策略结束的秒数
            long m = (calendar.getTimeInMillis() - now) / 1000;
            //每度电的单价
            BigDecimal total_unit = accountingStrategyDetailOrder.getElectrovalence().add(accountingStrategyDetailOrder.getServiceCharge());
            //每秒需要支付的金额
            BigDecimal multiply = s_degrees.multiply(total_unit);
            //计算充值金额能充多长时间的电
            long times = rechargeAmount1.divide(multiply, 0, RoundingMode.DOWN).longValue();
            if(times > m){
               //充电时间跨度两个计费策略,需要继续对下一个策略进行计算
               electrovalence = accountingStrategyDetailOrder.getElectrovalence().multiply(s_degrees).multiply(new BigDecimal(m));
               serviceCharge = accountingStrategyDetailOrder.getServiceCharge().multiply(s_degrees).multiply(new BigDecimal(m));
               discountAmount = discountAmount.add(serviceCharge.multiply((new BigDecimal(10).subtract(discount)).divide(new BigDecimal(10))));
               rechargeAmount1 = rechargeAmount1.subtract(multiply.multiply(new BigDecimal(m)));
            }else{
               electrovalence = accountingStrategyDetailOrder.getElectrovalence().multiply(s_degrees).multiply(new BigDecimal(times));
               serviceCharge = accountingStrategyDetailOrder.getServiceCharge().multiply(s_degrees).multiply(new BigDecimal(times));
               discountAmount = discountAmount.add(serviceCharge.multiply((new BigDecimal(10).subtract(discount)).divide(new BigDecimal(10))));
               break;
            }
         }
      }
      electrovalence = electrovalence.add(discount);
      if(discountAmount.compareTo(BigDecimal.ZERO) >= 0){
         //计算会员最大优惠金额
         if(null != appUser.getVipId()){
            TVip vip = vipClient.getInfo(appUser.getVipId()).getData();
            BigDecimal maximumDeduction = vip.getMaximumDeduction();
            //普通会员有最高优惠限制
            if(vip.getType() == 1 && discountAmount.compareTo(maximumDeduction) > 0){
               discountAmount = maximumDeduction;
            }
            //判断会员是否还有充电优惠次数
            GetAppUserVipDetail getAppUserVipDetail = new GetAppUserVipDetail();
            getAppUserVipDetail.setAppUserId(chargingOrder.getAppUserId());
            getAppUserVipDetail.setVipId(appUser.getVipId());
            TAppUserVipDetail data = appUserVipDetailClient.getAppUserVipDetail(getAppUserVipDetail).getData();
            if(data.getChargeNum() > 0){
               data.setChargeNum(data.getChargeNum() - 1);
               appUserVipDetailClient.updateAppUserVipDetail(data);
               //会员有充电优惠次数,直接将优惠金额加入到充电费用中增加充电时长
               electrovalence = electrovalence.add(discountAmount);
            }
         }
      }
      chargingOrder.setChargeAmount(electrovalence);
      chargingOrder.setVipDiscountAmount(discountAmount);
      this.updateById(chargingOrder);
      TChargingPile chargingPile = chargingPileClient.getChargingPileById(chargingGun.getChargingPileId()).getData();
      TChargingPile chargingPile = chargingPileClient.getChargingPileById(tChargingGun.getChargingPileId()).getData();
      //调用远程启动充电消息
      PlatformStartCharging platformStartCharging = new PlatformStartCharging();
      platformStartCharging.setTransaction_serial_number(chargingOrder.getCode());
      platformStartCharging.setCharging_pile_code(chargingPile.getCode());
      platformStartCharging.setCharging_gun_code(chargingGun.getCode());
      platformStartCharging.setCharging_gun_code(tChargingGun.getCode());
      //使用订单id作为逻辑卡号
      platformStartCharging.setCard_number(chargingOrder.getId().toString());
      platformStartCharging.setAccount_balance(electrovalence);
@@ -586,7 +646,7 @@
            PreChargeCheck preChargeCheck1 = redisService.getCacheObject(key);
            //状态为5的时候,硬件会间隔60秒后再次检测,依然未插枪,则不启动充电
            //因这里是间隔5秒执行检测,所以累计次数在30次以上
            if(failure_cause == 5 && null == counter || counter < 35){
            if(failure_cause == 5 && (null == counter || counter < 35)){
               counter++;
               counter_map.put(code, counter);
               //启动失败
@@ -767,7 +827,65 @@
      chargingOrder.setStatus(4);
      chargingOrder.setEndMode(1);
      this.updateById(chargingOrder);
      //处理用户标签数据
      List<TUserTag> data = userTagClient.getAllUserTag().getData();
      //累计充电次数
      long count1 = this.count(new LambdaQueryWrapper<TChargingOrder>().eq(TChargingOrder::getAppUserId, chargingOrder.getAppUserId())
            .eq(TChargingOrder::getRechargePaymentStatus, 2).isNotNull(TChargingOrder::getPaymentAmount).eq(TChargingOrder::getDelFlag, 0));
      List<TUserTag> userTagList1 = data.stream().filter(s -> s.getStandardCondition() == 1).collect(Collectors.toList());
      int old_times = 0;
      Integer userTagId = null;
      for (TUserTag tUserTag : userTagList1) {
         Integer times = JSON.parseObject(tUserTag.getConditions()).getInteger("times");
         //加上本次充电
         //获取最大值标签
         if((count1 + 1) >= times && old_times < times){
            userTagId = tUserTag.getId();
            old_times = times;
         }
      }
      if(null != userTagId){
         TAppUserTag appUserTag = new TAppUserTag();
         appUserTag.setAppUserId(chargingOrder.getAppUserId());
         appUserTag.setUserTagId(userTagId);
         TAppUserTag data1 = appUserTagClient.getUserTag(appUserTag).getData();
         if(null == data1){
            data1 = new TAppUserTag();
            data1.setAppUserId(chargingOrder.getAppUserId());
            data1.setUserTagId(userTagId);
            data1.setCreateTime(LocalDateTime.now());
            appUserTagClient.addUserTag(data1);
         }
      }
      //充电评率
      List<TUserTag> userTagList2 = data.stream().filter(s -> s.getStandardCondition() == 2).collect(Collectors.toList());
      SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
      for (TUserTag tUserTag : userTagList2) {
         TAppUserTag appUserTag = new TAppUserTag();
         appUserTag.setAppUserId(chargingOrder.getAppUserId());
         appUserTag.setUserTagId(tUserTag.getId());
         TAppUserTag data1 = appUserTagClient.getUserTag(appUserTag).getData();
         if(null == data1){
            Integer day = JSON.parseObject(tUserTag.getConditions()).getInteger("day");
            Integer times = JSON.parseObject(tUserTag.getConditions()).getInteger("times");
            Calendar start = Calendar.getInstance();
            start.set(Calendar.DAY_OF_YEAR, start.get(Calendar.DAY_OF_YEAR) + day);
            count1 = this.count(new LambdaQueryWrapper<TChargingOrder>().eq(TChargingOrder::getAppUserId, chargingOrder.getAppUserId())
                  .eq(TChargingOrder::getRechargePaymentStatus, 2).isNotNull(TChargingOrder::getPaymentAmount)
                  .between(TChargingOrder::getStartTime, sdf.format(start.getTime()), sdf.format(new Date())).eq(TChargingOrder::getDelFlag, 0));
            //加上本次充电
            if(count1 >= times){
               data1 = new TAppUserTag();
               data1.setAppUserId(chargingOrder.getAppUserId());
               data1.setUserTagId(tUserTag.getId());
               data1.setCreateTime(LocalDateTime.now());
               appUserTagClient.addUserTag(data1);
            }
         }
      }
      //异步线程处理停机
      ExecutorService cachedThreadPool = Executors.newFixedThreadPool(1);
      cachedThreadPool.execute(()->{