You've already forked FrameTour-BE
feat(pricing): 增加景区优惠券统计功能并优化优惠券使用逻辑
- 新增景区优惠券统计接口和相关查询方法 - 为优惠券配置和使用记录添加景区ID字段 - 实现优惠券使用时的景区限制检查 - 优化优惠券适用性的判断逻辑,增加对景区和商品类型的检查
This commit is contained in:
@@ -85,11 +85,12 @@ public class CouponManagementController {
|
|||||||
@RequestParam(defaultValue = "1") Integer pageNum,
|
@RequestParam(defaultValue = "1") Integer pageNum,
|
||||||
@RequestParam(defaultValue = "10") Integer pageSize,
|
@RequestParam(defaultValue = "10") Integer pageSize,
|
||||||
@RequestParam(required = false) Boolean isActive,
|
@RequestParam(required = false) Boolean isActive,
|
||||||
@RequestParam(required = false) String couponName) {
|
@RequestParam(required = false) String couponName,
|
||||||
log.info("分页查询优惠券配置: pageNum={}, pageSize={}, isActive={}, couponName={}",
|
@RequestParam(required = false) String scenicId) {
|
||||||
pageNum, pageSize, isActive, couponName);
|
log.info("分页查询优惠券配置: pageNum={}, pageSize={}, isActive={}, couponName={}, scenicId={}",
|
||||||
|
pageNum, pageSize, isActive, couponName, scenicId);
|
||||||
PageInfo<PriceCouponConfig> pageInfo = couponManagementService.getCouponConfigsPage(
|
PageInfo<PriceCouponConfig> pageInfo = couponManagementService.getCouponConfigsPage(
|
||||||
pageNum, pageSize, isActive, couponName);
|
pageNum, pageSize, isActive, couponName, scenicId);
|
||||||
return ApiResponse.success(pageInfo);
|
return ApiResponse.success(pageInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -136,11 +137,12 @@ public class CouponManagementController {
|
|||||||
@RequestParam(required = false) Long couponId,
|
@RequestParam(required = false) Long couponId,
|
||||||
@RequestParam(required = false) CouponStatus status,
|
@RequestParam(required = false) CouponStatus status,
|
||||||
@RequestParam(required = false) String startTime,
|
@RequestParam(required = false) String startTime,
|
||||||
@RequestParam(required = false) String endTime) {
|
@RequestParam(required = false) String endTime,
|
||||||
log.info("分页查询优惠券领取记录: pageNum={}, pageSize={}, userId={}, couponId={}, status={}, startTime={}, endTime={}",
|
@RequestParam(required = false) String scenicId) {
|
||||||
pageNum, pageSize, userId, couponId, status, startTime, endTime);
|
log.info("分页查询优惠券领取记录: pageNum={}, pageSize={}, userId={}, couponId={}, status={}, startTime={}, endTime={}, scenicId={}",
|
||||||
|
pageNum, pageSize, userId, couponId, status, startTime, endTime, scenicId);
|
||||||
PageInfo<PriceCouponClaimRecord> pageInfo = couponManagementService.getClaimRecordsPage(
|
PageInfo<PriceCouponClaimRecord> pageInfo = couponManagementService.getClaimRecordsPage(
|
||||||
pageNum, pageSize, userId, couponId, status, startTime, endTime);
|
pageNum, pageSize, userId, couponId, status, startTime, endTime, scenicId);
|
||||||
return ApiResponse.success(pageInfo);
|
return ApiResponse.success(pageInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -202,9 +204,20 @@ public class CouponManagementController {
|
|||||||
@GetMapping("/stats/period")
|
@GetMapping("/stats/period")
|
||||||
public ApiResponse<Map<String, Object>> getPeriodStats(
|
public ApiResponse<Map<String, Object>> getPeriodStats(
|
||||||
@RequestParam String startDate,
|
@RequestParam String startDate,
|
||||||
@RequestParam String endDate) {
|
@RequestParam String endDate,
|
||||||
log.info("查询时间范围统计: startDate={}, endDate={}", startDate, endDate);
|
@RequestParam(required = false) String scenicId) {
|
||||||
Map<String, Object> stats = couponManagementService.getPeriodStats(startDate, endDate);
|
log.info("查询时间范围统计: startDate={}, endDate={}, scenicId={}", startDate, endDate, scenicId);
|
||||||
|
Map<String, Object> stats = couponManagementService.getPeriodStats(startDate, endDate, scenicId);
|
||||||
|
return ApiResponse.success(stats);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询景区优惠券统计
|
||||||
|
*/
|
||||||
|
@GetMapping("/stats/scenic/{scenicId}")
|
||||||
|
public ApiResponse<Map<String, Object>> getScenicCouponStats(@PathVariable String scenicId) {
|
||||||
|
log.info("查询景区优惠券统计: scenicId={}", scenicId);
|
||||||
|
Map<String, Object> stats = couponManagementService.getScenicCouponStats(scenicId);
|
||||||
return ApiResponse.success(stats);
|
return ApiResponse.success(stats);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -34,4 +34,9 @@ public class CouponUseRequest {
|
|||||||
* 优惠金额
|
* 优惠金额
|
||||||
*/
|
*/
|
||||||
private BigDecimal discountAmount;
|
private BigDecimal discountAmount;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 景区ID
|
||||||
|
*/
|
||||||
|
private String scenicId;
|
||||||
}
|
}
|
@@ -45,4 +45,9 @@ public class ProductItem {
|
|||||||
* 小计(计算后填入)
|
* 小计(计算后填入)
|
||||||
*/
|
*/
|
||||||
private BigDecimal subtotal;
|
private BigDecimal subtotal;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 景区ID
|
||||||
|
*/
|
||||||
|
private String scenicId;
|
||||||
}
|
}
|
@@ -44,4 +44,9 @@ public class PriceCouponClaimRecord extends BaseEntity {
|
|||||||
* 状态
|
* 状态
|
||||||
*/
|
*/
|
||||||
private CouponStatus status;
|
private CouponStatus status;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 景区ID - 记录优惠券在哪个景区被领取/使用
|
||||||
|
*/
|
||||||
|
private String scenicId;
|
||||||
}
|
}
|
@@ -70,4 +70,9 @@ public class PriceCouponConfig extends BaseEntity {
|
|||||||
* 是否启用
|
* 是否启用
|
||||||
*/
|
*/
|
||||||
private Boolean isActive;
|
private Boolean isActive;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 景区ID - 限制优惠券只能在该景区使用
|
||||||
|
*/
|
||||||
|
private String scenicId;
|
||||||
}
|
}
|
@@ -40,18 +40,19 @@ public interface PriceCouponClaimRecordMapper extends BaseMapper<PriceCouponClai
|
|||||||
* 更新优惠券使用状态
|
* 更新优惠券使用状态
|
||||||
*/
|
*/
|
||||||
@Update("UPDATE price_coupon_claim_record SET status = #{status}, " +
|
@Update("UPDATE price_coupon_claim_record SET status = #{status}, " +
|
||||||
"use_time = #{useTime}, order_id = #{orderId}, updated_time = NOW() " +
|
"use_time = #{useTime}, order_id = #{orderId}, scenic_id = #{scenicId}, updated_time = NOW() " +
|
||||||
"WHERE id = #{id}")
|
"WHERE id = #{id}")
|
||||||
int updateCouponStatus(@Param("id") Long id,
|
int updateCouponStatus(@Param("id") Long id,
|
||||||
@Param("status") CouponStatus status,
|
@Param("status") CouponStatus status,
|
||||||
@Param("useTime") java.time.LocalDateTime useTime,
|
@Param("useTime") java.time.LocalDateTime useTime,
|
||||||
@Param("orderId") String orderId);
|
@Param("orderId") String orderId,
|
||||||
|
@Param("scenicId") String scenicId);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 插入优惠券领用记录
|
* 插入优惠券领用记录
|
||||||
*/
|
*/
|
||||||
@Insert("INSERT INTO price_coupon_claim_record (coupon_id, user_id, claim_time, status, created_time, updated_time) " +
|
@Insert("INSERT INTO price_coupon_claim_record (coupon_id, user_id, claim_time, status, scenic_id, created_time, updated_time) " +
|
||||||
"VALUES (#{couponId}, #{userId}, NOW(), #{status}, NOW(), NOW())")
|
"VALUES (#{couponId}, #{userId}, NOW(), #{status}, #{scenicId}, NOW(), NOW())")
|
||||||
int insertClaimRecord(PriceCouponClaimRecord record);
|
int insertClaimRecord(PriceCouponClaimRecord record);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -95,6 +96,9 @@ public interface PriceCouponClaimRecordMapper extends BaseMapper<PriceCouponClai
|
|||||||
"<if test='endTime != null and endTime != \"\"'>" +
|
"<if test='endTime != null and endTime != \"\"'>" +
|
||||||
"AND r.claim_time <= #{endTime}" +
|
"AND r.claim_time <= #{endTime}" +
|
||||||
"</if>" +
|
"</if>" +
|
||||||
|
"<if test='scenicId != null and scenicId != \"\"'>" +
|
||||||
|
"AND r.scenic_id = #{scenicId}" +
|
||||||
|
"</if>" +
|
||||||
"</where>" +
|
"</where>" +
|
||||||
"ORDER BY r.created_time DESC" +
|
"ORDER BY r.created_time DESC" +
|
||||||
"</script>")
|
"</script>")
|
||||||
@@ -102,7 +106,8 @@ public interface PriceCouponClaimRecordMapper extends BaseMapper<PriceCouponClai
|
|||||||
@Param("couponId") Long couponId,
|
@Param("couponId") Long couponId,
|
||||||
@Param("status") CouponStatus status,
|
@Param("status") CouponStatus status,
|
||||||
@Param("startTime") String startTime,
|
@Param("startTime") String startTime,
|
||||||
@Param("endTime") String endTime);
|
@Param("endTime") String endTime,
|
||||||
|
@Param("scenicId") String scenicId);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 管理端:根据用户ID查询优惠券领取记录
|
* 管理端:根据用户ID查询优惠券领取记录
|
||||||
@@ -161,7 +166,8 @@ public interface PriceCouponClaimRecordMapper extends BaseMapper<PriceCouponClai
|
|||||||
/**
|
/**
|
||||||
* 管理端:统计时间范围内的数据
|
* 管理端:统计时间范围内的数据
|
||||||
*/
|
*/
|
||||||
@Select("SELECT " +
|
@Select("<script>" +
|
||||||
|
"SELECT " +
|
||||||
"COUNT(*) as total_claimed, " +
|
"COUNT(*) as total_claimed, " +
|
||||||
"COUNT(CASE WHEN status = 'USED' THEN 1 END) as total_used, " +
|
"COUNT(CASE WHEN status = 'USED' THEN 1 END) as total_used, " +
|
||||||
"COUNT(CASE WHEN status = 'CLAIMED' THEN 1 END) as total_available, " +
|
"COUNT(CASE WHEN status = 'CLAIMED' THEN 1 END) as total_available, " +
|
||||||
@@ -169,7 +175,35 @@ public interface PriceCouponClaimRecordMapper extends BaseMapper<PriceCouponClai
|
|||||||
"COUNT(DISTINCT coupon_id) as total_coupon_types, " +
|
"COUNT(DISTINCT coupon_id) as total_coupon_types, " +
|
||||||
"COUNT(DISTINCT user_id) as total_users " +
|
"COUNT(DISTINCT user_id) as total_users " +
|
||||||
"FROM price_coupon_claim_record " +
|
"FROM price_coupon_claim_record " +
|
||||||
"WHERE claim_time >= #{startDate} AND claim_time <= #{endDate}")
|
"WHERE claim_time >= #{startDate} AND claim_time <= #{endDate} " +
|
||||||
|
"<if test='scenicId != null and scenicId != \"\"'>" +
|
||||||
|
"AND scenic_id = #{scenicId} " +
|
||||||
|
"</if>" +
|
||||||
|
"</script>")
|
||||||
java.util.Map<String, Object> selectPeriodStats(@Param("startDate") String startDate,
|
java.util.Map<String, Object> selectPeriodStats(@Param("startDate") String startDate,
|
||||||
@Param("endDate") String endDate);
|
@Param("endDate") String endDate,
|
||||||
|
@Param("scenicId") String scenicId);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 根据景区ID查询优惠券领取记录
|
||||||
|
*/
|
||||||
|
@Select("SELECT r.*, c.coupon_name, c.coupon_type, c.discount_value " +
|
||||||
|
"FROM price_coupon_claim_record r " +
|
||||||
|
"LEFT JOIN price_coupon_config c ON r.coupon_id = c.id " +
|
||||||
|
"WHERE r.scenic_id = #{scenicId} " +
|
||||||
|
"ORDER BY r.created_time DESC")
|
||||||
|
List<PriceCouponClaimRecord> selectByScenicIdForAdmin(@Param("scenicId") String scenicId);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 统计景区优惠券使用情况
|
||||||
|
*/
|
||||||
|
@Select("SELECT " +
|
||||||
|
"COUNT(*) as total_claimed, " +
|
||||||
|
"COUNT(CASE WHEN status = 'USED' THEN 1 END) as total_used, " +
|
||||||
|
"COUNT(CASE WHEN status = 'CLAIMED' THEN 1 END) as total_available, " +
|
||||||
|
"COUNT(CASE WHEN status = 'EXPIRED' THEN 1 END) as total_expired, " +
|
||||||
|
"COUNT(DISTINCT coupon_id) as total_coupon_types, " +
|
||||||
|
"COUNT(DISTINCT user_id) as total_users " +
|
||||||
|
"FROM price_coupon_claim_record WHERE scenic_id = #{scenicId}")
|
||||||
|
java.util.Map<String, Object> selectScenicCouponUsageStats(@Param("scenicId") String scenicId);
|
||||||
}
|
}
|
@@ -44,10 +44,10 @@ public interface PriceCouponConfigMapper extends BaseMapper<PriceCouponConfig> {
|
|||||||
*/
|
*/
|
||||||
@Insert("INSERT INTO price_coupon_config (coupon_name, coupon_type, discount_value, min_amount, " +
|
@Insert("INSERT INTO price_coupon_config (coupon_name, coupon_type, discount_value, min_amount, " +
|
||||||
"max_discount, applicable_products, total_quantity, used_quantity, valid_from, valid_until, " +
|
"max_discount, applicable_products, total_quantity, used_quantity, valid_from, valid_until, " +
|
||||||
"is_active, created_time, updated_time) VALUES " +
|
"is_active, scenic_id, created_time, updated_time) VALUES " +
|
||||||
"(#{couponName}, #{couponType}, #{discountValue}, #{minAmount}, #{maxDiscount}, " +
|
"(#{couponName}, #{couponType}, #{discountValue}, #{minAmount}, #{maxDiscount}, " +
|
||||||
"#{applicableProducts}, #{totalQuantity}, #{usedQuantity}, #{validFrom}, #{validUntil}, " +
|
"#{applicableProducts}, #{totalQuantity}, #{usedQuantity}, #{validFrom}, #{validUntil}, " +
|
||||||
"#{isActive}, NOW(), NOW())")
|
"#{isActive}, #{scenicId}, NOW(), NOW())")
|
||||||
int insertCoupon(PriceCouponConfig coupon);
|
int insertCoupon(PriceCouponConfig coupon);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -57,7 +57,7 @@ public interface PriceCouponConfigMapper extends BaseMapper<PriceCouponConfig> {
|
|||||||
"discount_value = #{discountValue}, min_amount = #{minAmount}, max_discount = #{maxDiscount}, " +
|
"discount_value = #{discountValue}, min_amount = #{minAmount}, max_discount = #{maxDiscount}, " +
|
||||||
"applicable_products = #{applicableProducts}, total_quantity = #{totalQuantity}, " +
|
"applicable_products = #{applicableProducts}, total_quantity = #{totalQuantity}, " +
|
||||||
"valid_from = #{validFrom}, valid_until = #{validUntil}, is_active = #{isActive}, " +
|
"valid_from = #{validFrom}, valid_until = #{validUntil}, is_active = #{isActive}, " +
|
||||||
"updated_time = NOW() WHERE id = #{id}")
|
"scenic_id = #{scenicId}, updated_time = NOW() WHERE id = #{id}")
|
||||||
int updateCoupon(PriceCouponConfig coupon);
|
int updateCoupon(PriceCouponConfig coupon);
|
||||||
|
|
||||||
// ==================== 管理端接口 ====================
|
// ==================== 管理端接口 ====================
|
||||||
@@ -80,11 +80,15 @@ public interface PriceCouponConfigMapper extends BaseMapper<PriceCouponConfig> {
|
|||||||
"<if test='couponName != null and couponName != \"\"'>" +
|
"<if test='couponName != null and couponName != \"\"'>" +
|
||||||
"AND coupon_name LIKE CONCAT('%', #{couponName}, '%')" +
|
"AND coupon_name LIKE CONCAT('%', #{couponName}, '%')" +
|
||||||
"</if>" +
|
"</if>" +
|
||||||
|
"<if test='scenicId != null and scenicId != \"\"'>" +
|
||||||
|
"AND scenic_id = #{scenicId}" +
|
||||||
|
"</if>" +
|
||||||
"</where>" +
|
"</where>" +
|
||||||
"ORDER BY created_time DESC" +
|
"ORDER BY created_time DESC" +
|
||||||
"</script>")
|
"</script>")
|
||||||
List<PriceCouponConfig> selectByConditionsForAdmin(@Param("isActive") Boolean isActive,
|
List<PriceCouponConfig> selectByConditionsForAdmin(@Param("isActive") Boolean isActive,
|
||||||
@Param("couponName") String couponName);
|
@Param("couponName") String couponName,
|
||||||
|
@Param("scenicId") String scenicId);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 管理端:根据状态查询优惠券配置
|
* 管理端:根据状态查询优惠券配置
|
||||||
@@ -103,4 +107,30 @@ public interface PriceCouponConfigMapper extends BaseMapper<PriceCouponConfig> {
|
|||||||
*/
|
*/
|
||||||
@Update("UPDATE price_coupon_config SET deleted = 1, updated_time = NOW() WHERE id = #{id}")
|
@Update("UPDATE price_coupon_config SET deleted = 1, updated_time = NOW() WHERE id = #{id}")
|
||||||
int deleteCoupon(Long id);
|
int deleteCoupon(Long id);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询指定景区的有效优惠券配置
|
||||||
|
*/
|
||||||
|
@Select("SELECT * FROM price_coupon_config WHERE is_active = 1 " +
|
||||||
|
"AND valid_from <= NOW() AND valid_until > NOW() " +
|
||||||
|
"AND used_quantity < total_quantity " +
|
||||||
|
"AND (scenic_id IS NULL OR scenic_id = #{scenicId})")
|
||||||
|
List<PriceCouponConfig> selectValidCouponsByScenicId(@Param("scenicId") String scenicId);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 管理端:根据景区ID查询优惠券配置
|
||||||
|
*/
|
||||||
|
@Select("SELECT * FROM price_coupon_config WHERE scenic_id = #{scenicId} ORDER BY created_time DESC")
|
||||||
|
List<PriceCouponConfig> selectByScenicIdForAdmin(@Param("scenicId") String scenicId);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 统计景区优惠券配置数量
|
||||||
|
*/
|
||||||
|
@Select("SELECT " +
|
||||||
|
"COUNT(*) as total_coupons, " +
|
||||||
|
"COUNT(CASE WHEN is_active = 1 THEN 1 END) as active_coupons, " +
|
||||||
|
"SUM(total_quantity) as total_quantity, " +
|
||||||
|
"SUM(used_quantity) as used_quantity " +
|
||||||
|
"FROM price_coupon_config WHERE scenic_id = #{scenicId}")
|
||||||
|
java.util.Map<String, Object> selectScenicCouponConfigStats(@Param("scenicId") String scenicId);
|
||||||
}
|
}
|
@@ -44,7 +44,7 @@ public interface ICouponManagementService {
|
|||||||
* 分页查询优惠券配置
|
* 分页查询优惠券配置
|
||||||
*/
|
*/
|
||||||
PageInfo<PriceCouponConfig> getCouponConfigsPage(Integer pageNum, Integer pageSize,
|
PageInfo<PriceCouponConfig> getCouponConfigsPage(Integer pageNum, Integer pageSize,
|
||||||
Boolean isActive, String couponName);
|
Boolean isActive, String couponName, String scenicId);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 根据状态查询优惠券配置
|
* 根据状态查询优惠券配置
|
||||||
@@ -68,7 +68,7 @@ public interface ICouponManagementService {
|
|||||||
*/
|
*/
|
||||||
PageInfo<PriceCouponClaimRecord> getClaimRecordsPage(Integer pageNum, Integer pageSize,
|
PageInfo<PriceCouponClaimRecord> getClaimRecordsPage(Integer pageNum, Integer pageSize,
|
||||||
Long userId, Long couponId, CouponStatus status,
|
Long userId, Long couponId, CouponStatus status,
|
||||||
String startTime, String endTime);
|
String startTime, String endTime, String scenicId);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 根据用户ID查询优惠券领取记录
|
* 根据用户ID查询优惠券领取记录
|
||||||
@@ -98,10 +98,15 @@ public interface ICouponManagementService {
|
|||||||
/**
|
/**
|
||||||
* 查询时间范围内的统计数据
|
* 查询时间范围内的统计数据
|
||||||
*/
|
*/
|
||||||
Map<String, Object> getPeriodStats(String startDate, String endDate);
|
Map<String, Object> getPeriodStats(String startDate, String endDate, String scenicId);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 查询所有优惠券的使用统计概览
|
* 查询所有优惠券的使用统计概览
|
||||||
*/
|
*/
|
||||||
List<Map<String, Object>> getAllCouponUsageOverview();
|
List<Map<String, Object>> getAllCouponUsageOverview();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询景区优惠券统计
|
||||||
|
*/
|
||||||
|
Map<String, Object> getScenicCouponStats(String scenicId);
|
||||||
}
|
}
|
@@ -126,12 +126,12 @@ public class CouponManagementServiceImpl implements ICouponManagementService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public PageInfo<PriceCouponConfig> getCouponConfigsPage(Integer pageNum, Integer pageSize,
|
public PageInfo<PriceCouponConfig> getCouponConfigsPage(Integer pageNum, Integer pageSize,
|
||||||
Boolean isActive, String couponName) {
|
Boolean isActive, String couponName, String scenicId) {
|
||||||
log.info("分页查询优惠券配置,页码: {}, 页大小: {}, 状态: {}, 名称: {}",
|
log.info("分页查询优惠券配置,页码: {}, 页大小: {}, 状态: {}, 名称: {}, 景区ID: {}",
|
||||||
pageNum, pageSize, isActive, couponName);
|
pageNum, pageSize, isActive, couponName, scenicId);
|
||||||
|
|
||||||
PageHelper.startPage(pageNum, pageSize);
|
PageHelper.startPage(pageNum, pageSize);
|
||||||
List<PriceCouponConfig> configs = couponConfigMapper.selectByConditionsForAdmin(isActive, couponName);
|
List<PriceCouponConfig> configs = couponConfigMapper.selectByConditionsForAdmin(isActive, couponName, scenicId);
|
||||||
return new PageInfo<>(configs);
|
return new PageInfo<>(configs);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -158,12 +158,12 @@ public class CouponManagementServiceImpl implements ICouponManagementService {
|
|||||||
@Override
|
@Override
|
||||||
public PageInfo<PriceCouponClaimRecord> getClaimRecordsPage(Integer pageNum, Integer pageSize,
|
public PageInfo<PriceCouponClaimRecord> getClaimRecordsPage(Integer pageNum, Integer pageSize,
|
||||||
Long userId, Long couponId, CouponStatus status,
|
Long userId, Long couponId, CouponStatus status,
|
||||||
String startTime, String endTime) {
|
String startTime, String endTime, String scenicId) {
|
||||||
log.info("分页查询优惠券领取记录,页码: {}, 页大小: {}, 用户ID: {}, 优惠券ID: {}, 状态: {}, 开始时间: {}, 结束时间: {}",
|
log.info("分页查询优惠券领取记录,页码: {}, 页大小: {}, 用户ID: {}, 优惠券ID: {}, 状态: {}, 开始时间: {}, 结束时间: {}, 景区ID: {}",
|
||||||
pageNum, pageSize, userId, couponId, status, startTime, endTime);
|
pageNum, pageSize, userId, couponId, status, startTime, endTime, scenicId);
|
||||||
|
|
||||||
PageHelper.startPage(pageNum, pageSize);
|
PageHelper.startPage(pageNum, pageSize);
|
||||||
List<PriceCouponClaimRecord> records = claimRecordMapper.selectByConditionsForAdmin(userId, couponId, status, startTime, endTime);
|
List<PriceCouponClaimRecord> records = claimRecordMapper.selectByConditionsForAdmin(userId, couponId, status, startTime, endTime, scenicId);
|
||||||
return new PageInfo<>(records);
|
return new PageInfo<>(records);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -198,9 +198,9 @@ public class CouponManagementServiceImpl implements ICouponManagementService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Map<String, Object> getPeriodStats(String startDate, String endDate) {
|
public Map<String, Object> getPeriodStats(String startDate, String endDate, String scenicId) {
|
||||||
log.info("查询时间范围统计,开始日期: {}, 结束日期: {}", startDate, endDate);
|
log.info("查询时间范围统计,开始日期: {}, 结束日期: {}, 景区ID: {}", startDate, endDate, scenicId);
|
||||||
return claimRecordMapper.selectPeriodStats(startDate, endDate);
|
return claimRecordMapper.selectPeriodStats(startDate, endDate, scenicId);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@@ -231,4 +231,23 @@ public class CouponManagementServiceImpl implements ICouponManagementService {
|
|||||||
|
|
||||||
return overview;
|
return overview;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Map<String, Object> getScenicCouponStats(String scenicId) {
|
||||||
|
log.info("查询景区优惠券统计,景区ID: {}", scenicId);
|
||||||
|
|
||||||
|
// 获取景区优惠券配置统计
|
||||||
|
Map<String, Object> configStats = couponConfigMapper.selectScenicCouponConfigStats(scenicId);
|
||||||
|
|
||||||
|
// 获取景区优惠券使用统计
|
||||||
|
Map<String, Object> usageStats = claimRecordMapper.selectScenicCouponUsageStats(scenicId);
|
||||||
|
|
||||||
|
// 合并统计结果
|
||||||
|
Map<String, Object> result = new HashMap<>();
|
||||||
|
result.put("scenic_id", scenicId);
|
||||||
|
result.putAll(configStats);
|
||||||
|
result.putAll(usageStats);
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
}
|
}
|
@@ -82,10 +82,29 @@ public class CouponServiceImpl implements ICouponService {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isCouponApplicable(PriceCouponConfig coupon, List<ProductItem> products, BigDecimal totalAmount) {
|
public boolean isCouponApplicable(PriceCouponConfig coupon, List<ProductItem> products, BigDecimal totalAmount) {
|
||||||
|
// 1. 检查最小使用金额
|
||||||
if (totalAmount.compareTo(coupon.getMinAmount()) < 0) {
|
if (totalAmount.compareTo(coupon.getMinAmount()) < 0) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 2. 检查景区限制
|
||||||
|
if (coupon.getScenicId() != null && !coupon.getScenicId().isEmpty()) {
|
||||||
|
boolean hasMatchingScenicProduct = false;
|
||||||
|
for (ProductItem product : products) {
|
||||||
|
if (coupon.getScenicId().equals(product.getScenicId())) {
|
||||||
|
hasMatchingScenicProduct = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!hasMatchingScenicProduct) {
|
||||||
|
log.debug("优惠券景区限制不匹配: 优惠券景区={}, 商品景区={}",
|
||||||
|
coupon.getScenicId(),
|
||||||
|
products.stream().map(ProductItem::getScenicId).distinct().toList());
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 3. 检查商品类型限制
|
||||||
if (coupon.getApplicableProducts() == null || coupon.getApplicableProducts().isEmpty()) {
|
if (coupon.getApplicableProducts() == null || coupon.getApplicableProducts().isEmpty()) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -127,14 +146,19 @@ public class CouponServiceImpl implements ICouponService {
|
|||||||
|
|
||||||
LocalDateTime useTime = LocalDateTime.now();
|
LocalDateTime useTime = LocalDateTime.now();
|
||||||
|
|
||||||
// 设置使用时间和订单信息
|
// 设置使用时间、订单信息和景区信息
|
||||||
record.setStatus(CouponStatus.USED);
|
record.setStatus(CouponStatus.USED);
|
||||||
record.setUseTime(useTime);
|
record.setUseTime(useTime);
|
||||||
record.setOrderId(request.getOrderId());
|
record.setOrderId(request.getOrderId());
|
||||||
record.setUpdatedTime(LocalDateTime.now());
|
record.setUpdatedTime(LocalDateTime.now());
|
||||||
|
|
||||||
|
// 如果请求中包含景区ID,记录到使用记录中
|
||||||
|
if (request.getScenicId() != null && !request.getScenicId().isEmpty()) {
|
||||||
|
record.setScenicId(request.getScenicId());
|
||||||
|
}
|
||||||
|
|
||||||
couponClaimRecordMapper.updateCouponStatus(
|
couponClaimRecordMapper.updateCouponStatus(
|
||||||
record.getId(), CouponStatus.USED, useTime, request.getOrderId());
|
record.getId(), CouponStatus.USED, useTime, request.getOrderId(), request.getScenicId());
|
||||||
|
|
||||||
CouponUseResult result = new CouponUseResult();
|
CouponUseResult result = new CouponUseResult();
|
||||||
result.setCouponId(request.getCouponId());
|
result.setCouponId(request.getCouponId());
|
||||||
|
Reference in New Issue
Block a user