Files
soul-yongping/开发文档/8、部署/后台提现审核数据对接.md
2026-02-09 15:09:29 +08:00

9.7 KiB
Raw Blame History

后台提现审核数据对接

需求

在后台管理的"交易中心-提现审核"页面,完善数据显示,让管理员能够:

  1. 查看用户的累计佣金信息
  2. 查看用户的已提现金额
  3. 查看用户的待审核提现金额
  4. 预判审核通过后用户的剩余余额
  5. 识别超额提现风险

实现内容

1. 后端API增强

文件app/api/admin/withdrawals/route.ts

数据库查询优化

添加了用户佣金相关信息的查询:

SELECT 
  w.*,
  u.nickname as user_nickname,
  u.phone as user_phone,
  u.avatar as user_avatar,
  u.referral_code,
  u.withdrawn_earnings,
  u.earnings,
  u.pending_earnings,
  -- 计算累计佣金(从 orders 表)
  (SELECT COALESCE(SUM(o.amount), 0) 
   FROM orders o 
   WHERE o.referrer_id = w.user_id AND o.status = 'paid') as total_order_amount,
  -- 计算待审核提现金额(不包括当前这条)
  (SELECT COALESCE(SUM(w2.amount), 0) 
   FROM withdrawals w2 
   WHERE w2.user_id = w.user_id AND w2.status = 'pending' AND w2.id != w.id) as other_pending_amount
FROM withdrawals w
LEFT JOIN users u ON w.user_id = u.id

返回数据结构

新增 userCommissionInfo 字段:

{
  id: string,
  userId: string,
  userNickname: string,
  amount: number,
  status: string,
  // ... 其他字段
  
  // ✅ 新增:用户佣金信息
  userCommissionInfo: {
    totalCommission: number,        // 累计佣金(订单金额 × 90%
    withdrawnEarnings: number,      // 已提现金额
    pendingWithdrawals: number,     // 待审核金额(包括当前这笔)
    availableAfterThis: number      // 审核通过后的剩余余额
  }
}

计算逻辑

// 计算累计佣金90%分成)
const totalCommission = parseFloat(w.total_order_amount) * 0.9

// 已提现金额
const withdrawnEarnings = parseFloat(w.withdrawn_earnings) || 0

// 其他待审核金额(不包括当前这笔)
const otherPendingAmount = parseFloat(w.other_pending_amount) || 0

// 当前提现金额
const currentWithdrawAmount = parseFloat(w.amount)

// ✅ 审核后余额 = 累计佣金 - 已提现 - 其他待审核 - 当前提现
const availableAfterThis = totalCommission - withdrawnEarnings - otherPendingAmount - currentWithdrawAmount

2. 前端页面增强

文件app/admin/withdrawals/page.tsx

新增列:用户佣金信息

在表格中添加了一列显示用户的完整佣金情况:

