You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
149 lines
3.8 KiB
149 lines
3.8 KiB
2 years ago
|
package new
|
||
|
|
||
|
import (
|
||
|
"Open_IM/pkg/common/constant"
|
||
|
promePkg "Open_IM/pkg/common/prometheus"
|
||
|
"context"
|
||
|
"errors"
|
||
|
"fmt"
|
||
|
"github.com/envoyproxy/protoc-gen-validate/validate"
|
||
|
"github.com/go-playground/validator/v10"
|
||
|
"open_im_sdk/pkg/log"
|
||
|
"open_im_sdk/pkg/utils"
|
||
|
"runtime/debug"
|
||
|
"sync"
|
||
|
)
|
||
|
|
||
|
const (
|
||
|
// MessageText is for UTF-8 encoded text messages like JSON.
|
||
|
MessageText = iota + 1
|
||
|
// MessageBinary is for binary messages like protobufs.
|
||
|
MessageBinary
|
||
|
// CloseMessage denotes a close control message. The optional message
|
||
|
// payload contains a numeric code and text. Use the FormatCloseMessage
|
||
|
// function to format a close message payload.
|
||
|
CloseMessage = 8
|
||
|
|
||
|
// PingMessage denotes a ping control message. The optional message payload
|
||
|
// is UTF-8 encoded text.
|
||
|
PingMessage = 9
|
||
|
|
||
|
// PongMessage denotes a pong control message. The optional message payload
|
||
|
// is UTF-8 encoded text.
|
||
|
PongMessage = 10
|
||
|
)
|
||
|
|
||
|
type Client struct {
|
||
|
w *sync.Mutex
|
||
|
conn LongConn
|
||
|
PlatformID int32
|
||
|
PushedMaxSeq uint32
|
||
|
IsCompress bool
|
||
|
userID string
|
||
|
IsBackground bool
|
||
|
token string
|
||
|
connID string
|
||
|
onlineAt int64 // 上线时间戳(毫秒)
|
||
|
handler MessageHandler
|
||
|
unregisterChan chan *Client
|
||
|
compressor Compressor
|
||
|
encoder Encoder
|
||
|
userContext UserConnContext
|
||
|
validate *validator.Validate
|
||
|
}
|
||
|
|
||
|
func newClient( conn LongConn,isCompress bool, userID string, isBackground bool, token string,
|
||
|
connID string, onlineAt int64, handler MessageHandler,unregisterChan chan *Client) *Client {
|
||
|
return &Client{
|
||
|
conn: conn,
|
||
|
IsCompress: isCompress,
|
||
|
userID: userID, IsBackground:
|
||
|
isBackground, token: token,
|
||
|
connID: connID,
|
||
|
onlineAt: onlineAt,
|
||
|
handler: handler,
|
||
|
unregisterChan: unregisterChan,
|
||
|
}
|
||
|
}
|
||
|
func(c *Client) readMessage(){
|
||
|
defer func() {
|
||
|
if r:=recover(); r != nil {
|
||
|
fmt.Println("socket have panic err:", r, string(debug.Stack()))
|
||
|
}
|
||
|
//c.close()
|
||
|
}()
|
||
|
var returnErr error
|
||
|
for {
|
||
|
messageType, message, returnErr := c.conn.ReadMessage()
|
||
|
if returnErr!=nil{
|
||
|
break
|
||
|
}
|
||
|
switch messageType {
|
||
|
case PingMessage:
|
||
|
case PongMessage:
|
||
|
case CloseMessage:
|
||
|
return
|
||
|
case MessageText:
|
||
|
case MessageBinary:
|
||
|
if len(message) == 0 {
|
||
|
continue
|
||
|
}
|
||
|
returnErr = c.handleMessage(message)
|
||
|
if returnErr!=nil{
|
||
|
break
|
||
|
}
|
||
|
|
||
|
}
|
||
|
}
|
||
|
|
||
|
}
|
||
|
func (c *Client) handleMessage(message []byte)error {
|
||
|
if c.IsCompress {
|
||
|
var decompressErr error
|
||
|
message,decompressErr = c.compressor.DeCompress(message)
|
||
|
if decompressErr != nil {
|
||
|
return utils.Wrap(decompressErr,"")
|
||
|
}
|
||
|
}
|
||
|
var binaryReq Req
|
||
|
err := c.encoder.Decode(message, &binaryReq)
|
||
|
if err != nil {
|
||
|
return utils.Wrap(err,"")
|
||
|
}
|
||
|
if err := c.validate.Struct(binaryReq); err != nil {
|
||
|
return utils.Wrap(err,"")
|
||
|
}
|
||
|
if binaryReq.SendID != c.userID {
|
||
|
return errors.New("exception conn userID not same to req userID")
|
||
|
}
|
||
|
ctx:=context.Background()
|
||
|
ctx =context.WithValue(ctx,"operationID",binaryReq.OperationID)
|
||
|
ctx = context.WithValue(ctx,"userID",binaryReq.SendID)
|
||
|
var messageErr error
|
||
|
var resp []byte
|
||
|
switch binaryReq.ReqIdentifier {
|
||
|
case constant.WSGetNewestSeq:
|
||
|
resp,messageErr=c.handler.GetSeq(ctx,binaryReq)
|
||
|
case constant.WSSendMsg:
|
||
|
resp,messageErr=c.handler.SendMessage(ctx,binaryReq)
|
||
|
case constant.WSSendSignalMsg:
|
||
|
resp,messageErr=c.handler.SendSignalMessage(ctx,binaryReq)
|
||
|
case constant.WSPullMsgBySeqList:
|
||
|
resp,messageErr=c.handler.PullMessageBySeqList(ctx,binaryReq)
|
||
|
case constant.WsLogoutMsg:
|
||
|
resp,messageErr=c.handler.UserLogout(ctx,binaryReq)
|
||
|
case constant.WsSetBackgroundStatus:
|
||
|
resp,messageErr=c.handler.SetUserDeviceBackground(ctx,binaryReq)
|
||
|
default:
|
||
|
return errors.New(fmt.Sprintf("ReqIdentifier failed,sendID:%d,msgIncr:%s,reqIdentifier:%s",binaryReq.SendID,binaryReq.MsgIncr,binaryReq.ReqIdentifier))
|
||
|
}
|
||
|
|
||
|
|
||
|
}
|
||
|
func (c *Client) close() {
|
||
|
|
||
|
}
|
||
|
func () {
|
||
|
|
||
|
}
|