From 3f5356ad87813d2add5e5e516ccab50b765426f8 Mon Sep 17 00:00:00 2001 From: linkeyu Date: Tue, 21 Jul 2026 11:59:50 +0800 Subject: [PATCH] =?UTF-8?q?feat(admin):=20=E9=A2=86=E5=88=B8=E5=AE=8C?= =?UTF-8?q?=E6=88=90=E7=8E=87=E5=92=8C=E7=82=B9=E4=BD=8D=E6=88=90=E5=8A=9F?= =?UTF-8?q?=E7=8E=87=E5=B1=95=E7=A4=BA=E8=AE=A1=E7=AE=97=E6=98=8E=E7=BB=86?= =?UTF-8?q?=20(#53)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ## 变更内容 - 将汇总卡“领券成功率”明确为“领券完成率” - 提示中动态展示完成数、发起数、中途退出数及本期代入计算结果 - 点位成功率提示逐券展示成功数、尝试数、单券成功率和最终等权平均结果 - 展示累计成功/尝试数作为辅助核对,并明确不作为当前加权公式 ## 验证 - npx tsc --noEmit - npm run build --------- Co-authored-by: linkeyu <798648091@qq.com> Reviewed-on: https://gitea.shaguabijia.com/WonderableAI/shaguabijia-admin-web/pulls/53 Co-authored-by: linkeyu Co-committed-by: linkeyu --- src/app/(main)/coupon-data/page.tsx | 49 +++++++++++++++++++++++------ 1 file changed, 40 insertions(+), 9 deletions(-) diff --git a/src/app/(main)/coupon-data/page.tsx b/src/app/(main)/coupon-data/page.tsx index 4267661..3f0a696 100644 --- a/src/app/(main)/coupon-data/page.tsx +++ b/src/app/(main)/coupon-data/page.tsx @@ -137,11 +137,6 @@ const slotRateMean = (rows: CouponSlotRow[]): number | null => { return rates.length ? rates.reduce((a, b) => a + b, 0) / rates.length : null; }; -// 汇总卡成功率口径 tooltip 文案 -const POINT_RATE_HINT = - '点位成功率(合计):当前区间内全部券成功率的算术平均(每张券等权);' + - '单券成功率=成功(含已领)÷尝试(不含跳过),源自领券每券记录。'; - // 按券表:coupon_id 平台 → 中文 const SLOT_PLATFORM: Record = { 'meituan-waimai': '美团', @@ -597,6 +592,10 @@ export default function CouponDataPage() { const successDenominator = summary ? Math.max(0, summary.started_count - abandonedCount) : 0; const couponSuccessRate = summary && successDenominator > 0 ? summary.completed_count / successDenominator : null; + const validCouponSlots = couponSlots.filter((r) => r.success_rate != null); + const pointSuccessRate = slotRateMean(validCouponSlots); + const pointSucceededTotal = validCouponSlots.reduce((total, r) => total + r.succeeded, 0); + const pointTriedTotal = validCouponSlots.reduce((total, r) => total + r.tried, 0); const items = data?.items ?? []; return ( @@ -714,8 +713,19 @@ export default function CouponDataPage() { - 领券成功率{' '} - + 领券完成率{' '} + +
计算逻辑:领券完成数 ÷(领券发起数-中途退出数)
+
+ 本期:{summary.completed_count} ÷({summary.started_count}-{abandonedCount}) + = {fmtPct(couponSuccessRate)} +
+ + } + >
@@ -728,12 +738,33 @@ export default function CouponDataPage() { title={ 点位成功率{' '} - + +
计算逻辑:全部单券成功率的算术平均,每张券等权。
+
单券成功率=成功数(含已领)÷ 尝试数(不含跳过)。
+
+ 本期共 {validCouponSlots.length} 张有效券: +
+ {validCouponSlots.map((slot) => ( +
+ {slot.coupon_name || slot.coupon_id}:{slot.succeeded} ÷ {slot.tried}= + {fmtPct(slot.success_rate)} +
+ ))} +
+ 等权平均={fmtPct(pointSuccessRate)};累计成功/尝试= + {pointSucceededTotal}/{pointTriedTotal}(累计数仅辅助核对,不作为当前加权公式)。 +
+ + } + >
} - value={fmtPct(slotRateMean(couponSlots))} + value={fmtPct(pointSuccessRate)} />