zxl
2 天以前 4f6bdfb31697377020126710bdbd500a363ba278
定时任务,优惠卷领取状态
3个文件已修改
1个文件已添加
197 ■■■■■ 已修改文件
buyer-api/src/main/java/cn/lili/controller/promotion/CouponBuyerController.java 82 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
framework/src/main/java/cn/lili/modules/promotion/service/CouponService.java 2 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
framework/src/main/java/cn/lili/modules/promotion/serviceimpl/CouponServiceImpl.java 15 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
lmk-job/src/main/java/cn/lili/job/MemberJob.java 98 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
buyer-api/src/main/java/cn/lili/controller/promotion/CouponBuyerController.java
@@ -6,6 +6,7 @@
import cn.lili.common.security.context.UserContext;
import cn.lili.common.vo.PageVO;
import cn.lili.common.vo.ResultMessage;
import cn.lili.modules.promotion.entity.dos.Coupon;
import cn.lili.modules.promotion.entity.dos.MemberCoupon;
import cn.lili.modules.promotion.entity.dto.CouponActivityTrigger;
import cn.lili.modules.promotion.entity.dto.search.CouponSearchParams;
@@ -18,10 +19,13 @@
import cn.lili.modules.promotion.service.CouponService;
import cn.lili.modules.promotion.service.MemberCouponService;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
@@ -86,22 +90,62 @@
    @GetMapping
    @ApiOperation(value = "获取可领取优惠券列表")
    public ResultMessage<IPage<CouponVO>> getCouponList(CouponSearchParams queryParam, PageVO page) {
        System.out.println("------------------------------------");
        System.out.println(queryParam);
        queryParam.setPromotionStatus(PromotionsStatusEnum.START.name());
        queryParam.setGetType(CouponGetEnum.FREE.name());
        IPage<CouponVO> canUseCoupons = couponService.pageVOFindAll(queryParam, page);
        // 查询原始分页数据
        IPage<CouponVO> originalPage = couponService.pageVOFindAll(queryParam, page);
        List<CouponVO> originalRecords = originalPage.getRecords();
        List<CouponVO> list = canUseCoupons.getRecords();
        couponService.getUserCouponsStatus(list);
        //更具用户id
        return ResultUtil.data(canUseCoupons);
//        // 获取用户优惠券状态
//        couponService.getUserCouponsStatus(originalRecords);
        //
        originalRecords.forEach(couponVO -> {
            couponVO.setOwned(Boolean.FALSE);
            // 发行数量为0表示不限制,只检查用户领取限制
            if (couponVO.getPublishNum() == 0) {
                 if(shouldRemoveCoupon(couponVO)){
                     couponVO.setOwned(Boolean.TRUE);
                 }
            } else {
                // 计算剩余数量
                int residueNum = couponVO.getPublishNum() - couponVO.getReceivedNum();
                // 剩余数量为0或用户达到领取限制,都需要删除
                 if(residueNum == 0 || shouldRemoveCoupon(couponVO)){
                     couponVO.setOwned(Boolean.TRUE);
                 }
            }
        });
        return ResultUtil.data(originalPage);
    }
    /**
     * 判断是否需要标记优惠券不可领取
     * 用户领取数量达到限制时返回true
     */
    private boolean shouldRemoveCoupon(CouponVO couponVO) {
        if (couponVO == null || couponVO.getCouponLimitNum() == null) {
            return false;
        }
        Long userCouponCount = couponService.getCouponsCountByIdAndMemberId(couponVO.getId());
        if (userCouponCount == null) {
            return false;
        }
        // 用户领取数量 >= 限制数量时,需要移除
        return userCouponCount >= couponVO.getCouponLimitNum();
    }
    @ApiOperation(value = "获取当前会员的优惠券列表")
    @GetMapping("/getCoupons")
    public ResultMessage<IPage<MemberCoupon>> getCoupons(MemberCouponSearchParams param, PageVO pageVo) {
        System.out.println("------------------------------------");
        System.out.println(param);
        AuthUser currentUser = Objects.requireNonNull(UserContext.getCurrentUser());
        param.setMemberId(currentUser.getId());
@@ -129,8 +173,30 @@
    @GetMapping("/receive/{couponId}")
    public ResultMessage<Object> receiveCoupon(@NotNull(message = "优惠券ID不能为空") @PathVariable("couponId") String couponId) {
        AuthUser currentUser = Objects.requireNonNull(UserContext.getCurrentUser());
        //在这里判断领取
        memberCouponService.receiveBuyerCoupon(couponId, currentUser.getId(), currentUser.getNickName());
        return ResultUtil.success();
        Coupon coupon = couponService.getById(couponId);
        CouponVO couponVO = new CouponVO();
        BeanUtils.copyProperties(coupon,couponVO);
        System.out.println(couponVO);
        couponVO.setOwned(Boolean.FALSE);
        // 发行数量为0表示不限制,只检查用户领取限制
        if (couponVO.getPublishNum() == 0) {
            if(shouldRemoveCoupon(couponVO)){
                couponVO.setOwned(Boolean.TRUE);
            }
        } else {
            // 计算剩余数量
            int residueNum = couponVO.getPublishNum() - couponVO.getReceivedNum();
            // 剩余数量为0或用户达到领取限制,都需要删除
            if(residueNum == 0 || shouldRemoveCoupon(couponVO)){
                couponVO.setOwned(Boolean.TRUE);
            }
        }
        return ResultUtil.data(couponVO);
    }
    @ApiOperation(value = "通过id获取")
framework/src/main/java/cn/lili/modules/promotion/service/CouponService.java
@@ -16,6 +16,8 @@
 */
public interface CouponService extends AbstractPromotionsService<Coupon> {
    Long getCouponsCountByIdAndMemberId(String couponId);
    void getUserCouponsStatus(List<CouponVO> list);
    /**
     * 领取优惠券
framework/src/main/java/cn/lili/modules/promotion/serviceimpl/CouponServiceImpl.java
@@ -91,6 +91,21 @@
    @Autowired
    private MemberCouponMapper memberCouponMapper;
    @Override
    public Long getCouponsCountByIdAndMemberId(String couponId){
        AuthUser currentUser = Objects.requireNonNull(UserContext.getCurrentUser());
        Long count = 0L;
        if (StringUtils.isNotBlank(currentUser.getId())) {
            count = new LambdaQueryChainWrapper<>(memberCouponMapper)
                    .eq(MemberCoupon::getCouponId,couponId)
                    .eq(MemberCoupon::getMemberId,currentUser.getId())
                    .count();
        }
        return count;
    }
    @Override
    public void getUserCouponsStatus(List<CouponVO> list) {
        AuthUser currentUser = Objects.requireNonNull(UserContext.getCurrentUser());
lmk-job/src/main/java/cn/lili/job/MemberJob.java
New file
@@ -0,0 +1,98 @@
package cn.lili.job;
import cn.lili.modules.member.entity.dos.Member;
import cn.lili.modules.member.entity.dos.MemberAddress;
import cn.lili.modules.member.mapper.MemberAddressMapper;
import cn.lili.modules.member.mapper.MemberMapper;
import cn.lili.modules.member.service.MemberService;
import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper;
import com.xxl.job.core.context.XxlJobHelper;
import com.xxl.job.core.handler.annotation.XxlJob;
import lombok.RequiredArgsConstructor;
import org.apache.commons.collections.CollectionUtils;
import org.springframework.stereotype.Component;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
/**
 * lmk-shop-java
 * 会员相关任务
 * @author : zxl
 * @date : 2025-09-04 16:49
 **/
@Component
@RequiredArgsConstructor
public class MemberJob {
    private final MemberMapper memberMapper;
    private final MemberService memberService;
    private final MemberAddressMapper memberAddressMapper;
    /**
     * 每日任务同步用户地址
     *
     * @throws Exception
     */
    @XxlJob("everyDayExecuteJobHandlerAsyncMemberAddress")
    public void everyDayExecuteJobHandlerAsyncMemberAddress() throws Exception {
        XxlJobHelper.log("开始执行每日任务:会员地址同步");
        List<Member> updateList = new ArrayList<>();
        List<Member> list = new LambdaQueryChainWrapper<>(memberMapper)
                // 查询region为空的记录
                .and(wrapper -> wrapper
                        .isNull(Member::getRegion)  // region 为 NULL
                        .or()                       // 或者
                        .eq(Member::getRegion, "")  // region 为空字符串
                )
                .and(wrapper -> wrapper
                        .isNull(Member::getRegionId)  // region_id 为 NULL
                        .or()                         // 或者
                        .eq(Member::getRegionId, "")  // region_id 为空字符串
                )
                .eq(Member::getDeleteFlag,Boolean.FALSE)
                .list();
        if (CollectionUtils.isNotEmpty(list)) {
            List<String> memberIds = list.stream().map(Member::getId).collect(Collectors.toList());
            if (CollectionUtils.isNotEmpty(memberIds)) {
                List<MemberAddress> addresses = new LambdaQueryChainWrapper<>(memberAddressMapper)
                        .in(MemberAddress::getMemberId, memberIds) // 查询指定 memberIds 的地址
                        .eq(MemberAddress::getDeleteFlag, Boolean.FALSE) // 逻辑删除字段,假设 0 表示未删除
                        .orderByDesc(MemberAddress::getIsDefault) // 优先返回默认地址(is_default=1 的排在前面)
                        .orderByDesc(MemberAddress::getCreateTime) // 然后按时间降序排列
                        .list();
                Map<String, MemberAddress> firstAddressByMember = addresses.stream()
                        .collect(Collectors.toMap(
                                MemberAddress::getMemberId,
                                address -> address,
                                (existing, replacement) -> existing // 如果已有该 member 的地址,保留第一个(由于排序,第一个就是优先级最高的)
                        ));
                for (Member member : list) {
                    MemberAddress address = firstAddressByMember.get(member.getId());
                    if (address != null) {
                        member.setRegion(address.getConsigneeAddressPath());
                        member.setRegionId(address.getConsigneeAddressIdPath());
                        updateList.add(member);
                    } else {
                        // 可选:处理无地址的情况(如日志记录、跳过更新等)
                        XxlJobHelper.log("会员{}没有对应的地址记录,不更新region信息", member.getId());
                    }
                }
                System.out.println("打印需要修改的集合--------------------");
                System.out.println(updateList);
                memberService.updateBatchById(list);
            }
        }
        // 修改
        XxlJobHelper.log("执行完成:会员地址同步完成");
    }
}