8.2 KiB
8.2 KiB
name, overview, todos, isProject
| name | overview | todos | isProject | |||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| 第一档提现或保留余额 | 为 Free Credits 第一档(定格后首笔金额)增加用户二选一:沿用现有独立提现,或新增「保留到可提现余额」(withdraw_balance、不创建打码任务)。涉及 slot_wallet 新钱包原子能力、slot_lib RPC、slot_console 新 C 端接口与档位状态同步。 |
|
false |
第一档:提现或保留到可提现余额
背景与现状
当前第一档(package_type=TYPE_FIRST_CASH)在累计充值解锁后仅支持走 WithdrawService::applyFreeCreditsFirstCashout → Pay 独立提现(bizType=free_credit_first_cashout),不经过钱包余额(需求文档 §15.3)。
后续释放档走 FreeCreditsLogic::claim → WalletLogic::freeCreditsClaim:入账 deposit_balance 并 创建 Y1 打码任务。
新需求:第一档金额用户可二选一:
| 选项 | 行为 |
|---|---|
| Withdraw | 保持现有 /api/withdraw/apply + package_id |
| Keep to balance | 入账 withdraw_balance,不 createTask,金额立即可参与普通提现规则(无其它未完成打码任务时) |
已确认:保留余额入账 withdraw_balance(非 deposit)。
flowchart TD
firstReady[第一档 status=ready]
firstReady --> withdrawPath["POST /api/withdraw/apply"]
firstReady --> keepPath["POST /api/free-credits/keep-first-cash"]
withdrawPath --> payOrder[Pay 独立提现单]
payOrder --> busCallback[EventBus 提现结果]
busCallback --> pkgDone[package completed]
keepPath --> walletKeep[wallet freeCreditsFirstCashKeep]
walletKeep --> pkgDone
pkgDone --> playerDone[player STATUS_FIRST_CASH_DONE]
目标契约
新接口(slot_console)
- 路径:
POST /api/free-credits/keep-first-cash(与现有claim命名风格一致) - 入参:
package_id(必填,free_credits_package.id,须为第一档且status=ready) - 成功:
data结构同status()/claim(buildStatus) - 幂等:
bizId = free_credits_first_keep:{packageId};重复请求不重复入账 - 互斥:同一第一档
processing/completed后不可再提现或 keep;提现处理中不可 keep
档位与玩家状态(与提现成功对齐)
完成后与 handleFirstCashoutResult(success) 一致:
- package →
STATUS_COMPLETED,写completed_time,claim_biz_id存幂等键(复用字段,无需改表) - player →
STATUS_FIRST_CASH_DONE - 调用
refreshPlayerCompletion - 首页状态条关闭逻辑与「第一档提现成功」相同(C 端仍用
status/ packages[0] completed)
钱包(slot_wallet)
新增 freeCreditsFirstCashKeep(WalletLogic::run 按 type 分发):
inc(withdraw=fee, deposit=0, bonus=0)增加 withdraw_balance- 不调用
createTask - 流水:
BIZ_TYPE_FREE_CREDITS_FIRST_KEEP = 'freeCreditsFirstCashKeep',WALLET_TYPE_GIFT(与 freeze/claim 一致) - 事务内完成入账 +
addLog;成功后sendConsoleBus(可选,用于统计/通知,类型建议freeCreditsFirstCashKeep)
对比现有实现:
| 能力 | 入账 | 打码任务 |
|---|---|---|
freeCreditsClaim(后续档) |
deposit | Y1 createTask |
freeCreditsFirstCashKeep(新) |
withdraw | 无 |
slot_lib
WalletService 增加常量与方法:
const WALLET_TYPE_FREE_CREDITS_FIRST_KEEP = 'freeCreditsFirstCashKeep';
public function freeCreditsFirstCashKeep($amount, $bizId = ''): Wallet
实现步骤
1. slot_wallet
| 文件 | 改动 |
|---|---|
WalletLogModel.php |
BIZ_TYPE_FREE_CREDITS_FIRST_KEEP |
WalletLogic.php |
freeCreditsFirstCashKeep():镜像 freeCreditsClaim 事务结构,改为 inc(fee,0,0),删除 createTask 调用 |
| 单测 | 新增 WalletFreeCreditsFirstKeepTest(或扩展现有 wallet 单测):断言 withdraw 增加、无 task 创建(可 mock createTask 不被调用) |
2. slot_lib
WalletService.php:常量 +freeCreditsFirstCashKeep($amount, $bizId)
3. slot_console — Logic
FreeCreditsLogic.php 新增 keepFirstCash(int $uid, int $packageId): array:
assertEligibleParticipant- 查询 package:
uid、TYPE_FIRST_CASH、STATUS_READY bizId = 'free_credits_first_keep:' . $packageId- package →
STATUS_PROCESSING,写claim_biz_id walletService->freeCreditsFirstCashKeep($package->amount_qf, $bizId)- 成功 → package
COMPLETED+ 时间戳;playerSTATUS_FIRST_CASH_DONE;refreshPlayerCompletion - 失败 → package 回滚
READY(同claim) - 返回
buildStatus
不改 advanceByRecharge / 定格冻结逻辑。
4. slot_console — API 层
| 文件 | 改动 |
|---|---|
FreeCreditsValidator.php |
SCENE_KEEP_FIRST_CASH:package_id require|integer |
FreeCreditsController.php |
keepFirstCash() + PHPDoc;类注释补充第二路径 |
| 路由配置 | 注册 POST /api/free-credits/keep-first-cash(查项目现有 route / config 中 free-credits 注册方式,与 claim 并列) |
5. 广播 / 统计(小改)
buildBroadcastList:第一档 completed 若走 keep,广播action可新增keep(或复用claim);与产品确认文案前可先keepFreeCreditsStatsLogic:first_cashout_*按「第一档 completed」统计,keep 与 withdraw 均计入(无需区分,除非运营后续要拆指标)
6. 单测(slot_console)
| 文件 | 内容 |
|---|---|
新增 FreeCreditsKeepFirstCashTest |
harness 注入 mock WalletService;断言状态迁移、幂等、非 ready 抛错 |
| 可选集成测 | keep 后 package completed + player FIRST_CASH_DONE |
运行:
docker exec -w /app/www/slot/slot_console php82 ./vendor/bin/phpunit tests/Unit/FreeCreditsKeepFirstCashTest.php
docker exec -w /app/www/slot/slot_wallet php82 ./vendor/bin/phpunit tests/Unit/WalletFreeCreditsFirstKeepTest.php
C 端约定(供联调,本次可不改 PWA)
第一档 packages[0].status === 1 时展示两个入口:
- Withdraw → 现有
POST /api/withdraw/apply+package_id - Keep to Balance →
POST /api/free-credits/keep-first-cash+package_id
完成后 packages[0].status === 3,与提现成功 UI 一致(按钮隐藏 / 成功态)。
不在本次范围
- slot_pwa / gateway 前端页面与文案
- 需求文档 §10–11 全文修订(可后续补「Add to Balance」分支)
- 修改后续档
claim的打码规则 - 第一档金额改由后台配置动态展示(仍从
packages[0].amount读取)
验收清单
- 第一档 ready:keep 成功 → withdraw_balance 增加对应千分位,无新 WagerTask
- 同一 package 重复 keep:幂等,不重复加钱
- keep 成功后:package/player 状态与提现成功一致;
status接口 packages[0] 为 completed - 第一档 processing(提现中):keep 拒绝
- 第一档 completed:withdraw / keep 均拒绝
- 相关单测通过