fix gao event rank

This commit is contained in:
Timi
2026-08-13 00:24:39 +08:00
parent ee530d2a8c
commit 67d79f7527
3 changed files with 86 additions and 15 deletions
@@ -279,6 +279,7 @@ public class GaoEventRecordServiceImplement extends AbstractEntityService<GaoEve
@Override
public PageResult<GaoCustomerEventRankView> pageRankByRange(GaoEventRecordRankPage page) {
TimiException.required(page.getStoreId(), "not found page.storeId");
page.setTodayDateValue(dateValue(Time.now()));
PageResult<GaoCustomerEventRankView> result = new PageResult<>();
result.setTotal(mapper.countRankByRange(page));
result.setList(mapper.selectRankByRange(page));
@@ -23,9 +23,24 @@ public class GaoEventRecordRankPage extends BasePage {
/// 登记事件 ID 列表,为空查询全部登记事件
private List<String> eventIdList;
/// 排行类型
private RankType rankType;
/// 开始登记时间
private Long beginAt;
/// 结束登记时间
private Long endAt;
/// 查询当天日期值,服务端内部填充,格式为 yyyyMMdd
private Integer todayDateValue;
public enum RankType {
/// 按累计登记天数
TOTAL_DAYS,
/// 按累计登记次数
TOTAL_COUNT,
/// 按最近连续登记天数
CONTINUOUS_DAYS
}
}
@@ -129,10 +129,10 @@
<include refid="rankWhere"/>
</select>
<select id="selectRankByRange" resultType="com.imyeyu.api.modules.gao.vo.GaoCustomerEventRankView">
WITH `daily_stat` AS (
WITH RECURSIVE `daily_stat` AS (
SELECT
r.`customer_id` AS `customerId`,
r.`business_day_no` AS `businessDayNo`,
r.`registered_date_value` AS `registeredDateValue`,
COUNT(1) AS `dailyCount`,
MAX(r.`registered_at`) AS `latestRegisteredAt`
FROM `gao_event_record` r
@@ -141,7 +141,39 @@
<include refid="rankWhere"/>
GROUP BY
r.`customer_id`,
r.`business_day_no`
r.`registered_date_value`
),
`range_bound` AS (
SELECT
LEAST(
STR_TO_DATE(CAST(MIN(`registeredDateValue`) AS CHAR), '%Y%m%d'),
STR_TO_DATE(CAST(#{todayDateValue} AS CHAR), '%Y%m%d')
) AS `beginDate`,
STR_TO_DATE(CAST(#{todayDateValue} AS CHAR), '%Y%m%d') AS `endDate`
FROM `daily_stat`
),
`calendar` AS (
SELECT
CAST(DATE_FORMAT(`beginDate`, '%Y%m%d') AS UNSIGNED) AS `dateValue`,
`beginDate` AS `dateDate`
FROM `range_bound`
WHERE `beginDate` IS NOT NULL
UNION ALL
SELECT
CAST(DATE_FORMAT(DATE_ADD(c.`dateDate`, INTERVAL 1 DAY), '%Y%m%d') AS UNSIGNED) AS `dateValue`,
DATE_ADD(c.`dateDate`, INTERVAL 1 DAY) AS `dateDate`
FROM `calendar` c
JOIN `range_bound` b ON c.`dateDate` &lt; b.`endDate`
),
`open_calendar` AS (
SELECT
c.`dateValue`,
ROW_NUMBER() OVER (ORDER BY c.`dateDate`) AS `openIndex`
FROM `calendar` c
LEFT JOIN `gao_store_business_day` b ON b.`store_id` = #{storeId}
AND b.`date_value` = c.`dateValue`
AND b.`deleted_at` IS NULL
WHERE COALESCE(b.`status`, 'OPEN') != 'CLOSED'
),
`rank_stat` AS (
SELECT
@@ -154,35 +186,58 @@
),
`continuous_ordered` AS (
SELECT
`customerId`,
`businessDayNo`,
ROW_NUMBER() OVER (PARTITION BY `customerId` ORDER BY `businessDayNo` DESC) AS `dayIndex`
FROM `daily_stat`
d.`customerId`,
o.`openIndex`,
ROW_NUMBER() OVER (PARTITION BY d.`customerId` ORDER BY o.`openIndex` DESC) AS `dayIndex`
FROM `daily_stat` d
JOIN `open_calendar` o ON d.`registeredDateValue` = o.`dateValue`
),
`latest_date` AS (
`anchor_date` AS (
SELECT
`customerId`,
MAX(`businessDayNo`) AS `latestBusinessDayNo`
FROM `daily_stat`
GROUP BY `customerId`
MAX(`openIndex`) AS `anchorOpenIndex`
FROM `open_calendar`
),
`continuous_stat` AS (
SELECT
o.`customerId`,
COUNT(1) AS `recentContinuousEventDays`
CASE
WHEN COUNT(1) &lt; 2 THEN 0
ELSE COUNT(1)
END AS `recentContinuousEventDays`
FROM `continuous_ordered` o
LEFT JOIN `latest_date` l ON o.`customerId` = l.`customerId`
WHERE o.`businessDayNo` + o.`dayIndex` = l.`latestBusinessDayNo` + 1
JOIN `anchor_date` a
WHERE
o.`openIndex` + o.`dayIndex` = a.`anchorOpenIndex` + 1
<if test="eventIdList == null or eventIdList.size() != 1">
AND 1 = 0
</if>
GROUP BY o.`customerId`
),
`ranked` AS (
SELECT
ROW_NUMBER() OVER (
ORDER BY
<choose>
<when test="rankType != null and rankType.name() == 'TOTAL_COUNT'">
r.`totalEventCount` DESC,
r.`totalEventDays` DESC,
r.`latestRegisteredAt` DESC,
r.`customerId`
</when>
<when test="rankType != null and rankType.name() == 'CONTINUOUS_DAYS'">
COALESCE(c.`recentContinuousEventDays`, 0) DESC,
r.`totalEventDays` DESC,
r.`totalEventCount` DESC,
r.`latestRegisteredAt` DESC,
r.`customerId`
</when>
<otherwise>
r.`totalEventDays` DESC,
r.`totalEventCount` DESC,
r.`latestRegisteredAt` DESC,
r.`customerId`
</otherwise>
</choose>
) AS `rank`,
r.`customerId`,
r.`totalEventDays`,