Merge branch 'feature/mall_product' of http://117.33.142.185:3000/zenghuapei/cyywl_server into feature/mall_product

pull/2/head
TianYu 2023-05-17 17:58:21 +08:00
commit d6e861a106
13 changed files with 310 additions and 128 deletions

View File

@ -0,0 +1,22 @@
package cn.iocoder.yudao.module.shop.response.member;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import java.io.Serializable;
/**
* @Title:MemberGradeResponse
* @Description: TODO
* @author: tangqian
* @date: 2023/5/17 13:45
* @version: V1.0.0
*/
@Data
public class MemberHeadResponse implements Serializable {
private static final long serialVersionUID = 5155396515478444684L;
@Schema(description = "会员等级")
private String grade;
@Schema(description = "会员积分")
private String integral;
}

View File

@ -2,6 +2,7 @@ package cn.iocoder.yudao.module.shop.controller.admin.notify;
import cn.hutool.json.JSONUtil;
import cn.iocoder.yudao.module.shop.service.order.StoreOrderService;
import com.github.binarywang.wxpay.bean.notify.OriginNotifyResponse;
import com.github.binarywang.wxpay.bean.notify.SignatureHeader;
import com.github.binarywang.wxpay.bean.notify.WxPayOrderNotifyV3Result;
@ -31,16 +32,12 @@ import javax.servlet.http.HttpServletResponse;
public class WxPayNotifyController {
@Autowired
private WxPayService wxPayService;
@Autowired
private StoreOrderService storeOrderService;
/**
@ -63,12 +60,9 @@ public class WxPayNotifyController {
//解密后的数据
v3Result = wxPayService.parseOrderNotifyV3Result(jsonData, this.getRequestHeader(request));
WxPayOrderNotifyV3Result.DecryptNotifyResult result = v3Result.getResult();
log.info("支付通知=" + JSONUtil.toJsonPrettyStr(result));
if (StringUtils.equals("SUCCESS",result.getTradeType())) {
log.info("微信支付回调成功");
// 验证相关参数-金额
// 修改订单状态
// 写入
// 验签
Boolean b = storeOrderService.wxPayNotify(result);
if (b) {
response.setStatus(HttpServletResponse.SC_OK);
return "success";
}

View File

@ -16,4 +16,7 @@ public class RechargeGearRespVO extends RechargeGearBaseVO {
@Schema(description = "创建时间", required = true)
private LocalDateTime createTime;
@Schema(description = "该挡位是否已充值1是0否", required = true)
private String isExist;
}

View File

@ -48,5 +48,11 @@ public class TopUpOrderController {
}
@Operation(summary = "申请退款")
@RequestMapping(value = "/memberApplyRefund", method = RequestMethod.POST)
public CommonResult<Boolean> memberApplyRefund(@Valid @RequestBody RefundRequest request){
log.info("memberApplyRefund申请退款===>{}", request);
return CommonResult.success(storeOrderService.memberApplyRefund(request));
}
}

View File

@ -1,12 +1,12 @@
package cn.iocoder.yudao.module.shop.controller.app.member;
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
import cn.iocoder.yudao.framework.security.core.annotations.PreAuthenticated;
import cn.iocoder.yudao.module.shop.controller.admin.recharge.vo.RechargeGearRespVO;
import cn.iocoder.yudao.module.shop.controller.admin.recharge.vo.RechargeOrderRespVO;
import cn.iocoder.yudao.module.shop.convert.recharge.RechargeGearConvert;
import cn.iocoder.yudao.module.shop.convert.recharge.RechargeOrderConvert;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.RechargeGearDO;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.RechargeOrderDO;
import cn.iocoder.yudao.module.shop.response.member.MemberHeadResponse;
import cn.iocoder.yudao.module.shop.service.recharge.RechargeGearService;
import cn.iocoder.yudao.module.shop.service.recharge.RechargeOrderService;
import io.swagger.v3.oas.annotations.Operation;
@ -40,17 +40,26 @@ public class MemberController {
// 会员档次信息列表
@Operation(summary = "会员档次信息")
@RequestMapping(value = "/memberGradeInfo", method = RequestMethod.GET)
@PreAuthenticated
public CommonResult<List<RechargeGearRespVO>> memberGradeInfo() {
List<RechargeGearDO> gradeInfo = rechargeGearService.getGradeInfo();
return CommonResult.success(RechargeGearConvert.INSTANCE.convertList(gradeInfo));
return CommonResult.success(rechargeGearService.getGradeInfo());
}
// 充值列表记录
@Operation(summary = "获取当前登录账号的充值记录")
@RequestMapping(value = "/memberOrderInfo", method = RequestMethod.GET)
@PreAuthenticated
public CommonResult<List<RechargeOrderRespVO>> memberOrderInfo() {
List<RechargeOrderDO> orderDOS = rechargeOrderService.memberOrderInfo();
return CommonResult.success(RechargeOrderConvert.INSTANCE.convertList(orderDOS));
}
@Operation(summary = "会员头部信息")
@RequestMapping(value = "/memberHeadInfo", method = RequestMethod.GET)
@PreAuthenticated
public CommonResult<MemberHeadResponse> memberHeadInfo() {
return CommonResult.success(rechargeOrderService.memberHeadInfo());
}
}

View File

@ -49,7 +49,7 @@ public class PhoneRecordDO extends BaseDO {
/**
*
*/
private BigDecimal rechargeGearId;
private Long rechargeGearId;
/**
*
*/

View File

@ -14,6 +14,7 @@ import cn.iocoder.yudao.module.shop.response.member.InitOrderResponse;
import cn.iocoder.yudao.module.shop.response.order.*;
import cn.iocoder.yudao.module.shop.vo.order.LogisticsResultVo;
import com.baomidou.mybatisplus.extension.service.IService;
import com.github.binarywang.wxpay.bean.notify.WxPayOrderNotifyV3Result;
import com.github.binarywang.wxpay.exception.WxPayException;
import com.github.pagehelper.PageInfo;
@ -398,4 +399,8 @@ public interface StoreOrderService extends IService<StoreOrder> {
Object memberRefund(RefundRequest request, HttpServletRequest servletRequest);
Object refundNotify(HttpServletRequest request, Map<String, String> params);
Boolean wxPayNotify(WxPayOrderNotifyV3Result.DecryptNotifyResult result);
Boolean memberApplyRefund(RefundRequest request);
}

View File

@ -70,6 +70,7 @@ public class StoreOrderRefundServiceImpl extends ServiceImpl<StoreOrderMapper, S
String apiDomain = apiConfigApi.getConfigKey(Constants.CONFIG_KEY_API_URL).toString();
// TODO 微信退款
}

