xuhy
2025-08-25 0ef46975993c06e780ec4981d7535167673aa51d
ruoyi-service/ruoyi-other/src/main/java/com/ruoyi/other/controller/ShopWithdrawController.java
@@ -1,13 +1,12 @@
package com.ruoyi.other.controller;
import com.alibaba.fastjson2.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.ruoyi.account.api.feignClient.AppUserClient;
import com.ruoyi.account.api.model.AppUser;
import com.ruoyi.common.core.domain.R;
import com.ruoyi.common.core.exception.ServiceException;
import com.ruoyi.common.core.utils.StringUtils;
@@ -16,29 +15,32 @@
import com.ruoyi.other.api.domain.Shop;
import com.ruoyi.other.api.domain.ShopBalanceStatement;
import com.ruoyi.other.api.domain.ShopWithdraw;
import com.ruoyi.other.mapper.ShopWithdrawMapper;
import com.ruoyi.other.service.ShopBalanceStatementService;
import com.ruoyi.other.service.ShopService;
import com.ruoyi.other.service.ShopWithdrawService;
import com.ruoyi.other.util.payment.TransferUtil;
import com.ruoyi.other.util.payment.model.AccountBalanceQueryResult;
import com.ruoyi.other.util.payment.model.SinglePay;
import com.ruoyi.other.util.payment.model.SinglePayCallbackResult;
import com.ruoyi.other.util.payment.model.SinglePayResult;
import com.ruoyi.other.util.BankCode;
import com.ruoyi.other.util.withdraw.HttpUtilWithdraw;
import com.ruoyi.other.util.pay.HttpRequester;
import com.ruoyi.other.util.pay.HttpRespons;
import com.ruoyi.other.util.payment.wx.WechatPayService;
import com.ruoyi.other.util.withdraw.WithdrawCallBackDTO;
import com.ruoyi.system.api.domain.SysUser;
import com.ruoyi.system.api.feignClient.SysUserClient;
import com.ruoyi.system.api.model.LoginUser;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.CollectionUtils;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import java.io.IOException;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Optional;
import java.util.*;
import java.util.stream.Collectors;
/**
@@ -69,6 +71,11 @@
    @Resource
    private SysUserClient sysUserClient;
    @Autowired
    private ShopWithdrawMapper shopWithdrawMapper;
    @Autowired
    private WechatPayService wechatPayService;
    @GetMapping("/getShopById")
@@ -119,22 +126,25 @@
                                           @ApiParam("手机号") String phone,
                                           @ApiParam("审核状态(0=待审核,1=审核通过,2=审核失败)")Integer auditStatus) {
        //模糊查询手机号
        List<Long> collect=null;
        List<Integer> shopIds=new ArrayList<>();
        if (StringUtils.isNotEmpty(phone)) {
            List<AppUser> data = appUserClient.getAppUserByPhoneNoFilter(phone).getData();
            collect = data.stream().map(AppUser::getId).collect(Collectors.toList());
            if (CollectionUtils.isEmpty(collect)) {
            QueryWrapper<Shop> queryWrapper=new QueryWrapper<>();
            queryWrapper.like(StringUtils.isNotEmpty(phone),"phone", phone);
           shopIds=shopService.list(queryWrapper).stream().map(Shop::getId).collect(Collectors.toList());
            if (CollectionUtils.isEmpty(shopIds)) {
                return R.ok(new PageInfo<>());
            }
        }
        if (shopId!=null && !shopIds.contains(shopId)){
            shopIds.add(shopId);
        }
        Page<ShopWithdraw> page = shopWithdrawService.page(Page.of(pageNum, pageSize), new LambdaQueryWrapper<ShopWithdraw>()
                        .eq(shopId!=null,ShopWithdraw::getShopId,shopId)
                        .eq(auditStatus!=null,ShopWithdraw::getAuditStatus,auditStatus)
                        .in(collect!=null,ShopWithdraw::getCreateUserId,collect)
                        .orderByDesc(ShopWithdraw::getCreateTime)
                );
        PageInfo<ShopWithdraw> page=new PageInfo<>(pageNum,pageSize);
        List<ShopWithdraw> list =shopWithdrawMapper.page(page,shopIds,auditStatus);
        list.forEach(x->{
            x.setIdStr(x.getId().toString());
        });
        page.setRecords(list);
        return R.ok(page);
    }
@@ -195,6 +205,7 @@
    }
    private void baseWithdrawalApplication(BigDecimal money, Long userId, Integer shopId) {
        money=money.setScale(2, BigDecimal.ROUND_HALF_DOWN);
        Shop shop = shopService.getById(shopId);
        if (money.compareTo(BigDecimal.ZERO)==0){
            throw new ServiceException("提现金额必须大于零");
@@ -224,10 +235,10 @@
        //扣除账户余额及添加变动明细
        BigDecimal balance = shop.getBalance();//余额
        BigDecimal canWithdrawMoney = shop.getCanWithdrawMoney();//可提现金额
        BigDecimal withdrawMoney = shop.getWithdrawMoney();//审核中金额
        BigDecimal withdrawAuditMoney = shop.getWithdrawAuditMoney();//审核中金额
        shop.setBalance(balance.subtract(money).setScale(2, RoundingMode.HALF_EVEN));//余额减少
        shop.setCanWithdrawMoney(canWithdrawMoney.subtract(money).setScale(2, RoundingMode.HALF_EVEN));//可提现金额减少
        shop.setWithdrawAuditMoney(withdrawMoney.add(money).setScale(2, RoundingMode.HALF_EVEN));//审核中金额增加
        shop.setWithdrawAuditMoney(withdrawAuditMoney.add(money).setScale(2, RoundingMode.HALF_EVEN));//审核中金额增加
        shopService.updateById(shop);
        //添加余额变动明细
        ShopBalanceStatement shopBalanceStatement = new ShopBalanceStatement();
@@ -249,7 +260,7 @@
     */
    @PostMapping("/audit")
    @ApiOperation("提现审核")
    public R<Void> audit(@RequestBody ShopWithdraw shopWithdraw) {
    public R<Void> audit(@RequestBody ShopWithdraw shopWithdraw) throws IOException {
        LoginUser loginUser = tokenService.getLoginUser();
        ShopWithdraw shopWithdraw1 = shopWithdrawService.getById(shopWithdraw.getId());
@@ -259,33 +270,34 @@
        Shop shop = shopService.getById(shopWithdraw1.getShopId());
        BigDecimal money = shopWithdraw1.getMoney();
        if(1 == shopWithdraw.getAuditStatus()){
            //通过
            //先检查账户余额是否充足
            AccountBalanceQueryResult accountBalanceQueryResult = TransferUtil.accountBalanceQuery();
            if(null == accountBalanceQueryResult){
                return R.fail("查询账户余额出错");
            // 打款
            String url = "https://ccdcapi.alipay.com/validateAndCacheCardInfo.json?_input_charset=utf-8&" +
                    "cardNo="+shopWithdraw1.getReceiverAccountNoEnc()+"&cardBinCheck=true";
            HashMap<String, String> hashMap = new HashMap<>();
            HttpRequester hr = new HttpRequester();
            HttpRespons HP = hr.sendPost(url, hashMap);
            System.out.println("接收返回参数:" + HP.getContent());
            com.alibaba.fastjson.JSONObject resPay = com.alibaba.fastjson.JSONObject.parseObject(HP.getContent());
            System.err.println(resPay);
            if (resPay.getString("validated")==null){
                System.err.println("不合法的银行卡号");
            }
            Double useAbleSettAmount = accountBalanceQueryResult.getUseAbleSettAmount();
            if(useAbleSettAmount < (shopWithdraw1.getMoney().doubleValue() + 1)){
                return R.fail("账户可用余额不足,请先补充账户余额");
            String bankCode = resPay.getString("bank");
            String bankName = BankCode.getBankNameByCode(bankCode); // 返回ABC枚举实例
            System.err.println(bankName);
            String withdraw = HttpUtilWithdraw.withdraw(shopWithdraw1, bankName);
            if (!withdraw.equals("success")){
                return R.fail("打款失败,原因:"+withdraw);
            }
            //银行卡转账
            SinglePay singlePay = new SinglePay();
            singlePay.setTradeMerchantNo(TransferUtil.sysTradeMerchantNo);
            singlePay.setMerchantOrderNo(shopWithdraw1.getId().toString());
            singlePay.setReceiverAccountNoEnc(shop.getReceiverAccountNoEnc());
            singlePay.setReceiverNameEnc(shop.getReceiverNameEnc());
            singlePay.setReceiverAccountType(shop.getReceiverAccountType());
            singlePay.setReceiverBankChannelNo(shop.getReceiverBankChannelNo());
            singlePay.setPaidAmount(shopWithdraw1.getMoney().doubleValue());
            singlePay.setPaidDesc("账户余额提现");
            singlePay.setPaidUse("208");
            singlePay.setCallbackUrl("/other/shop-withdraw/withdrawalCallback");
            SinglePayResult singlePayResult = TransferUtil.singlePay(singlePay);
            if(null == singlePayResult){
                return R.fail("转账失败");
            }
            shopWithdraw1.setStatus(1);
            shopWithdraw1.setStatus(2);
            shopWithdraw1.setArrivalTime(LocalDateTime.now());
            shopWithdrawService.updateById(shopWithdraw);
            //更新店铺审核中的金额,和提现金额
            shop.setWithdrawAuditMoney(shop.getWithdrawAuditMoney().subtract(shopWithdraw1.getMoney()));//审核中金额
            shop.setWithdrawMoney(shop.getWithdrawMoney().add(shopWithdraw1.getMoney()));//提现金额
            shopService.updateById(shop);
        }
        if(2 == shopWithdraw.getAuditStatus()){
            //审核不通过
@@ -301,7 +313,7 @@
            //添加门店变动明细
            ShopBalanceStatement shopBalanceStatement = new ShopBalanceStatement();
            shopBalanceStatement.setShopId(shop.getId());
            shopBalanceStatement.setType(4);
            shopBalanceStatement.setType(7);
            shopBalanceStatement.setHistoricalBalance(balance);
            shopBalanceStatement.setVariableAmount(money);
            shopBalanceStatement.setBalance(shop.getBalance());
@@ -320,23 +332,35 @@
        return R.ok();
    }
    /**
     * 提现审核通过后转账回调通知
     * @param singlePayCallbackResult
     */
    @ResponseBody
    @PostMapping("/withdrawalCallback")
    public Object withdrawalCallback(@RequestBody SinglePayCallbackResult singlePayCallbackResult){
    public Object withdrawalCallback(@RequestBody WithdrawCallBackDTO singlePayCallbackResult){
        String sign = singlePayCallbackResult.getSign();
        String orderCode = singlePayCallbackResult.getOrderCode();
        String tradeNo = singlePayCallbackResult.getTradeNo();
        BigDecimal money = singlePayCallbackResult.getMoney();
        Integer status = singlePayCallbackResult.getStatus();
        String merchantOrderNo = singlePayCallbackResult.getMerchantOrderNo();
        ShopWithdraw shopWithdraw = shopWithdrawService.getById(merchantOrderNo);
        if(203 == status || 205 == status){
        LocalDateTime time = singlePayCallbackResult.getTime();
        String message = singlePayCallbackResult.getMessage();
        ShopWithdraw shopWithdraw = shopWithdrawService.lambdaQuery().eq(ShopWithdraw::getCode, orderCode).one();
        if (shopWithdraw == null){
            return R.ok();
        }
        if (shopWithdraw.getStatus()==2 || 3 == shopWithdraw.getStatus()){
            return R.ok();
        }
        if(1 == status && Objects.equals(money, shopWithdraw.getMoney())){
            //到账
            if(1 == shopWithdraw.getStatus()){
                shopWithdraw.setStatus(2);
                shopWithdraw.setArrivalTime(LocalDateTime.now());
                shopWithdraw.setOrderNumber(tradeNo);
                shopWithdrawService.updateById(shopWithdraw);
            }
            //更新店铺审核中的金额,和提现金额
@@ -345,27 +369,25 @@
            shop.setWithdrawMoney(shop.getWithdrawMoney().add(shopWithdraw.getMoney()));//提现金额
            shopService.updateById(shop);
            JSONObject jsonObject = new JSONObject();
            jsonObject.put("statusCode", 2001);
            return jsonObject;
        }else{
            return R.ok();
        }else if (4 == status){
            //回退金额和添加变动明细
            BigDecimal money = shopWithdraw.getMoney().setScale(2, RoundingMode.HALF_EVEN);
            BigDecimal withdrawMoney = shopWithdraw.getMoney().setScale(2, RoundingMode.HALF_EVEN);
            Shop shop = shopService.getById(shopWithdraw.getShopId());
            BigDecimal balance = shop.getBalance();
            BigDecimal canWithdrawMoney = shop.getCanWithdrawMoney();
            BigDecimal withdrawAuditMoney = shop.getWithdrawAuditMoney();
            shop.setBalance(balance.add(money).setScale(2, RoundingMode.HALF_EVEN));
            shop.setCanWithdrawMoney(canWithdrawMoney.add(money).setScale(2, RoundingMode.HALF_EVEN));
            shop.setBalance(balance.add(withdrawMoney).setScale(2, RoundingMode.HALF_EVEN));
            shop.setCanWithdrawMoney(canWithdrawMoney.add(withdrawMoney).setScale(2, RoundingMode.HALF_EVEN));
            //审核中的金额减少
            shop.setWithdrawAuditMoney(withdrawAuditMoney.subtract(money).setScale(2, RoundingMode.HALF_EVEN));
            shop.setWithdrawAuditMoney(withdrawAuditMoney.subtract(withdrawMoney).setScale(2, RoundingMode.HALF_EVEN));
            shopService.updateById(shop);
            //添加门店变动明细
            ShopBalanceStatement shopBalanceStatement = new ShopBalanceStatement();
            shopBalanceStatement.setShopId(shop.getId());
            shopBalanceStatement.setType(4);
            shopBalanceStatement.setType(7);
            shopBalanceStatement.setHistoricalBalance(balance);
            shopBalanceStatement.setVariableAmount(money);
            shopBalanceStatement.setVariableAmount(withdrawMoney);
            shopBalanceStatement.setBalance(shop.getBalance());
            shopBalanceStatement.setCreateUserId(shopWithdraw.getAuditUserId());
            shopBalanceStatement.setCreateTime(LocalDateTime.now());
@@ -374,13 +396,12 @@
            shopWithdraw.setStatus(3);
            shopWithdraw.setRemark(singlePayCallbackResult.getErrorCodeDesc());
            shopWithdraw.setRemark(singlePayCallbackResult.getMessage());
            shopWithdrawService.updateById(shopWithdraw);
            JSONObject jsonObject = new JSONObject();
            jsonObject.put("statusCode", 2001);
            return jsonObject;
            return R.ok();
        }
        return R.ok();
    }
}