🎨 新增支付动态配置&优化支付回调&新增三方支付

This commit is contained in:
2025-12-09 21:47:22 +08:00
parent eaa5cdc100
commit 854c16e11c
26 changed files with 2963 additions and 72 deletions

View File

@@ -5,6 +5,8 @@ import (
"git.echol.cn/loser/lckt/model/app"
"git.echol.cn/loser/lckt/model/app/request"
r "git.echol.cn/loser/lckt/model/common/response"
"git.echol.cn/loser/lckt/model/system"
"git.echol.cn/loser/lckt/utils/pay"
"git.echol.cn/loser/lckt/utils/user_jwt"
"git.echol.cn/loser/lckt/utils/wechat"
"github.com/gin-gonic/gin"
@@ -13,6 +15,57 @@ import (
type OrderApi struct{}
// GetPayMethods 获取可用的支付方式列表(用户端)
// @Summary 获取可用的支付方式列表
// @Description 获取所有启用的支付配置返回前端所需的mode字段
// @Tags 订单
// @Accept application/json
// @Produce application/json
// @Success 200 {object} r.Response{data=[]PayMethodVO} "获取成功"
// @Router /app_order/pay_methods [get]
func (o *OrderApi) GetPayMethods(c *gin.Context) {
var payConfigs []system.PayConfig
if err := global.GVA_DB.Where("enable = ?", true).
Order("sort ASC").
Find(&payConfigs).Error; err != nil {
global.GVA_LOG.Error("获取支付方式列表失败", zap.Error(err))
r.FailWithMessage("获取失败", c)
return
}
// 返回前端所需的支付方式信息
type PayMethodVO struct {
Name string `json:"name"` // 支付名称,如"神奇支付-主账号"
Code string `json:"code"` // 支付配置编码,如"shenqi_main"
Type string `json:"type"` // 支付类型: wechat/shenqi
Modes []string `json:"modes"` // 可用的支付模式
Remark string `json:"remark"` // 备注说明
}
var methods []PayMethodVO
for _, config := range payConfigs {
// 使用 GetAvailableModes 方法获取实际启用的模式
availableModes := config.GetAvailableModes()
// 如果没有可用模式,跳过该配置
if len(availableModes) == 0 {
continue
}
method := PayMethodVO{
Name: config.Name,
Code: config.Code,
Type: config.Type,
Modes: availableModes,
Remark: config.Remark,
}
methods = append(methods, method)
}
r.OkWithData(methods, c)
}
// CreateOrder APP新建订单
func (o *OrderApi) CreateOrder(c *gin.Context) {
var p app.Order
@@ -62,6 +115,83 @@ func (o *OrderApi) NotifyOrder(context *gin.Context) {
r.OkWithMessage("微信支付回调处理成功", context)
}
// ShenqiPayNotify 神奇支付回调通知
// @Summary 神奇支付回调通知
// @Description 处理神奇支付平台的支付结果通知
// @Tags 订单
// @Accept x-www-form-urlencoded
// @Produce plain
// @Param code path string false "支付配置编码"
// @Success 200 {string} string "success"
// @Failure 400 {string} string "fail"
// @Router /app_order/shenqi/notify/{code} [get]
func (o *OrderApi) ShenqiPayNotify(c *gin.Context) {
// 获取支付配置编码
payCode := c.Param("code")
var client *pay.Client
var err error
if payCode != "" {
// 从数据库获取配置
var config system.PayConfig
if err := global.GVA_DB.Where("code = ? AND enable = ?", payCode, true).First(&config).Error; err != nil {
global.GVA_LOG.Error("获取神奇支付配置失败", zap.String("code", payCode), zap.Error(err))
c.String(400, "fail")
return
}
// 验证支付类型
if config.Type != "shenqi" {
global.GVA_LOG.Error("支付配置类型错误", zap.String("type", config.Type))
c.String(400, "fail")
return
}
// 获取神奇支付配置
shenqiConfig := config.GetShenqiConfig()
client, err = pay.NewClient(pay.Config{
PID: shenqiConfig.PID,
PrivateKey: shenqiConfig.PrivateKey,
PlatformPubKey: shenqiConfig.PlatformPubKey,
BaseURL: shenqiConfig.BaseURL,
})
} else {
// 兼容旧配置:从配置文件读取
if !global.GVA_CONFIG.ShenqiPay.Enable {
global.GVA_LOG.Error("神奇支付未启用")
c.String(400, "fail")
return
}
client, err = pay.NewClient(pay.Config{
PID: global.GVA_CONFIG.ShenqiPay.PID,
PrivateKey: global.GVA_CONFIG.ShenqiPay.PrivateKey,
PlatformPubKey: global.GVA_CONFIG.ShenqiPay.PlatformPubKey,
BaseURL: global.GVA_CONFIG.ShenqiPay.BaseURL,
})
}
if err != nil {
global.GVA_LOG.Error("创建神奇支付客户端失败", zap.Error(err))
c.String(400, "fail")
return
}
// 创建回调处理器并处理通知
handler := pay.NewNotifyHandler(client)
_, err = handler.HandleNotify(c.Request.URL.Query())
if err != nil {
global.GVA_LOG.Error("神奇支付回调处理失败", zap.Error(err))
c.String(400, "fail")
return
}
// 返回 success 告知支付平台处理成功
c.String(200, "success")
}
// GetOrderDetail 获取订单详情
func (o *OrderApi) GetOrderDetail(context *gin.Context) {
id := context.Param("id")

View File

@@ -3,13 +3,14 @@ package app
import (
"errors"
"fmt"
common "git.echol.cn/loser/lckt/model/common/request"
user2 "git.echol.cn/loser/lckt/model/user"
"gorm.io/gorm"
"net/http"
"strconv"
"time"
common "git.echol.cn/loser/lckt/model/common/request"
user2 "git.echol.cn/loser/lckt/model/user"
"gorm.io/gorm"
"git.echol.cn/loser/lckt/global"
"git.echol.cn/loser/lckt/model/app"
r "git.echol.cn/loser/lckt/model/common/response"
@@ -269,19 +270,6 @@ func (*AppUserApi) PwdLogin(ctx *gin.Context) {
}
}()
adcodes := utils.CheckIPInAdcodes(loginLog.Address)
if !adcodes {
global.GVA_LOG.Warn("异常登录地址", zap.String("address", loginLog.Address), zap.Uint("userId", user.ID))
user.Status = 0
if err := global.GVA_DB.Save(&user).Error; err != nil {
global.GVA_LOG.Error("禁用用户失败!", zap.Error(err))
}
r.Banned("用户已被禁用", ctx)
return
}
// 生成token
token, claims, err := user_jwt.LoginToken(user)
if err != nil {