View File

@ -4,6 +4,7 @@ import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.PhoneUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONUtil;
import cn.iocoder.yudao.framework.common.enums.Constants;
import cn.iocoder.yudao.framework.common.exception.ServiceException;
import cn.iocoder.yudao.framework.common.pojo.DateLimitUtilVo;
@ -15,9 +16,11 @@ import cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils;
import cn.iocoder.yudao.module.member.api.user.MemberUserApi;
import cn.iocoder.yudao.module.member.api.user.dto.MemberUserRespDTO;
import cn.iocoder.yudao.module.shop.dal.dataobject.order.StoreOrder;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.PhoneRecordDO;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.RechargeOrderDO;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.RechargeOrderInfoDO;
import cn.iocoder.yudao.module.shop.dal.mysql.order.StoreOrderMapper;
import cn.iocoder.yudao.module.shop.dal.mysql.recharge.PhoneRecordMapper;
import cn.iocoder.yudao.module.shop.dal.mysql.recharge.RechargeOrderInfoMapper;
import cn.iocoder.yudao.module.shop.dal.mysql.recharge.RechargeOrderMapper;
import cn.iocoder.yudao.module.shop.request.member.OrderContentRequest;
@ -48,6 +51,7 @@ import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.IdWorker;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.github.binarywang.wxpay.bean.notify.WxPayOrderNotifyV3Result;
import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
@ -65,6 +69,7 @@ import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.*;
import java.util.stream.Collectors;
@ -115,6 +120,8 @@ public class StoreOrderServiceImpl extends ServiceImpl<StoreOrderMapper, StoreOr
private RechargeOrderMapper rechargeOrderMapper;
@Autowired
private RechargeOrderInfoMapper rechargeOrderInfoMapper;
@Autowired
private PhoneRecordMapper phoneRecordMapper;
@Autowired
private AliPayProperties aliPayProperties;
@ -1148,11 +1155,12 @@ public class StoreOrderServiceImpl extends ServiceImpl<StoreOrderMapper, StoreOr
boolean verifyResult = false;
try {
verifyResult = AlipaySignature.rsaCheckV1(params, aliPayProperties.getAlipayPublicKey(), "UTF-8", "RSA2");
log.debug("支付宝验证签名结果:{}", verifyResult);
} catch (AlipayApiException e) {
e.printStackTrace();
}
if (verifyResult) {
log.info("支付宝支付回调成功");
log.info("ALIPAY====MAP===>{}", params);
String orderId = params.get("out_trade_no");
String amount = params.get("refund_amount");
String total_amount = params.get("total_amount");
@ -1160,18 +1168,59 @@ public class StoreOrderServiceImpl extends ServiceImpl<StoreOrderMapper, StoreOr
log.info("amount:{}", amount);
log.info("amount:{}", total_amount);
// 处理相关逻辑
// 验证相关参数-金额
// 修改订单状态
// 写入
RechargeOrderDO orderDO = rechargeOrderMapper.selectOne(Wrappers.<RechargeOrderDO>lambdaQuery().eq(RechargeOrderDO::getOrderId, orderId));
if (Objects.isNull(orderDO)) {
log.error("订单号错误,未查询到相关信息!入参订单号:{}", orderId);
return "failure";
}
// 验证相关参数-金额
if (new BigDecimal(amount).compareTo(orderDO.getPayPrice()) != 0) {
log.error("支付金额不匹配,订单实际支付金额:{},支付宝入参验证金额:{}", orderDO.getPayPrice(), amount);
return "failure";
}
// 修改订单状态
orderDO.setPaid((byte) 1);
rechargeOrderMapper.updateById(orderDO);
// 写入 充值档位记录表
addPhoneRecord(orderDO, orderId);
log.debug(">>>>>>>>>>>>>>支付宝订单交易成功!订单号:{}<<<<<<<<<<<<<<<<<<<<", orderId);
return "success";
} else {
return "failure";
}
}
public void addPhoneRecord(RechargeOrderDO orderDO, String orderId) {
List<RechargeOrderInfoDO> infoDOS = rechargeOrderInfoMapper.selectList(Wrappers.<RechargeOrderInfoDO>lambdaQuery().eq(RechargeOrderInfoDO::getOrderNo, orderId));
List<PhoneRecordDO> recordDOS = new ArrayList<>();
infoDOS.forEach(info -> {
PhoneRecordDO phoneRecordDO = new PhoneRecordDO();
phoneRecordDO.setUserId(Long.valueOf(orderDO.getUid()));
phoneRecordDO.setRechargeOrderId(Long.valueOf(orderDO.getId()));
phoneRecordDO.setPhone(orderDO.getUserPhone());
phoneRecordDO.setRefundFeeAmount(replace(info.getPrice()));
phoneRecordDO.setRechargeGearId(Long.valueOf(info.getRechargeGearId()));
LocalDateTime localDateTime = LocalDateTime.now();
LocalDateTime newLocalDateTime = localDateTime.plusMonths(12);
phoneRecordDO.setRefundFeeEndDate(newLocalDateTime);
phoneRecordDO.setRefundFeeNumber("12");
recordDOS.add(phoneRecordDO);
});
phoneRecordMapper.insertBatch(recordDOS);
}
public BigDecimal replace(BigDecimal amount) {
if (new BigDecimal("240").compareTo(amount) == 0) {
return new BigDecimal("360");
} else if (new BigDecimal("400").compareTo(amount) == 0) {
return new BigDecimal("600");
} else if (new BigDecimal("640").compareTo(amount) == 0) {
return new BigDecimal("960");
}
return null;
}
@Override
public Object memberRefund(RefundRequest request, HttpServletRequest servletRequest) {
RechargeOrderDO orderDO = rechargeOrderMapper.selectById(request.getOrderId());
@ -1203,15 +1252,11 @@ public class StoreOrderServiceImpl extends ServiceImpl<StoreOrderMapper, StoreOr
}
log.info("支付宝退款回调验证结果{}", isSignatureValid);
if (isSignatureValid) {
log.info("支付宝退款回调成功");
// 验证通过
if ("TRADE_SUCCESS".equals(tradeStatus)) {
// 处理相关逻辑
// 验证相关参数-金额
// 修改订单状态
// 写入
if ("TRADE_SUCCESS".equals(tradeStatus)) {
// 退款成功逻辑
} else {
// 退款失败逻辑
}
@ -1222,6 +1267,38 @@ public class StoreOrderServiceImpl extends ServiceImpl<StoreOrderMapper, StoreOr
}
}
@Override
public Boolean wxPayNotify(WxPayOrderNotifyV3Result.DecryptNotifyResult result) {
log.info("支付通知=" + JSONUtil.toJsonPrettyStr(result));
if (StringUtils.equals("SUCCESS", result.getTradeType())) {
log.info("WXPAY====result===>");
// 验证相关参数-金额
String outTradeNo = result.getOutTradeNo();
// 用户支付金额
Integer payerTotal = result.getAmount().getPayerTotal() / 100;
// 处理相关逻辑
RechargeOrderDO orderDO = rechargeOrderMapper.selectOne(Wrappers.<RechargeOrderDO>lambdaQuery().eq(RechargeOrderDO::getOrderId, outTradeNo));
if (new BigDecimal(payerTotal).compareTo(orderDO.getPayPrice()) != 0) {
log.error("支付金额不匹配,订单实际支付金额:{},微信入参验证金额:{}", orderDO.getPayPrice(), payerTotal);
return Boolean.FALSE;
}
// 修改订单状态
orderDO.setPaid((byte) 1);
rechargeOrderMapper.updateById(orderDO);
// 写入 充值档位记录表
addPhoneRecord(orderDO, outTradeNo);
log.debug(">>>>>>>>>>>>>>微信订单交易成功!订单号:{}<<<<<<<<<<<<<<<<<<<<", outTradeNo);
}
return Boolean.TRUE;
}
@Override
public Boolean memberApplyRefund(RefundRequest request) {
RechargeOrderDO orderDO = rechargeOrderMapper.selectById(request.getOrderId());
orderDO.setRefundStatus((byte) 1);
return rechargeOrderMapper.updateById(orderDO) > 0;
}
private RechargeOrderDO initializeOrder(OrderContentRequest request, String code, MemberUserRespDTO user) {
RechargeOrderDO orderDO = new RechargeOrderDO();

View File

@ -67,5 +67,5 @@ public interface RechargeGearService {
*/
List<RechargeGearDO> getRechargeGearList(RechargeGearExportReqVO exportReqVO);
List<RechargeGearDO> getGradeInfo();
List<RechargeGearRespVO> getGradeInfo();
}

View File

@ -1,11 +1,23 @@
package cn.iocoder.yudao.module.shop.service.recharge;
import cn.iocoder.yudao.framework.security.core.LoginUser;
import cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.RechargeOrderDO;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.RechargeOrderInfoDO;
import cn.iocoder.yudao.module.shop.dal.mysql.recharge.RechargeOrderInfoMapper;
import cn.iocoder.yudao.module.shop.dal.mysql.recharge.RechargeOrderMapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import org.springframework.util.Assert;
import org.springframework.util.CollectionUtils;
import org.springframework.validation.annotation.Validated;
import java.util.*;
import java.util.stream.Collectors;
import cn.iocoder.yudao.module.shop.controller.admin.recharge.vo.*;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.RechargeGearDO;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
@ -27,6 +39,10 @@ public class RechargeGearServiceImpl implements RechargeGearService {
@Resource
private RechargeGearMapper rechargeGearMapper;
@Resource
private RechargeOrderInfoMapper orderInfoMapper;
@Resource
private RechargeOrderMapper orderMapper;
@Override
public String createRechargeGear(RechargeGearCreateReqVO createReqVO) {
@ -81,9 +97,26 @@ public class RechargeGearServiceImpl implements RechargeGearService {
}
@Override
public List<RechargeGearDO> getGradeInfo() {
return rechargeGearMapper.selectList(Wrappers.<RechargeGearDO>lambdaQuery()
public List<RechargeGearRespVO> getGradeInfo() {
LoginUser loginUser = SecurityFrameworkUtils.getLoginUser();
Assert.notNull(loginUser, "登录失效,请重新登录!");
List<RechargeGearDO> rechargeGearDOS = rechargeGearMapper.selectList(Wrappers.<RechargeGearDO>lambdaQuery()
.eq(RechargeGearDO::getDeleted, 0));
List<RechargeGearRespVO> rechargeGearRespVOS = RechargeGearConvert.INSTANCE.convertList(rechargeGearDOS);
RechargeOrderDO orderDO = orderMapper.selectOne(Wrappers.<RechargeOrderDO>lambdaQuery().eq(RechargeOrderDO::getUid, loginUser.getId()).last("LIMIT 1"));
if (Objects.nonNull(orderDO)) {
List<RechargeOrderInfoDO> infoDOS = orderInfoMapper.selectList(Wrappers.<RechargeOrderInfoDO>lambdaQuery().eq(RechargeOrderInfoDO::getOrderNo, orderDO.getOrderId()));
Map<Integer, List<RechargeOrderInfoDO>> collect = infoDOS.stream().collect(Collectors.groupingBy(RechargeOrderInfoDO::getRechargeGearId));
rechargeGearRespVOS.forEach(vo -> {
List<RechargeOrderInfoDO> infoDOS1 = collect.get(vo.getId());
if (!CollectionUtils.isEmpty(infoDOS1)) {
vo.setIsExist("1");
} else {
vo.setIsExist("0");
}
});
}
return rechargeGearRespVOS;
}
}

View File

@ -5,6 +5,7 @@ import javax.validation.*;
import cn.iocoder.yudao.module.shop.controller.admin.recharge.vo.*;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.RechargeOrderDO;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.module.shop.response.member.MemberHeadResponse;
/**
* Service
@ -69,4 +70,5 @@ public interface RechargeOrderService {
List<RechargeOrderDO> memberOrderInfo();
MemberHeadResponse memberHeadInfo();
}

View File

@ -2,14 +2,19 @@ package cn.iocoder.yudao.module.shop.service.recharge;
import cn.iocoder.yudao.framework.security.core.LoginUser;
import cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUtils;
import cn.iocoder.yudao.module.shop.response.member.MemberHeadResponse;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import org.springframework.util.Assert;
import org.springframework.util.CollectionUtils;
import org.springframework.validation.annotation.Validated;
import java.math.BigDecimal;
import java.util.*;
import cn.iocoder.yudao.module.shop.controller.admin.recharge.vo.*;
import cn.iocoder.yudao.module.shop.dal.dataobject.recharge.RechargeOrderDO;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
@ -91,4 +96,29 @@ public class RechargeOrderServiceImpl implements RechargeOrderService {
return rechargeOrderMapper.selectList(Wrappers.<RechargeOrderDO>lambdaQuery().eq(RechargeOrderDO::getUid, loginUser.getId()));
}
@Override
public MemberHeadResponse memberHeadInfo() {
MemberHeadResponse response = new MemberHeadResponse();
LoginUser loginUser = SecurityFrameworkUtils.getLoginUser();
Assert.notNull(loginUser, "登录失效,请重新登录!");
List<RechargeOrderDO> orderDOS = rechargeOrderMapper.selectList(Wrappers.<RechargeOrderDO>lambdaQuery().eq(RechargeOrderDO::getUid, loginUser.getId()));
if (!CollectionUtils.isEmpty(orderDOS)) {
BigDecimal amount = new BigDecimal("0");
for (RechargeOrderDO orderDO : orderDOS) {
amount = amount.add(orderDO.getPayPrice());
}
if (amount.compareTo(new BigDecimal("640")) < 0) {
response.setGrade("普通会员");
response.setIntegral(amount.stripTrailingZeros().toPlainString() + "/" + "640");
} else if (amount.compareTo(new BigDecimal("640")) >= 0) {
response.setGrade("高级会员");
response.setIntegral(amount.stripTrailingZeros().toPlainString() + "/" + "1040");
} else {
response.setGrade("中级会员");
response.setIntegral(amount.stripTrailingZeros().toPlainString() + "/" + "1040");
}
}
return response;
}
}