erio
cee24c3afb
fix: 修复 isAlipayDirect 变量声明顺序导致构建失败
...
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com >
2026-03-06 16:34:01 +08:00
erio
dc78a41912
fix: alipay_direct 桌面端跳转到支付宝收银台而非显示二维码
...
alipay.trade.page.pay 返回的 payUrl 是跳转链接,不应作为
二维码内容展示。改为显示"前往支付宝收银台"按钮,在新标签页
打开支付宝收银台页面。
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com >
2026-03-06 16:32:50 +08:00
erio
f53aa9e14c
feat: 支持官方支付宝与易支付支付宝同时展示
...
- PaymentType 改为 string 类型,支持复合 key(如 alipay_direct)
- 官方支付宝注册为 alipay_direct,易支付保持 alipay/wxpay
- 前端按 PAYMENT_TYPE_META 展示标签区分(官方直连/易支付)
- 管理后台显示统一改为 getPaymentTypeLabel 通用映射
- 修复 admin/OrderTable 中 wechat 拼写错误
2026-03-06 15:33:22 +08:00
erio
0a35ba9002
style: 全量 prettier 格式化
2026-03-05 23:10:44 +08:00
erio
ab961e669a
fix: 修复 lint errors(hooks 条件调用、未转义引号、effect 内 setState)
2026-03-05 23:08:48 +08:00
eriol touwa
93a417b312
Merge pull request #4 from dexcoder6/feat/admin-dashboard
...
fix: 数据看板时区统一为 Asia/Shanghai + 订单列表支付方式显示修复
2026-03-05 23:03:24 +08:00
erio
448d36fe2b
feat: 移动端 H5 支付跳转 + 改进移动端检测
...
- PaymentQRCode: 移动端有 payUrl 时直接跳转支付,iframe 中新窗口打开
- detectDeviceIsMobile: 优先使用 navigator.userAgentData.mobile API
2026-03-05 16:21:12 +08:00
miwei
f1e3fd35ef
fix: 数据看板时区统一为 Asia/Shanghai + 订单列表支付方式显示修复
...
- dashboard API 日期计算和 SQL GROUP BY 统一使用东八区,避免 UTC 服务器上"今日"统计偏移
- OrderTable 支付方式显示支持 stripe/wechat/alipay 三种,修复 stripe 误显为微信支付
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com >
2026-03-05 10:13:57 +08:00
erio
9a90a7ebb9
fix: embedded 模式下也强制 min-h-screen,防止 dark 模式底部白底
2026-03-04 21:55:43 +08:00
miwei
3a9a32e2c2
feat: 管理后台数据看板
...
新增 /admin/dashboard 页面,提供充值订单统计与分析:
- 汇总统计卡片(今日/累计充值金额、订单数、成功率、平均充值)
- 每日充值趋势折线图(recharts,支持 7/30/90 天切换)
- 充值排行榜(Top 10 用户)
- 支付方式分布(水平条形图)
- 与 /admin 订单管理页面互相导航
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com >
2026-03-04 17:06:27 +08:00
miwei
d7d91857c7
fix: Stripe 弹窗安全加固 + 清理未使用依赖
...
安全修复:
- client_secret 和 publishableKey 不再通过 URL 传递,改用 postMessage
弹窗发送 STRIPE_POPUP_READY 信号,父页面响应 STRIPE_POPUP_INIT 传递敏感数据
校验 event.origin 防止跨域消息伪造
- confirmAlipayPayment 改为显式调用,移除动态方法查找
- handleStripeSubmit 中 returnUrl 清理残留 query params
依赖清理:
- 移除未使用的 @stripe/react-stripe-js
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com >
2026-03-04 15:27:51 +08:00
miwei
964a2aa6d9
feat: Stripe 改用 PaymentIntent + Payment Element,iframe 嵌入支付宝弹窗支付
...
Stripe 集成重构:
- 从 Checkout Session 改为 PaymentIntent + Payment Element 模式
- 前端内联渲染 Stripe 支付表单,支持信用卡、支付宝等多种方式
- Webhook 事件改为 payment_intent.succeeded / payment_intent.payment_failed
- provider/test 同步更新
iframe 嵌入模式 (ui_mode=embedded):
- 支付宝等需跳转的方式改为弹出新窗口处理,避免 X-Frame-Options 冲破 iframe
- 信用卡等无跳转方式仍在 iframe 内联完成
- 弹窗使用 confirmAlipayPayment 直接跳转,无需二次操作
- result 页面检测弹窗模式,支付成功后自动关闭窗口
Bug 修复:
- 修复配置加载前支付方式闪烁(初始值改为空数组 + loading)
- 修复桌面端 PaymentForm 缺少 methodLimits prop
- 修复 stripeError 隐藏表单导致无法重试
- 快捷金额增加 1000/2000 选项,过滤低于 minAmount 的选项
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com >
2026-03-04 11:11:46 +08:00
erio
5be0616e78
feat: 支付手续费功能
...
- 支持提供商级别和渠道级别手续费率配置(FEE_RATE_PROVIDER_* / FEE_RATE_*)
- 用户多付手续费,到账金额不变(充值 ¥100 + 1.6% = 实付 ¥101.60)
- 前端显示手续费明细和实付金额
- 退款时按实付金额退款,余额扣减到账金额
2026-03-03 22:00:44 +08:00
erio
52aa484202
feat: 列表页占满宽度,充值页保持居中卡片,嵌入模式优化
...
- maxWidth 新增 'lg' 选项(max-w-6xl),'full' 改为无限制
- 充值页 PC 端使用 'lg',管理后台/我的订单使用 'full' 占满宽度
- 嵌入模式:减小外边距、隐藏装饰光斑、取消 min-h-screen
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com >
2026-03-03 05:54:46 +08:00
erio
42da18484c
feat: 管理后台订单列表展示用户备注,用户信息摊平显示
...
- 新增 userNotes 字段,创建订单时从 Sub2API 读取用户 notes 保存
- 管理后台订单列表将用户名、邮箱、备注拆分为独立列,节约行高
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com >
2026-03-03 04:37:39 +08:00
erio
880f0211f3
feat: 管理后台统一 PayPageLayout 布局,支持 dark mode
...
管理后台使用与充值页面相同的 PayPageLayout 组件,OrderTable 和
OrderDetail 组件新增 dark prop,所有样式支持暗色模式切换。
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com >
2026-03-03 03:31:20 +08:00
erio
c9462f4f14
feat: 管理后台订单列表显示来源域名(srcHost)
...
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com >
2026-03-03 00:19:01 +08:00
erio
d952942627
feat: 订单来源追踪,保存 src_host / src_url 到订单记录
...
iframe 嵌入充值页面时 URL 自动附带来源参数,写入数据库用于追踪分析。
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com >
2026-03-02 20:40:16 +08:00
erio
85239e97f8
fix: 用户不存在时前端提示错误;修正微信支付图标;beta compose 改用 Docker Hub 镜像
2026-03-02 01:05:01 +08:00
erio
c6815fc2a3
feat: 插件化支付渠道限额 — provider 自声明单笔/每日默认限额
...
- PaymentProvider 接口新增 defaultLimits(单笔 singleMax + 每日 dailyMax)
- EasyPay 默认:支付宝/微信各 单笔 ¥1000、每日 ¥10000
- Stripe 默认:不限额(0 = unlimited)
- getMethodDailyLimit / getMethodSingleLimit 优先读 env var,再回退 provider 默认
- queryMethodLimits 返回 singleMax,PaymentForm 按渠道动态调整最大单笔金额
- MAX_DAILY_AMOUNT_* 改为可选 env var 覆盖(不再有硬编码默认值)
2026-03-01 22:51:09 +08:00
erio
136723b8af
feat: 支付渠道每日限额(渠道维度全平台统计)
...
- config.ts:新增 MAX_DAILY_AMOUNT_ALIPAY/WXPAY/STRIPE(默认 alipay/wxpay 各 1w,stripe 不限)
- lib/order/limits.ts:getMethodDailyLimit + queryMethodLimits 共用工具,支持动态渠道兜底
- order/service.ts:createOrder 校验渠道限额,超限抛 METHOD_DAILY_LIMIT_EXCEEDED
- api/limits/route.ts:公开接口 GET /api/limits,返回各渠道今日用量/剩余/是否可用
- api/user/route.ts:config 响应中加入 methodLimits,前端一次请求即可获取限额状态
- PaymentForm.tsx:额度已满的渠道置灰 + 标注「今日额度已满」,无法选择
- pay/page.tsx:AppConfig 加 methodLimits,传给 PaymentForm,新增错误码映射
2026-03-01 21:53:09 +08:00
erio
b4eebb0b1b
feat: 分页组件统一封装 + 移动端无限滚动
...
- 新增 PaginationBar 组件,支持 isDark / loading / 页码导航 / 每页大小切换
- 重写 pay/orders/page.tsx 使用 PaginationBar,summary 来自 API groupBy 全量统计
- admin/page.tsx 替换内联分页 UI 为 PaginationBar
- MobileOrderList 支持无限滚动:IntersectionObserver 哨兵 + hasMore/loadingMore props
- pay/page.tsx 新增 loadMoreOrders(append 模式),初始化/刷新时重置分页状态
2026-03-01 20:12:32 +08:00
erio
4374ca9126
feat: 每日充值限额 + 单笔上限默认 1000 + 前端金额校验优化
...
- 新增 MAX_DAILY_RECHARGE_AMOUNT 环境变量(0=不限制),
创建订单时统计当日已付款总额,超限返回友好提示
- MAX_RECHARGE_AMOUNT 默认值从 10000 改为 1000
- PaymentForm 快速金额按钮过滤掉超过 maxAmount 的选项
- 金额超限时前端显示明确提示(单笔最低/最高 ¥xxx)
- 支付说明栏展示每日限额信息
2026-03-01 19:41:44 +08:00
erio
c41933db70
security: 隐私接口全面加固,统一 token 鉴权
...
- /api/orders/[id] 只返回 id/status/expiresAt,移除 user_name/pay_url 等隐私字段
- /api/orders/[id]/cancel 改为 token 鉴权,服务端验证用户身份后执行取消
- /api/orders (POST 响应) 过滤 userName/userBalance,不向客户端暴露
- /api/user 移除 username/email/balance,只返回 id/status 和 config
- /api/users/[id] 只返回 {id, exists},不暴露任何隐私信息
- pay/page.tsx 恢复从服务端动态获取 config,无 token 时只显示用户 ID
- pay/orders/page.tsx 无 token 时不查询隐私接口,统一按钮样式
- PaymentQRCode 新增 token prop,无 token 时隐藏取消按钮
- 创建订单失败改为中文错误提示
2026-03-01 19:25:14 +08:00
erio
5a315a8f08
refactor: unify cancel logic with cancelOrderCore and show blocked UI
...
- Extract cancelOrderCore() shared by user cancel, admin cancel, and timeout expire
- Query payment platform before cancelling: if already paid, run confirmPayment
- Simplify timeout.ts to delegate to cancelOrderCore
- Cancel API returns already_paid outcome for frontend handling
- Show "订单已支付,无法取消" prompt with back button when cancel is blocked
2026-03-01 18:44:49 +08:00
erio
5751638f7b
fix: handle cancel when order already paid — check status immediately
...
When cancel API returns error (order already PAID/COMPLETED), immediately
re-poll the order status instead of silently doing nothing. Also check
terminal status before attempting cancel to avoid unnecessary API call.
2026-03-01 18:15:52 +08:00
erio
d9ab65ecf2
feat: integrate Stripe payment with bugfixes and active timeout cancellation
...
- Add Stripe payment provider with Checkout Session flow
- Payment provider abstraction layer (EasyPay + Stripe unified interface)
- Stripe webhook with proper raw body handling and signature verification
- Frontend: Stripe button with URL validation, anti-duplicate click, noopener
- Active timeout cancellation: query platform before expiring, recover paid orders
- Singleton Stripe client, idempotency keys, Math.round for amounts
- Handle async_payment events, return null for unknown webhook events
- Set Checkout Session expires_at aligned with order timeout
- Add cancelPayment to provider interface (Stripe: sessions.expire, EasyPay: no-op)
- Enable stripe in frontend payment type list
2026-03-01 17:58:08 +08:00
erio
2f45044073
refactor: extract pay page components and migrate zpay → easypay
...
Components:
- Add PayPageLayout, OrderFilterBar, MobileOrderList, OrderTable, OrderSummaryCards
- Extract shared pay-utils (types, constants, helper functions)
- Simplify pay/page.tsx and orders/page.tsx
EasyPay migration:
- Remove src/lib/zpay/, api/zpay/notify, zpay test, zpay.md
- Simplify config.ts: single envSchema, no ZPAY_* fallback
- Rename DB field zpay_trade_no → payment_trade_no (migration added)
- Update OrderDetail label: ZPAY订单号 → 支付单号
- Update CLAUDE.md project structure
2026-03-01 15:55:43 +08:00
erio
75f521e2cd
fix: add dark prop to OrderStatus component
2026-03-01 14:22:17 +08:00
erio
d5719bf213
feat: migrate payment provider to easy-pay, add order history and refund support
...
- Replace zpay with easy-pay payment provider (new lib/easy-pay/ module)
- Add order history page for users (pay/orders)
- Add GET /api/orders/my endpoint to list user's own orders
- Add GET /api/users/[id] endpoint for sub2api user lookup
- Add order status tracking module (lib/order/status.ts)
- Update config to support easy-pay credentials (merchant ID, key, gateway)
- Update PaymentForm and PaymentQRCode components for easy-pay flow
- Update pay page and admin page with new order management UI
- Update order service to support easy-pay, cancellation, and refund
2026-03-01 03:04:24 +08:00