From de1f1d01fc1a8a081693cef8ccb6d98a630174a3 Mon Sep 17 00:00:00 2001 From: wolter Date: Fri, 6 Dec 2024 15:23:57 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20=E5=BE=AE=E4=BF=A1=E6=94=AF=E4=BB=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/constants/errorcode/error_code.go | 5 +++++ .../controllers/front/payment_controller.go | 4 ++-- app/http/entities/front/pay.go | 1 + app/http/entities/front/wechat.go | 16 +++++++++++++--- app/services/thirdpay/do/pay.go | 4 ++++ app/services/thirdpay/do/pay_way.go | 14 ++++++++++++-- app/services/wecaht.go | 19 +++++++++++++++---- app/third/paymentService/payment_service.go | 1 + app/third/paymentService/wechat_service.go | 3 +++ app/utils/httpclient/fasthttp.go | 3 --- 10 files changed, 56 insertions(+), 14 deletions(-) diff --git a/app/constants/errorcode/error_code.go b/app/constants/errorcode/error_code.go index 8e52b96..d452264 100644 --- a/app/constants/errorcode/error_code.go +++ b/app/constants/errorcode/error_code.go @@ -96,6 +96,9 @@ const ( // 退款 RefundOutTradeNoSame = 1801 + + // 微信授权 + WechatAuthFail = 1901 ) var MsgEN = map[int]string{ @@ -178,6 +181,8 @@ var MsgZH = map[int]string{ CloseOrderPayed: "订单已支付成功,无法关闭", ThirdRefundFail: "第三方退款失败", + + WechatAuthFail: "微信授权失败", } var MsgMap map[string]map[int]string = map[string]map[int]string{"en": MsgZH} diff --git a/app/http/controllers/front/payment_controller.go b/app/http/controllers/front/payment_controller.go index b8459df..26f5596 100644 --- a/app/http/controllers/front/payment_controller.go +++ b/app/http/controllers/front/payment_controller.go @@ -208,6 +208,6 @@ func GetWxAuthUrl(c *gin.Context) { // 通过code获取授权,openid func GetWxAuth(c *gin.Context) { req, _ := controllers.GetRequest(c).(*front.GetWxAuthRequest) - code := services.GetWxAuth(*req) - controllers.HandCodeRes(c, code, code) + rsp, code := services.GetWxAuth(*req) + controllers.HandCodeRes(c, rsp, code) } diff --git a/app/http/entities/front/pay.go b/app/http/entities/front/pay.go index 2d9540e..291cdf0 100644 --- a/app/http/entities/front/pay.go +++ b/app/http/entities/front/pay.go @@ -19,6 +19,7 @@ type PayCommonReqBody struct { ExtJson string `json:"ext_json" label:"扩展参数"` Desc string `json:"desc" validate:"max=100" label:"商品描述"` ReturnUrl string `json:"return_url" validate:"max=1024" label:"支付成功后跳转的地址"` + OpenId string `json:"open_id" label:"用户openid"` } type PayReqs struct { diff --git a/app/http/entities/front/wechat.go b/app/http/entities/front/wechat.go index 3964c08..a5da351 100644 --- a/app/http/entities/front/wechat.go +++ b/app/http/entities/front/wechat.go @@ -5,7 +5,17 @@ type GetWxAuthUrlRequest struct { } type GetWxAuthRequest struct { - Code string `json:"code" form:"code" ` - State string `json:"state" form:"state"` - PayChannelId string `json:"pay_channel_id" form:"pay_channel_id"` + Code string `json:"code" form:"code" ` + State string `json:"state" form:"state"` +} + +// 获取微信用户信息 +type GetWxAuthResponse struct { + AccessToken string `json:"access_token"` //网页授权接口调用凭证,注意:此access_token与基础支持的access_token不同 + ExpiresIn int `json:"expires_in"` //access_token接口调用凭证超时时间,单位(秒) + RefreshToken string `json:"refresh_token"` //用户刷新access_token + Openid string `json:"openid"` //用户唯一标识,请注意,在未关注公众号时,用户访问公众号的网页,也会产生一个用户和公众号唯一的OpenID + Scope string `json:"scope"` //用户授权的作用域,使用逗号(,)分隔 + IsSnapshotuser int `json:"is_snapshotuser"` + Unionid string `json:"unionid"` // 用户统一标识(针对一个微信开放平台账号下的应用,同一用户的 unionid 是唯一的),只有当scope为"snsapi_userinfo"时返回 } diff --git a/app/services/thirdpay/do/pay.go b/app/services/thirdpay/do/pay.go index 2b7670b..32d8ce2 100644 --- a/app/services/thirdpay/do/pay.go +++ b/app/services/thirdpay/do/pay.go @@ -25,6 +25,7 @@ type PayParam struct { Desc string ClientIp string ReturnUrl string + OpenId string } type Pay struct { @@ -50,6 +51,7 @@ func NewPayWithPayCheck(paycheck *PayCheck) *Pay { Desc: paycheck.Reqs.Desc, ClientIp: paycheck.AppCheck.Ip, ReturnUrl: paycheck.Reqs.ReturnUrl, + OpenId: paycheck.Reqs.OpenId, }, RelationOrder: paycheck.OldOrder, PayCode: errorcode.Success, @@ -106,7 +108,9 @@ func (w *Pay) PayUrl() (url string) { Amount: w.Order.Amount, PayerClientIp: w.PayParam.ClientIp, ReturnUrl: w.PayParam.ReturnUrl, + OpenId: w.PayParam.OpenId, } + // 判断是否是支持的支付渠道,找到对应的配置 if payFunc, ok = PayWayList[w.PayParam.Channel.ChannelType]; !ok { w.PayCode = errorcode.PayChannelNotBuild return diff --git a/app/services/thirdpay/do/pay_way.go b/app/services/thirdpay/do/pay_way.go index 8d43ae9..34d0c56 100644 --- a/app/services/thirdpay/do/pay_way.go +++ b/app/services/thirdpay/do/pay_way.go @@ -7,9 +7,11 @@ import ( "github.com/bytedance/sonic" ) +// 支持的支付方式 var PayWayList = map[int]func(commonPayInfo *paymentService.PayOrderRequest, channel *paychannelmodel.PayChannel) error{ - common.PAY_CHANNEL_WECHAT_H5: WechatH5, - common.PAY_CHANNEL_ALIPAY_WEB: AlipayWeb, + common.PAY_CHANNEL_WECHAT_H5: WechatH5, + common.PAY_CHANNEL_ALIPAY_WEB: AlipayWeb, + common.PAY_CHANNEL_WECHAT_JSAPI: WechatJSAPI, } func WechatH5(commonPayInfo *paymentService.PayOrderRequest, channel *paychannelmodel.PayChannel) error { @@ -29,3 +31,11 @@ func AlipayWeb(commonPayInfo *paymentService.PayOrderRequest, channel *paychanne commonPayInfo.Ali.AppId = channel.AppId return nil } +func WechatJSAPI(commonPayInfo *paymentService.PayOrderRequest, channel *paychannelmodel.PayChannel) error { + err := sonic.Unmarshal([]byte(channel.ExtJson), &commonPayInfo.Wx) + if err != nil { + return err + } + commonPayInfo.Wx.AppId = channel.AppId + return nil +} diff --git a/app/services/wecaht.go b/app/services/wecaht.go index b37246f..388831e 100644 --- a/app/services/wecaht.go +++ b/app/services/wecaht.go @@ -50,11 +50,11 @@ func GetWxAuthUrl(param front.GetWxAuthUrlRequest) (targetUrl string, code int) return } -// // 通过code换取网页授权access_token -func GetWxAuth(param front.GetWxAuthRequest) (code int) { +// // 通过code换取网页授权access_token,openid +func GetWxAuth(param front.GetWxAuthRequest) (rsp front.GetWxAuthResponse, code int) { // 获取支付渠道的配置 - id, err := strconv.Atoi(param.PayChannelId) + id, err := strconv.Atoi(param.State) if err != nil { code = handErr(err) return @@ -65,7 +65,7 @@ func GetWxAuth(param front.GetWxAuthRequest) (code int) { return } - //// 配置解析 + //// 配置支付的解析 wxConfig := make(map[string]interface{}) err = json.Unmarshal([]byte(payChannel.ExtJson), &wxConfig) if err != nil { @@ -95,5 +95,16 @@ func GetWxAuth(param front.GetWxAuthRequest) (code int) { } utils.Log(nil, "获取微信授权信息", string(response), targetUrl) + // 解析返回数据 + err = json.Unmarshal(response, &rsp) + if err != nil { + code = handErr(err) + return + } + if rsp.Openid == "" { + code = errorcode.WechatAuthFail + return + } + code = handErr(err) return } diff --git a/app/third/paymentService/payment_service.go b/app/third/paymentService/payment_service.go index f2d681a..31c3978 100644 --- a/app/third/paymentService/payment_service.go +++ b/app/third/paymentService/payment_service.go @@ -30,6 +30,7 @@ type WxPay struct { SerialNo string `json:"serial_no"` // 商户证书的证书序列号 ApiV3Key string `json:"api_v_3_key"` // apiV3Key,商户平台获取 PrivateKey string `json:"private_key"` // 私钥 apiclient_key.pem 读取后的内容 + Secret string `json:"secret"` // 商户私钥,读取后的内容 } type AliPay struct { diff --git a/app/third/paymentService/wechat_service.go b/app/third/paymentService/wechat_service.go index e255ece..9ccdec2 100644 --- a/app/third/paymentService/wechat_service.go +++ b/app/third/paymentService/wechat_service.go @@ -97,6 +97,9 @@ func WxH5PayInfo(c context.Context, payOrderRequest PayOrderRequest) (string, er // 微信JSAPI支付 func WxJsApiPayInfo(c context.Context, payOrderRequest PayOrderRequest) (string, error) { + if payOrderRequest.OpenId == "" { + return "", errors.New("jsapi方式openId不能为空") + } // 初始化微信客户端 wxClient, err := InitClient(payOrderRequest.Wx) if err != nil { diff --git a/app/utils/httpclient/fasthttp.go b/app/utils/httpclient/fasthttp.go index 3ffd264..d0dde8c 100644 --- a/app/utils/httpclient/fasthttp.go +++ b/app/utils/httpclient/fasthttp.go @@ -2,8 +2,6 @@ package httpclient import ( "PaymentCenter/app/utils" - "fmt" - "github.com/valyala/fasthttp" "time" ) @@ -83,7 +81,6 @@ func FastHttpGet(url string, header map[string]string, body map[string]string, t } url = url[0 : len(url)-1] } - fmt.Println(url) req.SetRequestURI(url) resp := fasthttp.AcquireResponse() defer fasthttp.ReleaseResponse(resp) // 用完需要释放资源