fonchain-fiee/pkg/common/ws/client.go
2025-06-12 17:07:49 +08:00

112 lines
2.8 KiB
Go
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

// Package ws -----------------------------
// @file : client.go
// @author : JJXu
// @contact : wavingbear@163.com
// @time : 2022/10/21 18:18:05
// -------------------------------------------
package ws
import (
"context"
"fmt"
"github.com/gorilla/websocket"
uuid "github.com/satori/go.uuid"
"go.uber.org/zap"
"log"
"strings"
"time"
)
var (
// 注册事件最大等待时间
limitRegisterWaitTime = time.Second * 6
limitReadTime = time.Second * 5
)
// NewClient 创建客户端实例
//
// param userId 用户id
// param uid 用户uuid
// param conn 客户端websocket连接对象
// return *Client
func NewClient(userId int64, uid string, conn *websocket.Conn, room *ChatRoom) *Client {
uidobj, _ := uuid.NewV4()
var v = &Client{
Room: room,
UserId: userId,
Uuid: uid,
ClientId: strings.Replace(uidobj.String(), "-", "", -1),
Conn: conn,
Send: make(chan []byte, 500),
}
return v
}
type Client struct {
Room *ChatRoom `json:"-" `
UserId int64 `json:"userId" ` //用户id
Uuid string `json:"uuid"` //画家uid
ClientId string `json:"clientId"` //为用户不同设备分配不同的客户端ID
Conn *websocket.Conn `json:"-"`
Send chan []byte
SessionId string `json:"sessionId"` //会话ID同一个用户多客户端登录会话ID相同
Waiter bool `json:"waiter"` //是否是客服
}
func (c *Client) Reading(ctx context.Context, handleFunc ...func(sourceData []byte, cli *Client)) {
defer func() {
c.Room.UnRegister <- c
ctx.Done()
return
}()
//c.Conn.SetReadLimit(maxMessageSize)
c.Conn.SetReadDeadline(time.Now().Add(pongWait))
//接收到ping命令后更新读取时间
c.Conn.SetPongHandler(func(string) error {
c.Conn.SetReadDeadline(time.Now().Add(pongWait))
return nil
})
for {
msgType, byteData, err := c.Conn.ReadMessage()
if msgType == -1 {
return
}
if err != nil {
if websocket.IsUnexpectedCloseError(err, websocket.CloseGoingAway, websocket.CloseAbnormalClosure) {
log.Println("ws连接已关闭", zap.Error(err))
}
break
}
if handleFunc != nil {
handleFunc[0](byteData, c)
} else {
HandleMessage(byteData, c)
}
}
}
func (c *Client) WriteWait() {
ticker := time.NewTicker(pingPeriod)
defer func() {
ticker.Stop()
c.Conn.Close()
}()
for {
select {
case msg, ok := <-c.Send:
fmt.Printf("发送消息:%+v\n", string(msg))
c.Conn.WriteMessage(websocket.TextMessage, msg)
fmt.Println("发送消息结束")
if !ok {
// 聊天室关闭了管道
c.Conn.WriteControl(websocket.CloseMessage, []byte{}, time.Now().Add(writeWait))
return
}
case <-ticker.C:
if err := c.Conn.WriteControl(websocket.PingMessage, nil, time.Now().Add(pongWait)); err != nil {
return
}
}
}
}