package com.ylx.massage.service.impl; import cn.hutool.core.bean.BeanUtil; import cn.hutool.core.util.ObjectUtil; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import com.ylx.common.core.domain.model.WxLoginUser; import com.ylx.common.exception.ServiceException; import com.ylx.common.utils.SecurityUtils; import com.ylx.massage.domain.AfterSaleOrder; import com.ylx.massage.domain.ProductOrderInfo; import com.ylx.massage.domain.dto.AfterSaleOrderDTO; import com.ylx.massage.domain.dto.AfterSaleOrderUpdateDTO; import com.ylx.massage.domain.vo.OrderAfterSaleVo; import com.ylx.massage.enums.AfterSaleStatusEnum; import com.ylx.massage.enums.AfterSaleTypeEnum; import com.ylx.massage.enums.ProductOrderStatusEnum; import com.ylx.massage.mapper.AfterSaleOrderMapper; import com.ylx.massage.service.IAfterSaleOrderService; import com.ylx.massage.service.IProductOrderInfoService; import lombok.extern.slf4j.Slf4j; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; import javax.annotation.Resource; import java.time.LocalDateTime; @Service @Slf4j public class AfterSaleOrderServiceImpl extends ServiceImpl implements IAfterSaleOrderService { @Resource private AfterSaleOrderMapper afterSaleOrderMapper; @Resource private IProductOrderInfoService productOrderInfoService; @Override @Transactional(rollbackFor = Exception.class) public void add(AfterSaleOrderDTO dto) { // 1. 获取当前登录用户(公共方法提取) WxLoginUser loginUser = getCurrentWxLoginUser(); // 2. 查询并校验订单(公共方法提取) ProductOrderInfo productOrderInfo = this.productOrderInfoService.getAndCheckOrder(dto.getOrderId(), loginUser.getCOpenid()); // 3. 校验订单状态是否允许售后 Integer orderStatus = productOrderInfo.getOrderStatus(); log.info("订单状态:{}", orderStatus); // 明确不允许的状态 if (orderStatus == 0) { throw new ServiceException("待付款订单请直接取消"); } if (orderStatus == 1) { throw new ServiceException("待发货订单请申请取消"); } if (orderStatus == 4) { throw new ServiceException("售后申请已在处理中"); } if (orderStatus == 11) { throw new ServiceException("已取消订单不支持售后"); } // 只允许 2(待发货)或者3(已收货)发起售后 if (orderStatus != 2 && orderStatus != 3) { throw new ServiceException("当前订单状态不支持发起售后"); } // 4. 添加售后订单 AfterSaleOrder entity = new AfterSaleOrder(); BeanUtil.copyProperties(dto, entity); entity.setOpenId(loginUser.getCOpenid()); entity.setCreateTime(LocalDateTime.now()); entity.setAfterSaleStatus(AfterSaleStatusEnum.WAIT_AUDIT.getCode()); entity.setAfterSaleNo(generateAfterSaleNo(dto.getOrderId())); boolean insertResult = super.save(entity); if (!insertResult) { throw new ServiceException("创建售后订单失败"); } // 5. 更新订单状态 ProductOrderInfo updateInfo = new ProductOrderInfo(); updateInfo.setId(productOrderInfo.getId()); updateInfo.setOrderStatus(ProductOrderStatusEnum.AFTER_SALES.getCode()); updateInfo.setUpdateTime(LocalDateTime.now()); boolean updateResult = this.productOrderInfoService.updateById(updateInfo); if (!updateResult) { throw new ServiceException("订单状态变更失败"); } } @Override public OrderAfterSaleVo getOrderAfterSaleVo(Long orderId) { return this.afterSaleOrderMapper.selectAfterSaleVoByOrderId(orderId); } @Override @Transactional(rollbackFor = Exception.class) public void edit(AfterSaleOrderUpdateDTO dto) { // 1. 校验参数 Long id = dto.getAfterSaleOrderId(); if (ObjectUtil.isNull(id)) { throw new IllegalArgumentException("售后单ID不能为空"); } // 2. 获取“等待用户寄回”的售后单 LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.eq(AfterSaleOrder::getId, id) .eq(AfterSaleOrder::getAfterSaleStatus, AfterSaleStatusEnum.WAITING_USER_RETURN.getCode()); AfterSaleOrder afterSaleOrder = this.afterSaleOrderMapper.selectOne(queryWrapper); if (ObjectUtil.isNull(afterSaleOrder)) { throw new ServiceException("等待用户寄回售后单不存在"); } AfterSaleOrder updateInfo = new AfterSaleOrder(); updateInfo.setId(id); updateInfo.setLogisticsNo(dto.getLogisticsNo()); updateInfo.setUpdateTime(LocalDateTime.now()); updateInfo.setAfterSaleStatus(AfterSaleStatusEnum.WAITING_MERCHANT_RECEIVE.getCode()); boolean updateResult = this.updateById(updateInfo); if (!updateResult) { throw new ServiceException("取消售后单填写物流单号失败"); } } @Override @Transactional(rollbackFor = Exception.class) public void cancel(Long orderId) { // 1. 获取当前登录用户(公共方法提取) WxLoginUser loginUser = getCurrentWxLoginUser(); // 2. 查询并校验订单(公共方法提取) ProductOrderInfo productOrderInfo = this.productOrderInfoService.getAndCheckOrder(orderId, loginUser.getCOpenid()); // 3. 状态校验:必须是 退货中/退款中 才能取消退货 if (!ProductOrderStatusEnum.AFTER_SALES.getCode().equals(productOrderInfo.getOrderStatus())) { throw new ServiceException("订单状态异常,仅售后中状态可取消售后"); } // 4. 取消售后订单(待审核 或 等待用户寄回) LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.eq(AfterSaleOrder::getOrderId, orderId) .eq(AfterSaleOrder::getOpenId, loginUser.getCOpenid()) .in(AfterSaleOrder::getAfterSaleStatus, AfterSaleStatusEnum.WAIT_AUDIT.getCode(), AfterSaleStatusEnum.WAITING_USER_RETURN.getCode()); AfterSaleOrder afterSaleOrder = this.afterSaleOrderMapper.selectOne(queryWrapper); if (ObjectUtil.isNull(afterSaleOrder)) { throw new ServiceException("未找到可取消的售后订单"); } // 更新售后订单状态为已取消 afterSaleOrder.setAfterSaleStatus(AfterSaleStatusEnum.CANCELLED.getCode()); afterSaleOrder.setUpdateTime(LocalDateTime.now()); boolean afterSaleUpdateResult = this.updateById(afterSaleOrder); if (!afterSaleUpdateResult) { throw new ServiceException("取消售后订单失败"); } // 5. 更新订单状态 ProductOrderInfo updateInfo = new ProductOrderInfo(); updateInfo.setId(productOrderInfo.getId()); updateInfo.setOrderStatus(ProductOrderStatusEnum.WAIT_RECEIVE.getCode()); updateInfo.setUpdateTime(LocalDateTime.now()); boolean orderUpdateResult = this.productOrderInfoService.updateById(updateInfo); if (!orderUpdateResult) { throw new ServiceException("订单状态变更失败"); } } @Override @Transactional(rollbackFor = Exception.class) public void editByWechat(AfterSaleOrderUpdateDTO dto) { Long orderId = dto.getOrderId(); if (ObjectUtil.isNull(orderId)) { throw new IllegalArgumentException("订单ID不能为空"); } // 1. 获取当前登录用户(公共方法提取) WxLoginUser loginUser = getCurrentWxLoginUser(); // 2. 查询并校验订单(公共方法提取) this.productOrderInfoService.getAndCheckOrder(orderId, loginUser.getCOpenid()); // 3. 获取“同意退货/换货”的售后单 LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.eq(AfterSaleOrder::getOrderId, orderId) .eq(AfterSaleOrder::getOpenId, loginUser.getCOpenid()) .eq(AfterSaleOrder::getAfterSaleStatus, AfterSaleStatusEnum.WAITING_USER_RETURN.getCode()); AfterSaleOrder afterSaleOrder = this.afterSaleOrderMapper.selectOne(queryWrapper); if (ObjectUtil.isNull(afterSaleOrder)) { throw new ServiceException("等待用户寄回售后单不存在"); } // 4. 更新售后单信息 AfterSaleOrder updateInfo = new AfterSaleOrder(); updateInfo.setId(afterSaleOrder.getId()); updateInfo.setLogisticsNo(dto.getLogisticsNo()); updateInfo.setUpdateTime(LocalDateTime.now()); updateInfo.setAfterSaleStatus(AfterSaleStatusEnum.WAITING_MERCHANT_RECEIVE.getCode()); boolean updateResult = this.updateById(updateInfo); if (!updateResult) { throw new ServiceException("取消售后单填写物流单号失败"); } } @Override @Transactional(rollbackFor = Exception.class) public void agreeReturn(Long orderId) { // 1. 查询并校验订单(公共方法提取) ProductOrderInfo productOrderInfo = this.productOrderInfoService.getAndCheckOrder(orderId, null); // 2. 状态校验:必须是 售后中 才能同意退货 if (!ProductOrderStatusEnum.AFTER_SALES.getCode().equals(productOrderInfo.getOrderStatus())) { throw new ServiceException("订单状态异常,仅售后中状态可同意退货"); } // 3. 判断售后单的状态为退货 LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.eq(AfterSaleOrder::getOrderId, orderId) .eq(AfterSaleOrder::getAfterSaleType, AfterSaleTypeEnum.RETURN_GOODS.getCode()) .eq(AfterSaleOrder::getAfterSaleStatus, AfterSaleStatusEnum.WAIT_AUDIT.getCode()); AfterSaleOrder afterSaleOrder = this.afterSaleOrderMapper.selectOne(queryWrapper); if (ObjectUtil.isNull(afterSaleOrder)) { throw new ServiceException("未找到待审核的退货的售后单"); } // 4. 更新售后订单状态为等待用户寄回 afterSaleOrder.setAfterSaleStatus(AfterSaleStatusEnum.WAITING_USER_RETURN.getCode()); afterSaleOrder.setUpdateTime(LocalDateTime.now()); boolean afterSaleUpdateResult = this.updateById(afterSaleOrder); if (!afterSaleUpdateResult) { throw new ServiceException("更新售后单失败"); } } @Override @Transactional(rollbackFor = Exception.class) public void agreeExchange(Long orderId) { // 1. 查询并校验订单(公共方法提取) ProductOrderInfo productOrderInfo = this.productOrderInfoService.getAndCheckOrder(orderId, null); // 2. 状态校验:必须是 售后中 才能同意退货 if (!ProductOrderStatusEnum.AFTER_SALES.getCode().equals(productOrderInfo.getOrderStatus())) { throw new ServiceException("订单状态异常,仅售后中状态可同意换货"); } // 3. 判断售后单的状态为换货 LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.eq(AfterSaleOrder::getOrderId, orderId) .eq(AfterSaleOrder::getAfterSaleType, AfterSaleTypeEnum.EXCHANGE_GOODS.getCode()) .eq(AfterSaleOrder::getAfterSaleStatus, AfterSaleStatusEnum.WAIT_AUDIT.getCode()); AfterSaleOrder afterSaleOrder = this.afterSaleOrderMapper.selectOne(queryWrapper); if (ObjectUtil.isNull(afterSaleOrder)) { throw new ServiceException("未找到待审核的换货的售后单"); } // 4. 更新售后订单状态为等待用户寄回 afterSaleOrder.setAfterSaleStatus(AfterSaleStatusEnum.WAITING_USER_RETURN.getCode()); afterSaleOrder.setUpdateTime(LocalDateTime.now()); boolean afterSaleUpdateResult = this.updateById(afterSaleOrder); if (!afterSaleUpdateResult) { throw new ServiceException("更新售后单失败"); } } @Override @Transactional(rollbackFor = Exception.class) public void agreeRefund(Long orderId) { // 1. 查询并校验订单(公共方法提取) ProductOrderInfo productOrderInfo = this.productOrderInfoService.getAndCheckOrder(orderId, null); // 2. 状态校验:必须是 售后中 才能确认收货 if (!ProductOrderStatusEnum.AFTER_SALES.getCode().equals(productOrderInfo.getOrderStatus())) { throw new ServiceException("订单状态异常,仅售后中状态可确认收货"); } // 3. 获取等待商家收货的售后单 LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.eq(AfterSaleOrder::getOrderId, orderId) .in(AfterSaleOrder::getAfterSaleStatus, AfterSaleStatusEnum.WAIT_AUDIT.getCode(), AfterSaleStatusEnum.WAITING_MERCHANT_RECEIVE.getCode()); AfterSaleOrder afterSaleOrder = this.afterSaleOrderMapper.selectOne(queryWrapper); if (ObjectUtil.isNull(afterSaleOrder)) { throw new ServiceException("未找到可审核的售后单"); } AfterSaleTypeEnum typeEnum = AfterSaleTypeEnum.valueOf(afterSaleOrder.getAfterSaleType()); AfterSaleStatusEnum statusEnum = AfterSaleStatusEnum.valueOf(afterSaleOrder.getAfterSaleStatus()); switch (typeEnum) { case NOT_RECEIVED: // ====================== 未收到货 → 仅退款 ====================== if (statusEnum != AfterSaleStatusEnum.WAIT_AUDIT) { throw new ServiceException("仅退款单状态异常,无法审核"); } break; case RETURN_GOODS: // ====================== 已收到货 → 退货退款 ====================== if (statusEnum != AfterSaleStatusEnum.WAITING_MERCHANT_RECEIVE) { throw new ServiceException("退货单需用户寄回、商家收货后才能审核退款"); } break; default: throw new ServiceException("不支持的售后类型"); } // 4. 判断售后单的售后类型 if (ObjectUtil.notEqual(AfterSaleTypeEnum.RETURN_GOODS.getCode(), afterSaleOrder.getAfterSaleType())) { throw new ServiceException("售后单类型异常,仅退货的售后单可退货"); } // TODO 5.退款 // 6. 更新售后单数据 afterSaleOrder.setAfterSaleStatus(AfterSaleStatusEnum.REFUND_COMPLETED.getCode()); afterSaleOrder.setUpdateTime(LocalDateTime.now()); boolean afterSaleUpdateResult = this.updateById(afterSaleOrder); if (!afterSaleUpdateResult) { throw new ServiceException("更新售后单失败"); } // TODO 7.更新库存信息 } @Override @Transactional(rollbackFor = Exception.class) public void confirmReceive(Long orderId) { // 1. 查询并校验订单(公共方法提取) ProductOrderInfo productOrderInfo = this.productOrderInfoService.getAndCheckOrder(orderId, null); // 2. 状态校验:必须是 售后中 才能确认收货 if (!ProductOrderStatusEnum.AFTER_SALES.getCode().equals(productOrderInfo.getOrderStatus())) { throw new ServiceException("订单状态异常,仅售后中状态可确认收货"); } // 3. 获取等待商家收货的售后单 LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.eq(AfterSaleOrder::getOrderId, orderId) .eq(AfterSaleOrder::getAfterSaleStatus, AfterSaleStatusEnum.WAITING_MERCHANT_RECEIVE.getCode()); AfterSaleOrder afterSaleOrder = this.afterSaleOrderMapper.selectOne(queryWrapper); if (ObjectUtil.isNull(afterSaleOrder)) { throw new ServiceException("未找到等待商家收货的售后单"); } // 4. 判断售后单的售后类型 if (ObjectUtil.notEqual(AfterSaleTypeEnum.EXCHANGE_GOODS.getCode(), afterSaleOrder.getAfterSaleType())) { throw new ServiceException("售后单类型异常,仅换货的售后单可换货"); } // 5. 更新售后单数据 afterSaleOrder.setAfterSaleStatus(AfterSaleStatusEnum.WAITING_MERCHANT_SHIP.getCode()); afterSaleOrder.setUpdateTime(LocalDateTime.now()); boolean afterSaleUpdateResult = this.updateById(afterSaleOrder); if (!afterSaleUpdateResult) { throw new ServiceException("更新售后单失败"); } } private WxLoginUser getCurrentWxLoginUser() { WxLoginUser loginUser = SecurityUtils.getWxLoginUser(); if (ObjectUtil.isNull(loginUser)) { throw new ServiceException("用户未登录或登录已过期"); } return loginUser; } /** * 生成售后单号 * @param orderId 订单ID * @return String 售后单号 */ private String generateAfterSaleNo(Long orderId) { return "AFTERSALE" + orderId + System.currentTimeMillis(); } }