bb3559bd51
- app/pay 域新增活动订单模型与事件服务,复用充值支付链路(JSAPI+回调验签+幂等+15 分钟过期+对账补单) - 0027: bookings 加 pay_status/order_no,events 加 price_fen(0=免费) - 运营端桥透传活动定价字段 Co-Authored-By: Claude <noreply@anthropic.com>
70 lines
4.8 KiB
Python
70 lines
4.8 KiB
Python
# -*- coding: utf-8 -*-
|
||
"""支付子应用 ORM:算力充值订单 + 活动报名订单(落平台主库,alembic 统一迁移)。"""
|
||
from __future__ import annotations
|
||
|
||
from sqlalchemy import Integer, String, Text
|
||
from sqlalchemy.orm import Mapped, mapped_column
|
||
|
||
from ..infrastructure.db import Base
|
||
|
||
|
||
class ComputeRechargeOrder(Base):
|
||
"""算力充值订单(微信支付 V3)。
|
||
|
||
状态机:pending → paid(支付成功,本地终态)→ credited(引擎到账完成);
|
||
pending 超时未支付 → closed;到账异常 → failed(待人工/对账补单)。
|
||
"""
|
||
__tablename__ = "compute_recharge_orders"
|
||
|
||
id: Mapped[str] = mapped_column(String, primary_key=True) # cr_<hex>
|
||
order_no: Mapped[str] = mapped_column(String, unique=True, index=True) # CR_<ts>_<hex8>,微信 out_trade_no
|
||
user_id: Mapped[str] = mapped_column(String, default="", index=True) # 平台 users.id
|
||
username: Mapped[str] = mapped_column(String, default="", index=True) # 平台/引擎用户名(充值归集键)
|
||
engine_user_id: Mapped[int] = mapped_column(Integer, default=0) # 引擎用户 id(下单时解析缓存,0=待解析)
|
||
package_id: Mapped[str] = mapped_column(String, default="") # 套餐 id;空 = 自由金额
|
||
amount_fen: Mapped[int] = mapped_column(Integer, default=0) # 实付金额(分,微信口径)
|
||
quota_micro: Mapped[int] = mapped_column(Integer, default=0) # 到账微元 = amount_fen//100 * 1_000_000
|
||
bonus_quota_micro: Mapped[int] = mapped_column(Integer, default=0) # 套餐赠送微元
|
||
client_type: Mapped[str] = mapped_column(String, default="native") # native(扫码) | jsapi(小程序)
|
||
appid: Mapped[str] = mapped_column(String, default="") # 下单所用 appid(对账依据)
|
||
status: Mapped[str] = mapped_column(String, default="pending", index=True) # pending|paid|credited|closed|failed
|
||
prepay_id: Mapped[str] = mapped_column(String, default="") # 微信预支付单号(jsapi)
|
||
transaction_id: Mapped[str] = mapped_column(String, default="", index=True) # 微信支付单号
|
||
code_url: Mapped[str] = mapped_column(String, default="") # Native 二维码内容
|
||
expires_at: Mapped[str] = mapped_column(String, default="") # 过期时刻(ISO,超时未付 → closed)
|
||
paid_at: Mapped[str] = mapped_column(String, default="")
|
||
credited_at: Mapped[str] = mapped_column(String, default="") # 引擎到账完成时刻
|
||
notify_payload: Mapped[str] = mapped_column(Text, default="") # 回调/查单原始报文(JSON 串,排查用)
|
||
created_at: Mapped[str] = mapped_column(String, default="", index=True)
|
||
updated_at: Mapped[str] = mapped_column(String, default="")
|
||
|
||
|
||
class EventOrder(Base):
|
||
"""活动报名订单(微信支付 V3,课程/沙龙定价)。
|
||
|
||
状态机与充值订单一致:pending → paid(支付成功)→ credited(报名确认完成);
|
||
pending 超时未支付 → closed;确认异常 → failed(对账补单)。
|
||
"""
|
||
__tablename__ = "event_orders"
|
||
|
||
id: Mapped[str] = mapped_column(String, primary_key=True) # ev_<hex>
|
||
order_no: Mapped[str] = mapped_column(String, unique=True, index=True) # EV_<ts>_<hex8>,微信 out_trade_no
|
||
booking_id: Mapped[str] = mapped_column(String, default="", index=True) # bookings.id
|
||
event_id: Mapped[str] = mapped_column(String, default="", index=True) # events.id
|
||
event_title: Mapped[str] = mapped_column(String, default="")
|
||
user_id: Mapped[str] = mapped_column(String, default="", index=True) # 平台 users.id
|
||
username: Mapped[str] = mapped_column(String, default="", index=True)
|
||
openid: Mapped[str] = mapped_column(String, default="") # JSAPI 支付 openid(下单人)
|
||
amount_fen: Mapped[int] = mapped_column(Integer, default=0) # 实付金额(分)
|
||
client_type: Mapped[str] = mapped_column(String, default="jsapi")
|
||
appid: Mapped[str] = mapped_column(String, default="")
|
||
status: Mapped[str] = mapped_column(String, default="pending", index=True) # pending|paid|credited|closed|failed
|
||
prepay_id: Mapped[str] = mapped_column(String, default="")
|
||
transaction_id: Mapped[str] = mapped_column(String, default="", index=True)
|
||
expires_at: Mapped[str] = mapped_column(String, default="")
|
||
paid_at: Mapped[str] = mapped_column(String, default="")
|
||
credited_at: Mapped[str] = mapped_column(String, default="")
|
||
notify_payload: Mapped[str] = mapped_column(Text, default="")
|
||
created_at: Mapped[str] = mapped_column(String, default="", index=True)
|
||
updated_at: Mapped[str] = mapped_column(String, default="")
|