字段 说明 颜色
累计佣金 用户的历史总佣金 青色(#38bdac
已提现 已到账的金额 灰色
待审核 所有待审核的提现申请总和 橙色
审核后余额 如果通过当前申请,用户剩余的可提现金额 绿色≥0/ 红色(<0

界面效果

┌─────────────────────────────────────────┐
│ 用户佣金信息                            │
├─────────────────────────────────────────┤
│ 累计佣金:           ¥100.00 [青色]     │
│ 已提现:             ¥30.00  [灰色]     │
│ 待审核:             ¥50.00  [橙色]     │
│ ─────────────────────────────           │
│ 审核后余额:         ¥20.00  [绿色]     │
└─────────────────────────────────────────┘

风险警告

审核后余额 < 0 时:

  • 显示为红色
  • 批准时弹出警告提示
if (withdrawal.userCommissionInfo.availableAfterThis < 0) {
  confirm(`⚠️ 风险警告:该用户审核后余额为负数(¥${availableAfterThis}),可能存在超额提现。\n\n确认已核实用户账户并完成打款`)
}

数据示例

示例1正常提现

用户A
- 累计佣金: ¥100
- 已提现: ¥30
- 其他待审核: ¥20
- 当前申请: ¥40

审核后余额 = 100 - 30 - 20 - 40 = ¥10 ✅ 正常

示例2超额提现风险

用户B
- 累计佣金: ¥100
- 已提现: ¥30
- 其他待审核: ¥20
- 当前申请: ¥60

审核后余额 = 100 - 30 - 20 - 60 = -¥10 ❌ 超额!

警告用户B可能存在以下问题

  1. 重复提现(并发提交)
  2. 恶意超额提现
  3. 数据异常

示例3多笔待审核

用户C
- 累计佣金: ¥200
- 已提现: ¥50
- 其他待审核: ¥80两笔¥50 + ¥30
- 当前申请: ¥50

审核后余额 = 200 - 50 - 80 - 50 = ¥20 ✅ 正常
但注意:如果三笔都通过,还能再提 ¥20

审核流程

管理员视角

1. 打开提现审核页面
   ↓
2. 查看待审核列表
   ↓
3. 查看用户佣金信息
   - 累计佣金: 判断用户赚了多少
   - 已提现: 判断之前提现过多少
   - 待审核: 判断还有多少在审核中
   - 审核后余额: 判断是否超额
   ↓
4. 点击"批准"或"拒绝"
   ↓
5. 如果审核后余额 < 0:
   - ⚠️ 弹出风险警告
   - 需要二次确认
   ↓
6. 确认后执行操作

决策依据

批准条件

  • 审核后余额 ≥ 0
  • 用户信息真实
  • 已完成线下打款(或准备自动转账)

拒绝条件

  • 审核后余额 < 0超额提现
  • 用户信息异常
  • 疑似恶意提现
  • 未完成打款且不打算打款

统计信息

顶部统计卡片

显示全局提现统计:

统计项 说明
总申请 所有提现申请的数量
待处理 状态为 pending 的数量和金额
已完成 状态为 success 的数量和金额
已拒绝 状态为 failed 的数量

筛选功能

可以按状态筛选:

  • 全部
  • 待处理pending
  • 已完成success
  • 已拒绝failed

状态说明

状态 英文 说明 可操作
待处理 pending 用户刚提交,等待审核 批准/拒绝
处理中 processing 已发起微信转账,等待到账 -
已完成 success 已到账,提现完成 -
已拒绝 failed 管理员拒绝,余额已返还 -

测试步骤

1. 准备测试数据

-- 插入测试用户
INSERT INTO users (id, nickname, phone, withdrawn_earnings, referral_code) 
VALUES ('test_user_1', '测试用户A', '13800138000', 0, 'SOULA001');

-- 插入测试订单(产生佣金)
INSERT INTO orders (id, user_id, amount, referrer_id, status, pay_time) 
VALUES ('order_1', 'buyer_1', 100, 'test_user_1', 'paid', NOW());

-- 插入测试提现申请
INSERT INTO withdrawals (id, user_id, amount, status, created_at) 
VALUES ('W001', 'test_user_1', 50, 'pending', NOW());

2. 访问页面

http://localhost:3006/admin/withdrawals

3. 验证数据

查看提现记录

  • 用户昵称测试用户A
  • 电话138****8000
  • 提现金额¥50.00

查看佣金信息

  • 累计佣金¥90.00100 × 90%
  • 已提现¥0.00
  • 待审核¥50.00
  • 审核后余额¥40.00

4. 测试超额提现

-- 再插入一笔超额提现
INSERT INTO withdrawals (id, user_id, amount, status, created_at) 
VALUES ('W002', 'test_user_1', 60, 'pending', NOW());

刷新页面,查看 W002

  • 累计佣金¥90.00
  • 已提现¥0.00
  • 待审核¥110.0050 + 60
  • 审核后余额:-¥20.00 红色显示

点击批准

  • 应该弹出风险警告
  • 需要二次确认

安全检查

防止超额提现

  1. 前端校验:小程序端计算可提现金额
  2. 后端校验:提现接口验证金额
  3. 管理端提示:显示审核后余额,红色警告

并发提现防护

如果用户快速提交多笔提现:

  • 后端查询会累加所有待审核金额
  • 管理员能看到"待审核"总额
  • "审核后余额"会提前减去所有待审核的金额

数据一致性

  • 累计佣金:实时从 orders 表计算
  • 已提现:从 users.withdrawn_earnings 读取
  • 待审核:实时从 withdrawals 表查询

常见问题

Q1: 为什么审核后余额是负数?

A: 可能原因:

  1. 用户并发提交多笔提现
  2. 前端校验被绕过
  3. 数据库数据异常

处理

  • 拒绝超额提现申请
  • 核查用户账户
  • 只批准合理范围内的提现

Q2: 如果有多笔待审核,应该如何处理?

A:

  • 查看"待审核"总额
  • 确保所有待审核的总和 ≤ 可提现金额
  • 按时间顺序逐笔审核
  • 或者拒绝超额的申请

Q3: 审核后余额为0还能再提现吗

A:

  • 如果有新订单产生佣金,可以
  • 审核后余额0表示当前所有佣金都将被提走
  • 新订单会增加累计佣金,从而增加可提现金额

Q4: 如何处理已拒绝的提现?

A:

  • 拒绝时余额自动返还
  • 用户可以在小程序重新申请
  • "审核后余额"会恢复

相关文件

  • app/admin/withdrawals/page.tsx - 前端页面
  • app/api/admin/withdrawals/route.ts - 后端API
  • app/api/withdraw/route.ts - 用户提现接口
  • miniprogram/pages/referral/referral.js - 小程序提现页面

总结

这次数据对接实现了:

功能增强

  • 显示用户的完整佣金信息
  • 计算审核后余额
  • 风险警告(超额提现)
  • 数据实时计算,确保准确

管理便利

  • 一眼看清用户的资金状况
  • 提前识别超额提现风险
  • 批准/拒绝决策有据可依

安全保障

  • 三层校验(前端、后端、管理端)
  • 并发提现检测
  • 超额提现警告

核心价值:让管理员能够看到完整的资金流水,做出明智的审核决策,防止超额提现风险