This commit is contained in:
yangduo 2024-12-30 11:33:39 +08:00
parent e1bb4b963d
commit 44ce15c20b
9 changed files with 188 additions and 36 deletions

View File

@ -2,10 +2,12 @@ package v1
import (
"main/api/v1/ingame"
"main/api/v1/mainservice"
)
type ApiGroup struct {
InGameApiGroup ingame.ApiGroup
InGameApiGroup ingame.ApiGroup
MainServiceApiGroup mainservice.MainServiceApi
}
var ApiGroupApp = new(ApiGroup)

View File

@ -58,7 +58,7 @@ func (this *InGameApi) ServerPreOrder(c *gin.Context) {
goodsid := c.Query("goods_id")
sessionid := c.Query("session_id")
sign := c.Query("sign")
if strings.ToLower(q5.Md5Str(accountId+goodsid+"f3a6a9a5-217a-4079-ab99-b5d69b8212be"+sessionid)) != strings.ToLower(sign) {
if strings.ToLower(q5.Md5Str(accountId+goodsid+constant.GLOBAL_SALT+sessionid)) != strings.ToLower(sign) {
f5.RspErr(c, 401, "sign err")
return
}
@ -96,7 +96,7 @@ func (this *InGameApi) PayDone(c *gin.Context) {
orderid := c.Query("order_id")
sessionid := c.Query("session_id")
sign := c.Query("sign")
if strings.ToLower(q5.Md5Str(accountId+orderid+"f3a6a9a5-217a-4079-ab99-b5d69b8212be"+sessionid)) != strings.ToLower(sign) {
if strings.ToLower(q5.Md5Str(accountId+orderid+constant.GLOBAL_SALT+sessionid)) != strings.ToLower(sign) {
f5.RspErr(c, 401, "sign err")
return
}

View File

@ -0,0 +1,5 @@
package mainservice
type ApiGroup struct {
MainServiceApi
}

View File

@ -0,0 +1,38 @@
package mainservice
import (
"f5"
"main/constant"
"main/service"
"q5"
"github.com/gin-gonic/gin"
)
type MainServiceApi struct {
}
func (this *MainServiceApi) RefreshToken(c *gin.Context) {
reqtime := q5.SafeToInt64(c.Query("time"))
reqsign := c.Query("sign")
nowTime := f5.GetApp().GetRealSeconds()
if reqtime > nowTime+30 || reqtime+30 < nowTime {
f5.RspErr(c, 400, "request error")
return
}
sign := service.Wxpay.GenSHA256Signature(c.Query("time")+constant.GLOBAL_SALT, constant.GLOBAL_SALT)
if reqsign != sign {
f5.RspErr(c, 400, "request error 2")
return
}
rspObj := struct {
Data []service.TokenInfo `json:"data"`
ErrCode int64 `json:"errcode"`
ErrMsg string `json:"errmsg"`
}{}
service.Wxpay.GetAccessTokenList(&rspObj.Data)
c.JSON(200, rspObj)
}

View File

@ -40,12 +40,19 @@ const (
)
const (
WX_ERRCODE_OK = 0
WX_ERRCODE_BUSY = -1
WX_ERRCODE_SIGERR = 90010
WX_ERRCODE_PAYSIGERR = 90011
WX_ERRCODE_SAMEBILLNO = 90012
WX_ERRCODE_NOENOUGH = 90013
WX_ERRCODE_SESSIONERR = 90016
WX_ERRCODE_PARAMERR = 90018
WX_ERRCODE_OK = 0
WX_ERRCODE_BUSY = -1
WX_ERRCODE_UNAUTH_ACCESSTOKEN = 40014
WX_ERRCODE_MISSING_ACCESSTOKEN = 41001
WX_ERRCODE_EXPIRE_ACCESSTOKEN = 42001
WX_ERRCODE_SIGERR = 90010
WX_ERRCODE_PAYSIGERR = 90011
WX_ERRCODE_SAMEBILLNO = 90012
WX_ERRCODE_NOENOUGH = 90013
WX_ERRCODE_SESSIONERR = 90016
WX_ERRCODE_PARAMERR = 90018
)
const (
GLOBAL_SALT = "f3a6a9a5-217a-4079-ab99-b5d69b8212be"
)

View File

@ -0,0 +1,5 @@
package mainservice
type RouterGroup struct {
MainServiceRouter
}

View File

@ -0,0 +1,14 @@
package mainservice
import (
"f5"
v1 "main/api/v1"
)
type MainServiceRouter struct{}
func (this *MainServiceRouter) InitRouter() {
api := v1.ApiGroupApp.MainServiceApiGroup
f5.GetApp().GetGinEngine().GET("/api/service/refresh",
api.RefreshToken)
}

View File

@ -4,15 +4,18 @@ import (
"f5"
"main/middleware"
"main/router/ingame"
"main/router/mainservice"
)
type routerMgr struct {
ingame ingame.RouterGroup
mainservice mainservice.RouterGroup
}
func (this *routerMgr) Init() {
f5.GetApp().GetGinEngine().Use(middleware.Cors())
this.ingame.IngameRouter.InitRouter()
this.mainservice.MainServiceRouter.InitRouter()
f5.GetSysLog().Info("routerMgr.init")

View File

@ -14,9 +14,10 @@ import (
"time"
)
type tokenItem struct {
token string
expire int64
type TokenInfo struct {
GameId int64 `json:"gameid"`
Token string `json:"token"`
Expire int64 `json:"expire"`
}
type expireSession struct {
@ -25,9 +26,9 @@ type expireSession struct {
}
type wxpay struct {
gamesGoods q5.ConcurrentMap[int64, map[int64]int64] //[gameid, [goodsid]count]
accessTokens q5.ConcurrentMap[int64, tokenItem] //[gameid, tokenitem]
expireInfo q5.ConcurrentMap[string, *expireSession] //[accountid, expireSession]
accessTokens q5.ConcurrentMap[int64, TokenInfo] //[gameid, TokenInfo]
expireInfo q5.ConcurrentMap[string, *expireSession] //[accountid, expireSession]
refreshflag bool
}
type WxQuery struct {
@ -59,7 +60,7 @@ type WxPayRsp struct {
func (wp *wxpay) init() {
wp.gamesGoods = q5.ConcurrentMap[int64, map[int64]int64]{}
wp.accessTokens = q5.ConcurrentMap[int64, tokenItem]{}
wp.accessTokens = q5.ConcurrentMap[int64, TokenInfo]{}
wp.expireInfo = q5.ConcurrentMap[string, *expireSession]{}
mt.Table.Wxconfig.Traverse(func(w *mt.Wxconfig) bool {
@ -77,17 +78,15 @@ func (wp *wxpay) init() {
gamegoods[q5.SafeToInt64(data["id"])] = q5.SafeToInt64(data["count"])
}
wp.gamesGoods.Store(w.GetGameid(), gamegoods)
wp.accessTokens.Store(w.GetGameid(), tokenItem{})
wp.accessTokens.Store(w.GetGameid(), TokenInfo{})
}
return true
})
wp.gamesGoods.Range(func(gameid int64, value map[int64]int64) bool {
wp.freshAccessToken(gameid)
return true
})
go wp.checkExpireInfo()
wp.refreshflag = true
go wp.checkAccessToken()
}
func (wp *wxpay) unInit() {
@ -128,8 +127,9 @@ func (wp *wxpay) freshAccessToken(gameid int64) (token string) {
if rspObj.ErrCode == 0 {
tokenitem, _ := wp.accessTokens.Load(gameid)
tokenitem.token = rspObj.Token
tokenitem.expire = rspObj.Expire + f5.GetApp().GetRealSeconds()
tokenitem.GameId = gameid
tokenitem.Token = rspObj.Token
tokenitem.Expire = rspObj.Expire + f5.GetApp().GetRealSeconds()
wp.accessTokens.Store(gameid, *tokenitem)
}
@ -147,11 +147,17 @@ func (wp *wxpay) getAccessToken(gameid int64) (token string) {
cfg, exist := wp.accessTokens.Load(gameid)
nowTime := f5.GetApp().GetRealSeconds()
if exist {
if cfg.expire > nowTime+60 {
return cfg.token
if cfg.Expire > nowTime+6 {
if cfg.Expire < nowTime+30 && !wp.refreshflag {
wp.refreshflag = true
}
return cfg.Token
}
return wp.freshAccessToken(gameid)
if !wp.refreshflag {
wp.refreshflag = true
}
return ""
}
return ""
}
@ -196,9 +202,9 @@ func (wp *wxpay) QueryBalance(openid string, gameid int64, userip string, sessio
queryuri := "/wxa/game/getbalance"
query := WxQuery{
AccessToken: wp.getAccessToken(gameid),
Signature: wp.genSHA256Signature(poststr, sessionkey),
Signature: wp.GenSHA256Signature(poststr, sessionkey),
SigMethod: "hmac_sha256",
PaySig: wp.genSHA256Signature(queryuri+"&"+poststr, cfg.GetAppkey()),
PaySig: wp.GenSHA256Signature(queryuri+"&"+poststr, cfg.GetAppkey()),
}
params := map[string]string{}
@ -235,6 +241,7 @@ func (wp *wxpay) QueryBalance(openid string, gameid int64, userip string, sessio
sendRequest = false
default:
f5.GetSysLog().Info("err msg:%s", rspJson.ErrMsg)
wp.checkErrorCode(rspJson.ErrCode)
}
})
@ -276,9 +283,9 @@ func (wp *wxpay) QueryPay(openid string, gameid int64, userip string, sessionkey
queryuri := "/wxa/game/pay"
query := WxQuery{
AccessToken: wp.getAccessToken(gameid),
Signature: wp.genSHA256Signature(poststr, sessionkey),
Signature: wp.GenSHA256Signature(poststr, sessionkey),
SigMethod: "hmac_sha256",
PaySig: wp.genSHA256Signature(queryuri+"&"+poststr, cfg.GetAppkey()),
PaySig: wp.GenSHA256Signature(queryuri+"&"+poststr, cfg.GetAppkey()),
}
params := map[string]string{}
@ -314,6 +321,7 @@ func (wp *wxpay) QueryPay(openid string, gameid int64, userip string, sessionkey
sendRequest = false
default:
f5.GetSysLog().Info("err msg:%s", rspJson.ErrMsg)
wp.checkErrorCode(rspJson.ErrCode)
}
})
@ -348,12 +356,19 @@ func (wp *wxpay) CheckExpireCache(accountid string, expire int64) bool {
return true
}
func (wp *wxpay) genSHA256Signature(str string, key string) string {
func (wp *wxpay) GenSHA256Signature(str string, key string) string {
mac := hmac.New(sha256.New, []byte(key))
_, _ = mac.Write([]byte(str))
return strings.ToLower(hex.EncodeToString(mac.Sum(nil)))
}
func (wp *wxpay) GetAccessTokenList(data *[]TokenInfo) {
wp.accessTokens.Range(func(key int64, value TokenInfo) bool {
*data = append(*data, value)
return true
})
}
func (wp *wxpay) checkExpireInfo() {
for {
time.Sleep(time.Minute * 30)
@ -371,3 +386,66 @@ func (wp *wxpay) checkExpireInfo() {
}
}
}
func (wp *wxpay) checkAccessToken() {
for {
time.Sleep(time.Second)
if !wp.refreshflag {
continue
}
if f5.IsOnlineEnv() {
wp.gamesGoods.Range(func(gameid int64, value map[int64]int64) bool {
wp.freshAccessToken(gameid)
return true
})
} else {
url := "https://payservice.kingsome.cn/api/service/refresh"
nowtimestr := q5.SafeToString(f5.GetApp().GetRealSeconds())
params := map[string]string{
"time": nowtimestr,
"sign": wp.GenSHA256Signature(nowtimestr+constant.GLOBAL_SALT, constant.GLOBAL_SALT),
}
f5.GetHttpCliMgr().SendGoStyleRequest(
url,
params,
func(hcr f5.HttpCliResponse) {
if hcr.GetErr() != nil {
return
}
rspObj := struct {
Data []TokenInfo `json:"data"`
ErrCode int64 `json:"errcode"`
ErrMsg string `json:"errmsg"`
}{}
f5.GetSysLog().Debug("get online payservice rsp:%s", hcr.GetRawData())
if json.Unmarshal([]byte(hcr.GetRawData()), &rspObj) != nil {
return
}
if rspObj.ErrCode == 0 {
for _, dataitem := range rspObj.Data {
wp.accessTokens.Store(dataitem.GameId, dataitem)
}
}
})
}
wp.refreshflag = false
}
}
func (wp *wxpay) checkErrorCode(errcode int32) {
if errcode == constant.WX_ERRCODE_EXPIRE_ACCESSTOKEN ||
errcode == constant.WX_ERRCODE_MISSING_ACCESSTOKEN ||
errcode == constant.WX_ERRCODE_UNAUTH_ACCESSTOKEN {
if !wp.refreshflag {
wp.refreshflag = true
}
}
}