parent
b7983ffcab
commit
17d1ac0131
8 changed files with 1256 additions and 1 deletions
@ -0,0 +1,220 @@ |
||||
package sn |
||||
|
||||
// Success Codes
|
||||
const ( |
||||
CodeSuccess = 0 // 操作成功
|
||||
|
||||
SnAccount = "wjA77Game_N601" |
||||
DefaultLanguage = "en" |
||||
AgentId = 320 |
||||
SnId = 135 |
||||
SignKey = "2e0af20e8f0444a7decde7ae4c382dec" |
||||
) |
||||
|
||||
// Request Error Codes
|
||||
const ( |
||||
CodeRequestSuccess = 1001 // 成功
|
||||
|
||||
CodeRequestInvalidGameId = 100214 // 无效的游戏id
|
||||
CodeRequestInvalidGame = 100202 // 游戏不存在
|
||||
CodeRequestInvalidUser = 100213 // 玩家不存在
|
||||
CodeRequestExist = 100216 // 玩家已经存在
|
||||
) |
||||
|
||||
// Operation Error Codes
|
||||
const ( |
||||
INVALIDREQUESTERR = 1 // 参数错误
|
||||
CodeOperationFailed = 3001 // 操作失败(没有具体的失败原因说明)
|
||||
CodeUserNotFound = 3002 // 用户不存在
|
||||
CodeUserDataIncomplete = 3003 // 用户数据未加载完全
|
||||
CodeParameterProcessingError = 3004 // 参数处理异常(一般是数据不一致导致的)
|
||||
CodeDuplicateOrder = 3005 // 订单号重复
|
||||
CodeTokenMismatch = 3006 // Token不一致
|
||||
CodeRequestRateLimit = 3007 // 请求频率过高
|
||||
CodeInsufficientBalance = 3008 // 余额不足
|
||||
) |
||||
|
||||
type BaseReq struct { |
||||
SnAccount string `json:"sn_account"` |
||||
Time int64 `json:"time"` |
||||
Sign string `json:"sign"` |
||||
} |
||||
|
||||
type GetBalanceReq struct { |
||||
CoinCode string `json:"coin_code"` |
||||
GameId int `json:"game_id"` |
||||
RoomType string `json:"room_type"` |
||||
Timestamp int64 `json:"timestamp"` |
||||
Sign string `json:"sign"` |
||||
} |
||||
|
||||
type GetBalanceResp struct { |
||||
Code int `json:"code"` |
||||
Data struct { |
||||
Chips int `json:"chips"` |
||||
} `json:"data"` |
||||
Msg string `json:"msg"` |
||||
} |
||||
|
||||
//type GameBetReq struct {
|
||||
// IsEnd bool // 返奖时游戏结束标识(true: 当前对局已结束, false: 当前对局未结束)
|
||||
// AppID string // 运营商唯一标识
|
||||
// AppSecret string // 运营商 AppSecret
|
||||
// UserID string // 运营商的玩家唯一标识
|
||||
// TransactionID string // 交易订单号
|
||||
// Amount float64 // 增加/扣除金额(+ 增加, - 扣除)
|
||||
// RoundID string // 本局游戏 ID
|
||||
// GameID string // 游戏 ID
|
||||
// ReqTime string // 请求时间
|
||||
// Reason string // bet 下注扣款; win 派奖; refund 服务器内部出错,退回下注
|
||||
//}
|
||||
|
||||
type GameBetReq struct { |
||||
CoinCode string `json:"coin_code"` // 金币类型
|
||||
GameId int `json:"game_id"` // 游戏id
|
||||
RoomType string `json:"room_type"` // 玩法
|
||||
OrderId string `json:"order_id"` // 订单id
|
||||
MinAmount int `json:"min_amount"` // 最小下注值
|
||||
Amount int `json:"amount"` // 最大下注值
|
||||
BetId string `json:"bet_id"` // 下注id
|
||||
Sign string `json:"sign"` // 签名
|
||||
} |
||||
|
||||
type GameBetResp struct { |
||||
Code int `json:"code"` // 0成功 1失败
|
||||
Msg string `json:"msg"` |
||||
Data struct { |
||||
Chips int `json:"chips"` // 余额
|
||||
DeductionAmount int `json:"deduction_amount"` // 本次扣除
|
||||
} `json:"data"` |
||||
} |
||||
|
||||
type JackpotReq struct { |
||||
Reference string `json:"reference" form:"reference"` // 当前注单号
|
||||
OperatorID string `json:"operator_id" form:"operator_id"` // 本平台提供的运营商ID
|
||||
Accounts string `json:"accounts" form:"accounts"` // 运营的游戏帐号或ID
|
||||
Token string `json:"token" form:"token"` // authentication 返回的 token
|
||||
GameID string `json:"game_id" form:"game_id"` // 游戏类型ID
|
||||
RoomID string `json:"room_id" form:"room_id"` // 游戏房间ID
|
||||
WinAmount float64 `json:"win_amount" form:"win_amount"` // 当前游戏彩金金额
|
||||
RecordType string `json:"record_type" form:"record_type"` // 10 小彩金 11 大彩金 12 中等彩金
|
||||
BetReferenceID string `json:"bet_reference_id" form:"bet_reference_id"` // 压注注单号
|
||||
RoundID string `json:"round_id" form:"round_id"` // 局号
|
||||
} |
||||
|
||||
type JackpotResp struct { |
||||
Code int `json:"code"` |
||||
Msg string `json:"msg"` |
||||
Data struct { |
||||
Amount float64 `json:"amount"` |
||||
} `json:"data"` |
||||
} |
||||
|
||||
type SettleReq struct { |
||||
BackAmount int `json:"back_amount"` |
||||
CoinCode string `json:"coin_code"` |
||||
Details []struct { |
||||
AllBets int `json:"all_bets"` |
||||
Amount int `json:"amount"` |
||||
BetId string `json:"bet_id"` |
||||
CodedQuantity int `json:"coded_quantity"` |
||||
Index int `json:"index"` |
||||
IsFinish bool `json:"is_finish"` |
||||
WinAmount int `json:"win_amount"` |
||||
} `json:"details"` |
||||
GameId int `json:"game_id"` |
||||
IsFree bool `json:"is_free"` |
||||
IsOrderFinish bool `json:"is_order_finish"` |
||||
JpBonus int `json:"jp_bonus"` |
||||
JpContri int `json:"jp_contri"` |
||||
OrderId string `json:"order_id"` |
||||
RoomType string `json:"room_type"` |
||||
RoundId string `json:"round_id"` |
||||
SettlementId string `json:"settlement_id"` |
||||
Sign string `json:"sign"` |
||||
Timestamp int `json:"timestamp"` |
||||
} |
||||
|
||||
type SettleResp struct { |
||||
Code int `json:"code"` // 0成功 1失败
|
||||
Msg string `json:"msg"` |
||||
Data struct { |
||||
Chips int `json:"chips"` // 余额
|
||||
} `json:"data"` |
||||
} |
||||
|
||||
type RollbackReq struct { |
||||
CoinCode string `json:"coin_code"` |
||||
GameId int `json:"game_id"` |
||||
RoomType string `json:"room_type"` |
||||
OrderId string `json:"order_id"` |
||||
Sign string `json:"sign"` |
||||
} |
||||
|
||||
type RollbackResp struct { |
||||
Code int `json:"code"` // 0成功 1失败
|
||||
Msg string `json:"msg"` |
||||
Data struct { |
||||
Chips int `json:"chips"` // 余额
|
||||
} `json:"data"` |
||||
} |
||||
|
||||
type UpdateReq struct { |
||||
CoinCode string `json:"coin_code"` // 金币类型
|
||||
GameId int `json:"game_id"` |
||||
RoomType string `json:"room_type"` |
||||
OrderId string `json:"order_id"` |
||||
SubTypeId int `json:"sub_type_id"` // 更新金币类型
|
||||
Amount int `json:"amount"` // 更新数值
|
||||
Extend map[string]interface{} `json:"extend"` // 扩展信息
|
||||
Sign string `json:"sign"` |
||||
} |
||||
|
||||
type UpdateResp struct { |
||||
Code int `json:"code"` // 0成功 1失败
|
||||
Msg string `json:"msg"` |
||||
Data struct { |
||||
Chips int `json:"chips"` // 余额
|
||||
} `json:"data"` |
||||
} |
||||
|
||||
type GameControlCallbackReq struct { |
||||
Type string `json:"type"` |
||||
ControlId string `json:"control_id"` |
||||
Sign string `json:"sign"` |
||||
} |
||||
|
||||
type GameControlCallbackResp struct { |
||||
Code int `json:"code"` // 0成功 1失败
|
||||
Msg string `json:"msg"` |
||||
} |
||||
|
||||
type ControlReq struct { |
||||
BaseReq |
||||
ThirdName string `json:"third_name"` |
||||
ControlId int `json:"control_id"` |
||||
TemplateId int `json:"template_id"` |
||||
Data []struct { |
||||
TargetRtp int `json:"target_rtp"` |
||||
} `json:"data"` |
||||
Sn int `json:"sn"` |
||||
ControlDesc string `json:"control_desc"` |
||||
AgentId int `json:"agent_id"` |
||||
UserId int `json:"user_id"` |
||||
} |
||||
|
||||
type ControlResp struct { |
||||
Code int `json:"code"` |
||||
Success bool `json:"success"` |
||||
StatusCode int `json:"status_code"` |
||||
System int `json:"system"` |
||||
Message string `json:"message"` |
||||
Msg string `json:"msg"` |
||||
Prompt string `json:"prompt"` |
||||
RequestId string `json:"request_id"` |
||||
RequestMethod string `json:"request_method"` |
||||
Provider string `json:"provider"` |
||||
Doc string `json:"doc"` |
||||
Data struct { |
||||
} `json:"data"` |
||||
} |
||||
@ -0,0 +1,160 @@ |
||||
package sn |
||||
|
||||
import ( |
||||
"encoding/json" |
||||
"fmt" |
||||
"server/call" |
||||
"server/config" |
||||
"server/modules/web/providers/base" |
||||
"server/util" |
||||
"time" |
||||
|
||||
"github.com/liangdas/mqant/log" |
||||
) |
||||
|
||||
type Sub struct { |
||||
Base *base.Base |
||||
} |
||||
|
||||
func NewSub(base *base.Base) { |
||||
base.Sub = &Sub{Base: base} |
||||
base.SubInitRouter = Sn |
||||
} |
||||
|
||||
func (s *Sub) Init() { |
||||
API = APITest |
||||
APICreate = APICreateUserTest |
||||
APIControl = APIControlTest |
||||
AgentMap = AgentMapTest |
||||
if config.GetBase().Release { |
||||
API = APIRlease |
||||
APICreate = APICreateUserRlease |
||||
APIControl = APIControlRlease |
||||
AgentMap = AgentMapRelease |
||||
} |
||||
} |
||||
|
||||
type EnterReq struct { |
||||
BaseReq |
||||
|
||||
GameId int `json:"game_id"` // 游戏id
|
||||
AgentId int `json:"agent_id"` // 代理id
|
||||
ThirdName string `json:"third_name"` // 第三方昵称
|
||||
ClientIp string `json:"client_ip"` |
||||
|
||||
Language string `json:"language"` // 语言
|
||||
} |
||||
|
||||
type EnterResp struct { |
||||
Code int `json:"code"` |
||||
Success bool `json:"success"` |
||||
StatusCode int `json:"status_code"` |
||||
System int `json:"system"` |
||||
Msg string `json:"msg"` |
||||
Prompt string `json:"prompt"` |
||||
RequestId string `json:"request_id"` |
||||
RequestMethod string `json:"request_method"` |
||||
Provider string `json:"provider"` |
||||
Doc string `json:"doc"` |
||||
Data struct { |
||||
GameUrl string `json:"game_url"` |
||||
GameIdBase64 string `json:"game_id_base64"` |
||||
ApiGameBase64 string `json:"api_game_base64"` |
||||
ApiGameToken string `json:"api_game_token"` |
||||
Language string `json:"language"` |
||||
OrderIdList interface{} `json:"order_id_list"` |
||||
} `json:"data"` |
||||
} |
||||
|
||||
type CreateUserReq struct { |
||||
BaseReq |
||||
ThirdName string `json:"third_name"` |
||||
AgentId int `json:"agent_id"` |
||||
UserType int `json:"user_type"` |
||||
} |
||||
|
||||
type CreateUserResp struct { |
||||
Code int `json:"code"` |
||||
Msg string `json:"msg"` |
||||
Data struct { |
||||
OpenId int64 `json:"open_id"` |
||||
} `json:"data"` |
||||
} |
||||
|
||||
func (s *Sub) EnterGame() string { |
||||
log.Debug("sn enter game, %+v", *s.Base.EnterGameReq) |
||||
providerID := s.Base.EnterGameReq.ProviderID |
||||
gameID := s.Base.EnterGameReq.GameID |
||||
game := call.GetGameListByByID(providerID, gameID) |
||||
if game == nil { |
||||
return "" |
||||
} |
||||
|
||||
req := &EnterReq{ |
||||
BaseReq: BaseReq{ |
||||
SnAccount: SnAccount, |
||||
Time: time.Now().Unix(), |
||||
}, |
||||
GameId: game.GameID, |
||||
AgentId: AgentId, |
||||
ThirdName: call.GetProviderUserName(fmt.Sprintf("%d", s.Base.UID)), |
||||
ClientIp: s.Base.IP, |
||||
Language: DefaultLanguage, |
||||
} |
||||
|
||||
reqBody, _ := json.Marshal(req) |
||||
var tmpValue map[string]interface{} |
||||
json.Unmarshal(reqBody, &tmpValue) |
||||
req.Sign = GeneratedSign(tmpValue, SignKey) |
||||
|
||||
var resp EnterResp |
||||
err := util.HttpPost(API, req, &resp, nil) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
return "" |
||||
} |
||||
if resp.Code == CodeRequestInvalidUser { |
||||
err = s.createUser() |
||||
if err != nil { |
||||
log.Error("create err, %s", err.Error()) |
||||
return "" |
||||
} |
||||
return s.EnterGame() |
||||
} |
||||
if resp.Data.GameUrl == "" { |
||||
log.Error("err:%+v", resp) |
||||
return "" |
||||
} |
||||
|
||||
return resp.Data.GameUrl |
||||
} |
||||
|
||||
func (s *Sub) createUser() error { |
||||
log.Debug("sn create user, %+v", *s.Base.EnterGameReq) |
||||
req := &CreateUserReq{ |
||||
BaseReq: BaseReq{ |
||||
SnAccount: SnAccount, |
||||
Time: time.Now().Unix(), |
||||
}, |
||||
AgentId: AgentId, |
||||
ThirdName: call.GetProviderUserName(fmt.Sprintf("%d", s.Base.UID)), |
||||
} |
||||
|
||||
reqBody, _ := json.Marshal(req) |
||||
var tmpValue map[string]interface{} |
||||
json.Unmarshal(reqBody, &tmpValue) |
||||
req.Sign = GeneratedSign(tmpValue, SignKey) |
||||
|
||||
var resp CreateUserResp |
||||
err := util.HttpPost(APICreate, req, &resp, nil) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
return err |
||||
} |
||||
if resp.Code != CodeRequestSuccess && resp.Code != CodeRequestExist { |
||||
log.Error("create uer err, %+v", resp) |
||||
return fmt.Errorf("create err, %+v ", resp) |
||||
} |
||||
|
||||
return nil |
||||
} |
||||
@ -0,0 +1,638 @@ |
||||
package sn |
||||
|
||||
import ( |
||||
"encoding/json" |
||||
"fmt" |
||||
"io/ioutil" |
||||
"server/call" |
||||
"server/common" |
||||
"server/db" |
||||
"server/modules/web/app" |
||||
"server/modules/web/providers/base" |
||||
"server/util" |
||||
"strconv" |
||||
"time" |
||||
|
||||
"github.com/gin-gonic/gin" |
||||
"github.com/liangdas/mqant/log" |
||||
) |
||||
|
||||
func Sn(e *gin.RouterGroup) { |
||||
e.POST("/wallet_request", GetBalance) |
||||
e.POST("/wallet_bet", GameBet) |
||||
e.POST("/wallet_settlement", Settle) |
||||
e.POST("/wallet_bet_rollback", Rollback) |
||||
e.POST("/wallet_update", Update) |
||||
e.POST("/game_control_callback", GameControlCallback) |
||||
} |
||||
|
||||
func GetBalance(c *gin.Context) { |
||||
a := app.NewApp(c) |
||||
defer func() { |
||||
a.ResponseB() |
||||
}() |
||||
req := &GetBalanceReq{} |
||||
resp := &GetBalanceResp{} |
||||
a.RetData = resp |
||||
body, err := ioutil.ReadAll(c.Request.Body) |
||||
if err != nil { |
||||
log.Error("read body err: %v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
log.Debug("get balance:%s", string(body)) |
||||
err = json.Unmarshal(body, &req) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
|
||||
account := c.GetHeader("account") |
||||
headers := make(map[string]string) |
||||
for key, values := range c.Request.Header { |
||||
if len(values) > 0 { |
||||
headers[key] = values[0] // 取第一个值
|
||||
} |
||||
} |
||||
if a.ShouldRouteByAccount(&account, common.ProviderAPITypeJson, req, headers) { |
||||
return |
||||
} |
||||
newBody, _ := json.Marshal(req) |
||||
var tmpValue map[string]interface{} |
||||
json.Unmarshal(newBody, &tmpValue) |
||||
tmpSign := GeneratedSign(tmpValue, SignKey) |
||||
if tmpSign != req.Sign { |
||||
log.Error("sign is wrong, %+v", req) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
uids := account |
||||
uid, err := strconv.Atoi(uids) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
|
||||
currency, err := db.Redis().GetInt(common.GetRedisKeyGameCurrency(uid)) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
|
||||
resp.Msg = "success" |
||||
resp.Data.Chips = int(call.GetUserCurrencyFloat(uid, common.CurrencyType(currency), 0) * common.DecimalDigits) |
||||
log.Debug("GetBalanceResp:%+v", resp) |
||||
} |
||||
|
||||
func GameBet(c *gin.Context) { |
||||
a := app.NewApp(c) |
||||
defer func() { |
||||
a.ResponseB() |
||||
}() |
||||
req := &GameBetReq{} |
||||
resp := &GameBetResp{} |
||||
a.RetData = resp |
||||
body, err := ioutil.ReadAll(c.Request.Body) |
||||
if err != nil { |
||||
log.Error("read body err: %v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
log.Debug("game bet:%s", string(body)) |
||||
err = json.Unmarshal(body, &req) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
account := c.GetHeader("account") |
||||
headers := make(map[string]string) |
||||
for key, values := range c.Request.Header { |
||||
if len(values) > 0 { |
||||
headers[key] = values[0] // 取第一个值
|
||||
} |
||||
} |
||||
if a.ShouldRouteByAccount(&account, common.ProviderAPITypeJson, req, headers) { |
||||
return |
||||
} |
||||
//reqBody, _ := json.Marshal(req)
|
||||
var tmpValue map[string]interface{} |
||||
err = json.Unmarshal(body, &tmpValue) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
tmpSign := GeneratedSign(tmpValue, SignKey) |
||||
if tmpSign != req.Sign { |
||||
log.Error("sign is wrong, %+v", req) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
uids := account |
||||
uid, err := strconv.Atoi(uids) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
provider := call.GetConfigGameProvider(common.ProviderSn) |
||||
now := time.Now().Unix() |
||||
configGame := call.GetGameListByByID(common.ProviderSn, req.GameId) |
||||
if configGame == nil { |
||||
log.Error("get game config err") |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
betAmount := req.Amount |
||||
if betAmount < 0 { |
||||
betAmount = -req.Amount |
||||
} |
||||
betReq := &base.BetReq{ |
||||
UID: uid, |
||||
CurrencyType: common.CurrencyINR, |
||||
SessionType: base.SessionTypeBet, |
||||
GameID: req.GameId, |
||||
GameName: configGame.GameCode, |
||||
Provider: provider, |
||||
BetID: req.BetId, |
||||
SessionID: req.OrderId, |
||||
Time: now, |
||||
BetAmount: int64(betAmount), |
||||
TurnOver: int64(betAmount), |
||||
} |
||||
betResp := base.SessionBet(betReq) |
||||
if betResp.Code != base.CodeOk { |
||||
resp.Code = INVALIDREQUESTERR |
||||
if betResp.Code == base.CodeAccepted { |
||||
resp.Msg = "duplicate order" |
||||
} else if betResp.Code == base.CodeNotEnoughAmount { |
||||
resp.Msg = "insufficient balance" |
||||
} else { |
||||
resp.Msg = "operation failed." |
||||
} |
||||
log.Error("GameBetResp err:%v", resp.Code) |
||||
return |
||||
} |
||||
resp.Data.DeductionAmount = betAmount |
||||
resp.Data.Chips = int(call.GetUserCurrencyFloat(uid, common.CurrencyType(0), 0) * common.DecimalDigits) |
||||
resp.Msg = "success" |
||||
log.Debug("GameBetResp:%+v", resp) |
||||
a.Data = resp |
||||
} |
||||
|
||||
func Settle(c *gin.Context) { |
||||
a := app.NewApp(c) |
||||
defer func() { |
||||
a.ResponseB() |
||||
}() |
||||
req := &SettleReq{} |
||||
resp := &SettleResp{} |
||||
a.RetData = resp |
||||
body, err := ioutil.ReadAll(c.Request.Body) |
||||
if err != nil { |
||||
log.Error("read body err: %v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
log.Debug("sn Settle:%s", string(body)) |
||||
err = json.Unmarshal(body, &req) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
account := c.GetHeader("account") |
||||
headers := make(map[string]string) |
||||
for key, values := range c.Request.Header { |
||||
if len(values) > 0 { |
||||
headers[key] = values[0] // 取第一个值
|
||||
} |
||||
} |
||||
if a.ShouldRouteByAccount(&account, common.ProviderAPITypeJson, req, headers) { |
||||
return |
||||
} |
||||
var tmpValue map[string]interface{} |
||||
err = json.Unmarshal(body, &tmpValue) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
tmpSign := GeneratedSign(tmpValue, SignKey) |
||||
if tmpSign != req.Sign { |
||||
log.Error("sign is wrong, %+v", req) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
uids := account |
||||
uid, err := strconv.Atoi(uids) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
provider := call.GetConfigGameProvider(common.ProviderSn) |
||||
{ // 订单是否合法
|
||||
record := &common.ProviderBetRecord{ |
||||
UID: uid, |
||||
Provider: provider.ProviderID, |
||||
Type: base.SessionTypeBet, |
||||
SessionID: req.OrderId, |
||||
} |
||||
db.Mysql().Get(record) |
||||
if record.ID == 0 { |
||||
resp.Code = INVALIDREQUESTERR |
||||
resp.Data.Chips = int(call.GetUserCurrencyFloat(uid, common.CurrencyType(0), 0) * common.DecimalDigits) |
||||
return |
||||
} |
||||
} |
||||
now := time.Now().Unix() |
||||
configGame := call.GetGameListByByID(common.ProviderSn, req.GameId) |
||||
if configGame == nil { |
||||
log.Error("get game config err") |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
var betId string |
||||
if len(req.Details) > 0 { |
||||
betId = req.Details[0].BetId |
||||
} |
||||
settleAmount := int64(req.JpBonus + req.BackAmount) |
||||
betReq := &base.BetReq{ |
||||
UID: uid, |
||||
CurrencyType: common.CurrencyINR, |
||||
SessionType: base.SessionTypeSettle, |
||||
GameID: req.GameId, |
||||
GameName: configGame.GameCode, |
||||
Provider: provider, |
||||
BetID: betId, |
||||
SessionID: req.OrderId, |
||||
Time: now, |
||||
} |
||||
for _, detail := range req.Details { |
||||
settleAmount += int64(detail.WinAmount) |
||||
} |
||||
betReq.SettleAmount = settleAmount |
||||
betResp := base.SessionBet(betReq) |
||||
if betResp.Code != base.CodeOk { |
||||
resp.Code = INVALIDREQUESTERR |
||||
if betResp.Code == base.CodeAccepted { |
||||
resp.Msg = "duplicate order" |
||||
} else if betResp.Code == base.CodeNotEnoughAmount { |
||||
resp.Msg = "insufficient balance" |
||||
} else { |
||||
resp.Msg = "operation failed." |
||||
} |
||||
log.Error("GameBetResp err:%v", resp.Code) |
||||
return |
||||
} |
||||
|
||||
resp.Data.Chips = int(call.GetUserCurrencyFloat(uid, common.CurrencyType(0), 0) * common.DecimalDigits) |
||||
resp.Msg = "success" |
||||
log.Debug("SettleResp:%+v", resp) |
||||
a.Data = resp |
||||
} |
||||
|
||||
func Rollback(c *gin.Context) { |
||||
a := app.NewApp(c) |
||||
defer func() { |
||||
a.ResponseB() |
||||
}() |
||||
req := &RollbackReq{} |
||||
resp := &RollbackResp{} |
||||
a.RetData = resp |
||||
body, err := ioutil.ReadAll(c.Request.Body) |
||||
if err != nil { |
||||
log.Error("read body err: %v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
log.Debug("sn rollback:%s", string(body)) |
||||
err = json.Unmarshal(body, &req) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
account := c.GetHeader("account") |
||||
headers := make(map[string]string) |
||||
for key, values := range c.Request.Header { |
||||
if len(values) > 0 { |
||||
headers[key] = values[0] // 取第一个值
|
||||
} |
||||
} |
||||
if a.ShouldRouteByAccount(&account, common.ProviderAPITypeJson, req, headers) { |
||||
return |
||||
} |
||||
var tmpValue map[string]interface{} |
||||
err = json.Unmarshal(body, &tmpValue) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
tmpSign := GeneratedSign(tmpValue, SignKey) |
||||
if tmpSign != req.Sign { |
||||
log.Error("sign is wrong, %+v", req) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
uids := account |
||||
uid, err := strconv.Atoi(uids) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
provider := call.GetConfigGameProvider(common.ProviderSn) |
||||
|
||||
configGame := call.GetGameListByByID(common.ProviderSn, req.GameId) |
||||
if configGame == nil { |
||||
log.Error("get game config err") |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
|
||||
// 订单是否合法
|
||||
record := &common.ProviderBetRecord{ |
||||
UID: uid, |
||||
Provider: provider.ProviderID, |
||||
SessionID: req.OrderId, |
||||
} |
||||
db.Mysql().Get(record) |
||||
if record.ID == 0 { |
||||
resp.Code = INVALIDREQUESTERR |
||||
resp.Data.Chips = int(call.GetUserCurrencyFloat(uid, common.CurrencyType(0), 0) * common.DecimalDigits) |
||||
return |
||||
} |
||||
|
||||
var rollbackAmount int64 |
||||
|
||||
if record.Type == base.SessionTypeBet { |
||||
rollbackAmount = record.Amount |
||||
} else if record.Type == base.SessionTypeSettle { |
||||
rollbackAmount = record.Settle - record.Amount |
||||
} |
||||
|
||||
adjustReq := &base.AdjustmentReq{ |
||||
UID: uid, |
||||
Amount: rollbackAmount, |
||||
GameID: req.GameId, |
||||
GameName: configGame.GameCode, |
||||
Provider: provider, |
||||
BetID: req.OrderId, |
||||
SessionID: req.OrderId, |
||||
Time: time.Now().Unix(), |
||||
Type: base.SessionTypeAdjustment, |
||||
Ess: fmt.Sprintf("%s rollback", configGame.Name), |
||||
} |
||||
adjustResp := base.Adjustment(adjustReq) |
||||
if adjustResp.Code != CodeSuccess { |
||||
log.Debug("rollback adjustResp code:%d", adjustResp.Code) |
||||
resp.Code = INVALIDREQUESTERR |
||||
resp.Msg = "operation failed." |
||||
return |
||||
} |
||||
resp.Data.Chips = int(call.GetUserCurrencyFloat(uid, common.CurrencyType(0), 0) * common.DecimalDigits) |
||||
resp.Msg = "success" |
||||
log.Debug("rollback:%+v", resp) |
||||
a.Data = resp |
||||
} |
||||
|
||||
func Update(c *gin.Context) { |
||||
a := app.NewApp(c) |
||||
defer func() { |
||||
a.ResponseB() |
||||
}() |
||||
req := &UpdateReq{} |
||||
resp := &UpdateResp{} |
||||
a.RetData = resp |
||||
body, err := ioutil.ReadAll(c.Request.Body) |
||||
if err != nil { |
||||
log.Error("read body err: %v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
log.Debug("sn update:%s", string(body)) |
||||
err = json.Unmarshal(body, &req) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
account := c.GetHeader("account") |
||||
headers := make(map[string]string) |
||||
for key, values := range c.Request.Header { |
||||
if len(values) > 0 { |
||||
headers[key] = values[0] // 取第一个值
|
||||
} |
||||
} |
||||
if a.ShouldRouteByAccount(&account, common.ProviderAPITypeJson, req, headers) { |
||||
return |
||||
} |
||||
var tmpValue map[string]interface{} |
||||
err = json.Unmarshal(body, &tmpValue) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
tmpSign := GeneratedSign(tmpValue, SignKey) |
||||
if tmpSign != req.Sign { |
||||
log.Error("sign is wrong, %+v", req) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
uids := account |
||||
uid, err := strconv.Atoi(uids) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
provider := call.GetConfigGameProvider(common.ProviderSn) |
||||
|
||||
configGame := call.GetGameListByByID(common.ProviderSn, req.GameId) |
||||
if configGame == nil { |
||||
log.Error("get game config err") |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
|
||||
// 订单是否合法
|
||||
record := &common.ProviderBetRecord{ |
||||
UID: uid, |
||||
Provider: provider.ProviderID, |
||||
SessionID: req.OrderId, |
||||
} |
||||
db.Mysql().Get(record) |
||||
if record.ID == 0 { |
||||
resp.Code = INVALIDREQUESTERR |
||||
resp.Data.Chips = int(call.GetUserCurrencyFloat(uid, common.CurrencyType(0), 0) * common.DecimalDigits) |
||||
return |
||||
} |
||||
|
||||
updateAmount := int64(req.Amount) |
||||
desc := "game update" |
||||
|
||||
if req.SubTypeId == 80006 || req.SubTypeId == 80007 || req.SubTypeId == 80031 || req.SubTypeId == 101010 { |
||||
if updateAmount < 0 { |
||||
updateAmount *= -1 |
||||
} |
||||
} else if req.SubTypeId == 80016 { |
||||
|
||||
} else { |
||||
if updateAmount > 0 { |
||||
updateAmount *= -1 |
||||
} |
||||
} |
||||
|
||||
switch req.SubTypeId { |
||||
case 80005: // 小费
|
||||
desc = "game tip" |
||||
case 80006: |
||||
desc = "game activity" |
||||
case 80007: |
||||
desc = "game jp" |
||||
case 800016: |
||||
desc = "game award" |
||||
case 80030: |
||||
desc = "create room free" |
||||
case 80031: |
||||
desc = "create room award" |
||||
case 101010: |
||||
desc = "create room rollback" |
||||
} |
||||
|
||||
adjustReq := &base.AdjustmentReq{ |
||||
UID: uid, |
||||
Amount: updateAmount, |
||||
GameID: req.GameId, |
||||
GameName: configGame.GameCode, |
||||
Provider: provider, |
||||
BetID: req.OrderId, |
||||
SessionID: req.OrderId, |
||||
Time: time.Now().Unix(), |
||||
Type: base.SessionTypeAdjustment, |
||||
Ess: desc, |
||||
} |
||||
adjustResp := base.Adjustment(adjustReq) |
||||
if adjustResp.Code != CodeSuccess { |
||||
log.Debug("update adjustResp code:%d", adjustResp.Code) |
||||
resp.Code = INVALIDREQUESTERR |
||||
resp.Msg = "operation failed." |
||||
return |
||||
} |
||||
resp.Data.Chips = int(call.GetUserCurrencyFloat(uid, common.CurrencyType(0), 0) * common.DecimalDigits) |
||||
resp.Msg = "success" |
||||
log.Debug("rollback:%+v", resp) |
||||
a.Data = resp |
||||
} |
||||
|
||||
func GameControlCallback(c *gin.Context) { |
||||
a := app.NewApp(c) |
||||
defer func() { |
||||
a.ResponseB() |
||||
}() |
||||
req := &GameControlCallbackReq{} |
||||
resp := &GameControlCallbackResp{} |
||||
a.RetData = resp |
||||
body, err := ioutil.ReadAll(c.Request.Body) |
||||
if err != nil { |
||||
log.Error("read body err: %v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
log.Debug("sn gameControlCallback:%s", string(body)) |
||||
err = json.Unmarshal(body, &req) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
account := c.GetHeader("account") |
||||
headers := make(map[string]string) |
||||
for key, values := range c.Request.Header { |
||||
if len(values) > 0 { |
||||
headers[key] = values[0] // 取第一个值
|
||||
} |
||||
} |
||||
if a.ShouldRouteByAccount(&account, common.ProviderAPITypeJson, req, headers) { |
||||
return |
||||
} |
||||
var tmpValue map[string]interface{} |
||||
err = json.Unmarshal(body, &tmpValue) |
||||
if err != nil { |
||||
log.Error("unmarshal err, %s", err.Error()) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
tmpSign := GeneratedSign(tmpValue, SignKey) |
||||
if tmpSign != req.Sign { |
||||
log.Error("sign is wrong, %+v", req) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
uids := account |
||||
uid, err := strconv.Atoi(uids) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
resp.Code = INVALIDREQUESTERR |
||||
return |
||||
} |
||||
resp.Msg = "success" |
||||
log.Debug("gameControlCallback resp:%+v", resp) |
||||
a.Data = resp |
||||
defer func() { |
||||
err = Control(uid, util.ToInt(req.ControlId)) |
||||
if err != nil { |
||||
log.Error("sn control err, %s", err.Error()) |
||||
} |
||||
}() |
||||
} |
||||
|
||||
func Control(uid int, controlId int) error { |
||||
if controlId == 0 { |
||||
controlId = 1 |
||||
} |
||||
req := &ControlReq{ |
||||
BaseReq: BaseReq{ |
||||
SnAccount: SnAccount, |
||||
Time: time.Now().Unix(), |
||||
}, |
||||
ThirdName: call.GetProviderUserName(fmt.Sprintf("%d", uid)), |
||||
ControlId: controlId, |
||||
Sn: SnId, |
||||
AgentId: AgentId, |
||||
Data: []struct { |
||||
TargetRtp int `json:"target_rtp"` |
||||
}{ |
||||
{ |
||||
TargetRtp: call.GetProviderGameRtp(uid), |
||||
}, |
||||
}, |
||||
} |
||||
|
||||
log.Debug("sn control req, %+v", *req) |
||||
reqBody, _ := json.Marshal(req) |
||||
var tmpValue map[string]interface{} |
||||
json.Unmarshal(reqBody, &tmpValue) |
||||
req.Sign = GeneratedSign(tmpValue, SignKey) |
||||
|
||||
var resp ControlResp |
||||
err := util.HttpPost(APIControl, req, &resp, nil) |
||||
if err != nil { |
||||
log.Error("err:%v", err) |
||||
return err |
||||
} |
||||
if resp.Code != CodeRequestSuccess && resp.Code != CodeRequestExist { |
||||
log.Error("control err, %+v", resp) |
||||
return fmt.Errorf("control err, %+v ", resp) |
||||
} |
||||
|
||||
return nil |
||||
} |
||||
@ -0,0 +1,210 @@ |
||||
package sn |
||||
|
||||
import ( |
||||
"crypto/md5" |
||||
"encoding/hex" |
||||
"encoding/json" |
||||
"fmt" |
||||
"github.com/liangdas/mqant/log" |
||||
"sort" |
||||
"strings" |
||||
) |
||||
|
||||
const ( |
||||
APIRlease = "https://api.nbetps.com/v2/launch_game" |
||||
APITest = "https://api.nbetps.com/v2/launch_game" |
||||
|
||||
APICreateUserRlease = "https://api.nbetps.com/v1/create_user" |
||||
APICreateUserTest = "https://api.nbetps.com/v1/create_user" |
||||
|
||||
APIControlRlease = "https://api.nbetps.com/v1/control" |
||||
APIControlTest = "https://api.nbetps.com/v1/control" |
||||
|
||||
// LaunchGameURL = "/api/usr/ingame"
|
||||
// GetGameListURL = "/api/game/loadlist"
|
||||
// Lang = "hi"
|
||||
) |
||||
|
||||
type Agent struct { |
||||
MchId string `json:"mch_id"` |
||||
Key string `json:"key"` |
||||
} |
||||
|
||||
var ( |
||||
API = "" |
||||
APICreate = "" |
||||
APIControl = "" |
||||
AgentMap Agent |
||||
AgentMapTest = Agent{ |
||||
MchId: "slotgolden777test", |
||||
Key: "010804d1-7bbf-4ed5-9b50-60fbd2b22e34", |
||||
} |
||||
AgentMapRelease = Agent{ |
||||
MchId: "slotgolden777", |
||||
Key: "ddeaeb76-5624-41fe-a6ea-7ad9307d7701", |
||||
} |
||||
) |
||||
|
||||
func getSignStr(str string, pass ...string) string { |
||||
m := map[string]json.RawMessage{} |
||||
sortStrs := []string{} |
||||
json.Unmarshal([]byte(str), &m) |
||||
for i := range m { |
||||
sortStrs = append(sortStrs, i) |
||||
} |
||||
signStr := "" |
||||
sort.Strings(sortStrs) |
||||
for _, v := range sortStrs { |
||||
shouldPass := false |
||||
for _, s := range pass { |
||||
if v == s { |
||||
shouldPass = true |
||||
break |
||||
} |
||||
} |
||||
if shouldPass { |
||||
continue |
||||
} |
||||
if len(m[v]) > 1 && m[v][0] == 34 { |
||||
m[v] = m[v][1 : len(m[v])-1] |
||||
} |
||||
if len(m[v]) == 0 { |
||||
continue |
||||
} |
||||
signStr += fmt.Sprintf("%v=%v", v, string(m[v])) |
||||
signStr += "&" |
||||
} |
||||
signStr = signStr[:len(signStr)-1] |
||||
return signStr |
||||
} |
||||
|
||||
//func GeneratedSign(str string) string {
|
||||
// signStr := getSignStr(str, "sign") + "&key=" + SignKey
|
||||
// md5Value := createMd5(signStr)
|
||||
// md5Value = strings.ToUpper(createMd5(md5Value))
|
||||
// log.Debug("sn signStr:%s, md5:%s", signStr, md5Value)
|
||||
// return md5Value
|
||||
//}
|
||||
|
||||
func GeneratedSignMap(params map[string]interface{}) string { |
||||
keys := make([]string, 0, len(params)) |
||||
for k := range params { |
||||
if k != "" && k != "sign" && params[k] != nil { |
||||
keys = append(keys, k) |
||||
} |
||||
} |
||||
sort.Strings(keys) |
||||
var result string |
||||
for _, v := range keys { |
||||
if result != "" { |
||||
result += "&" |
||||
} |
||||
var value string |
||||
switch params[v].(type) { |
||||
case float64: |
||||
value = fmt.Sprintf("%d", int64(params[v].(float64))) |
||||
case int64: |
||||
value = fmt.Sprintf("%d", params[v].(int64)) |
||||
default: |
||||
value = fmt.Sprintf("%v", params[v]) |
||||
} |
||||
|
||||
result += v + "=" + value |
||||
} |
||||
return result |
||||
} |
||||
|
||||
func GeneratedSign(params map[string]interface{}, key string) string { |
||||
keys := make([]string, 0, len(params)) |
||||
for k := range params { |
||||
if k != "" && k != "sign" && params[k] != nil { |
||||
keys = append(keys, k) |
||||
} |
||||
} |
||||
sort.Strings(keys) |
||||
var sign string |
||||
for _, v := range keys { |
||||
var value string |
||||
switch params[v].(type) { |
||||
case float64: |
||||
value = fmt.Sprintf("%d", int64(params[v].(float64))) |
||||
case int64: |
||||
value = fmt.Sprintf("%d", params[v].(int64)) |
||||
case []interface{}, map[string]interface{}: |
||||
data, _ := json.Marshal(params[v]) |
||||
value = string(data) |
||||
default: |
||||
log.Debug("params[%s]: type=%T, value=%+v", v, params[v], params[v]) |
||||
value = fmt.Sprintf("%v", params[v]) |
||||
} |
||||
sign += v + "=" + value + "&" |
||||
} |
||||
sign += "key=" + key |
||||
result := strings.ToUpper(createMd5(sign)) |
||||
log.Debug("signStr:%v sign:%s\n", sign, result) |
||||
|
||||
return result |
||||
} |
||||
|
||||
// createMd5 生成md5字符串
|
||||
func createMd5(str string) string { |
||||
h := md5.New() |
||||
h.Write([]byte(str)) |
||||
return hex.EncodeToString(h.Sum(nil)) |
||||
} |
||||
|
||||
// var (
|
||||
// RtpMap = map[int]int{
|
||||
// 97: 11,
|
||||
// 96: 12,
|
||||
// 95: 13,
|
||||
// 93: 14,
|
||||
// 90: 15,
|
||||
// 85: 16,
|
||||
// 80: 17,
|
||||
// 60: 18,
|
||||
// 40: 19,
|
||||
// }
|
||||
// rtps = []int{97, 96, 95, 93, 90, 85, 80, 60, 40}
|
||||
// LevelMap = map[int]int{
|
||||
// 11: 97,
|
||||
// 12: 96,
|
||||
// 13: 95,
|
||||
// 14: 93,
|
||||
// 15: 90,
|
||||
// 16: 85,
|
||||
// 17: 80,
|
||||
// 18: 60,
|
||||
// 19: 40,
|
||||
// }
|
||||
// )
|
||||
|
||||
// func GetLevel(uid int) int {
|
||||
// rtp := call.GetProviderGameRtp(uid)
|
||||
// if rtp >= rtps[0] {
|
||||
// return RtpMap[97]
|
||||
// } else if rtp <= rtps[len(rtps)-1] {
|
||||
// return RtpMap[40]
|
||||
// }
|
||||
// for i := 1; i < len(rtps); i++ {
|
||||
// if rtp <= rtps[i-1] && rtp >= rtps[i] {
|
||||
// return RtpMap[rtps[i]]
|
||||
// }
|
||||
// }
|
||||
// return 15
|
||||
// }
|
||||
|
||||
// func GetRtp(uid int) int {
|
||||
// rtp := call.GetProviderGameRtp(uid)
|
||||
// if rtp >= rtps[0] {
|
||||
// return LevelMap[RtpMap[97]]
|
||||
// } else if rtp <= rtps[len(rtps)-1] {
|
||||
// return LevelMap[RtpMap[40]]
|
||||
// }
|
||||
// for i := 1; i < len(rtps); i++ {
|
||||
// if rtp <= rtps[i-1] && rtp >= rtps[i] {
|
||||
// return LevelMap[RtpMap[rtps[i]]]
|
||||
// }
|
||||
// }
|
||||
// return 90
|
||||
// }
|
||||
Loading…
Reference in new issue