diff --git a/app/api/v1/wallet.py b/app/api/v1/wallet.py index 8641cf2..29a0407 100644 --- a/app/api/v1/wallet.py +++ b/app/api/v1/wallet.py @@ -202,6 +202,9 @@ def withdraw(req: WithdrawRequest, user: CurrentUser, db: DbSession) -> Withdraw order = crud_wallet.create_withdraw( db, user.id, req.amount_cents, source=req.source, user_name=req.user_name, out_bill_no=req.out_bill_no, + # 0.01 元调试提现:放行低于最低额的小额。双闸——客户端仅 debug 包在「0.01 元提现」开关开时 + # 连同 skip_review 一起下发;服务端仅非 prod 才认。生产恒 False,最低额校验照常。 + allow_sub_min=(req.skip_review and not settings.is_prod), ) except crud_wallet.InvalidWithdrawAmountError as e: raise HTTPException( diff --git a/app/repositories/invite.py b/app/repositories/invite.py index 7fd7dbc..8dbd290 100644 --- a/app/repositories/invite.py +++ b/app/repositories/invite.py @@ -216,13 +216,21 @@ def try_reward_on_compare(db: Session, invitee_user_id: int) -> CompareRewardRes def get_stats(db: Session, inviter_id: int) -> tuple[int, int]: """返回 (已成功邀请人数, 累计从邀请获得的金币)。 + "已邀请好友数"口径 = 完成一次比价(已触发邀请奖励金)的被邀请人数,即 compare_reward_granted=True。 + 不再数"仅绑定未比价"的关系——否则会出现"已邀请 1、可提现余额 0"(好友下载登录但没比价), + 与产品口径"已邀请好友数 × 2元 = 累计提现 + 可提现余额"对不上。过滤后该恒等式天然成立 + (每个计入的好友都恰好发过 1 笔 2 元,钱要么在余额要么已提现)。 + 金币口径(inviter_coin 之和)自 v3 起恒 0(邀请人收益改走邀请奖励金,见 get_reward_stats / try_reward_on_compare);保留返回位兼容旧响应字段 coins_earned。 """ count = db.execute( select(func.count()) .select_from(InviteRelation) - .where(InviteRelation.inviter_user_id == inviter_id) + .where( + InviteRelation.inviter_user_id == inviter_id, + InviteRelation.compare_reward_granted.is_(True), + ) ).scalar_one() coins = db.execute( select(func.coalesce(func.sum(InviteRelation.inviter_coin), 0)) diff --git a/app/repositories/wallet.py b/app/repositories/wallet.py index 611bbc9..1edd034 100644 --- a/app/repositories/wallet.py +++ b/app/repositories/wallet.py @@ -610,6 +610,7 @@ def create_withdraw( source: str = "coin_cash", user_name: str | None = None, out_bill_no: str | None = None, + allow_sub_min: bool = False, ) -> WithdrawOrder: """发起提现:原子扣款 + 建单 reviewing(待人工审核),**不打款**。 @@ -619,8 +620,13 @@ def create_withdraw( 重复发起多笔提现(审核拒绝再退回)。 #2 out_bill_no 客户端幂等键:同号重试返回该单现状(reviewing 等审核),不重复扣款建单。 实名 user_name 在此存下(WithdrawOrder.user_name),供异步审核打款时传给微信(达额需实名)。 + + allow_sub_min:放行低于"提现最低额"的小额(用于 0.01 元调试提现)。仅由 endpoint 在 + `skip_review and not is_prod`(debug 包 + 非生产双闸)时置 True;仍受 schema gt=0 与 max 上限约束。 + 生产恒为 False → 最低额校验照常,绝不可能提 0.01。 """ - if amount_cents < rewards.get_withdraw_min_cents(db) or amount_cents > rewards.get_withdraw_max_cents(db): + min_c = 0 if allow_sub_min else rewards.get_withdraw_min_cents(db) + if amount_cents < min_c or amount_cents > rewards.get_withdraw_max_cents(db): raise InvalidWithdrawAmountError # 提现即要求已绑微信:否则审核通过也打不了款,提前拦更友好