WebSocket应用
# 一、什么是WebSocket?
webSocket 是一种在单个TCP连接上进行全双工通信的协议,这里不在表述 websocket 相关基础知识。
plus
中有两个包和 websocket
相关:
# 1.1 mate-starter-websocket
引用
<dependency>
<groupId>vip.mate</groupId>
<artifactId>mate-starter-websocket</artifactId>
</dependency>
2
3
4
# 二、核心概念
mate-starter-websocket
的二次封装中的一些角色信息如下:
# 2.1 Message
websocket 双方交互传递的数据就是 message,message 可以是任意格式的文本信息。
# JsonMessage
为了方便使用和解析,plus 使用 json 来作为消息传递的格式,且规定 json 数据中,必须有 type 属性。
例如字典修改的消息体如下:
{
// 必有属性
type: 'dict-change',
// 自定义的属性,用来标识当前哪个字段被修改了
dictCode: 'gender',
}
2
3
4
5
6
新增其他类型的消息,只需要继承 AbstractJsonWebSocketMessage 即可:
public abstract class AbstractJsonWebSocketMessage implements JsonWebSocketMessage {
public static final String TYPE_FIELD = "type";
private final String type;
public AbstractJsonWebSocketMessage(String type) {
this.type = type;
}
@Override
public String getType() {
return type;
}
}
2
3
4
5
6
7
8
9
10
11
12
13
# PlanTextMessgae
当消息体无法使用 Json 解析时,或者解析出的 Json 中没有 Type,就会认为当前消息是一个普通文本。
PlanText 消息体将直接使用 String 传递。
# 2.2 MessageHandler
针对不同类型的消息,需要不同逻辑的处理,MessageHandler
就是用来管理处理逻辑的。
# JsonMessageHandler
JsonMessage 的处理器必须实现 JsonMessageHandler
接口。
public interface JsonMessageHandler<T extends JsonWebSocketMessage> {
/**
* JsonWebSocketMessage 类型消息处理
* @param session 当前接收 session
* @param message 当前接收到的 message
*/
void handle(WebSocketSession session, T message);
/**
* 当前处理器处理的消息类型
* @return messageType
*/
String type();
/**
* 当前处理器对应的消息Class
* @return Class<T>
*/
Class<T> getMessageClass();
}
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
- type(): 返回当前处理器对应的 type 类型,便于接收到不同 type 的 jsonMessage 时,进行调度。
- getMessageClass():返回 type 对象类型的 Json 映射实体类,Plus 会自动将接收到的消息,转化为此实体实例
- handle():消息处理方法,在此实现接收到消息后的处理逻辑
Plus 默认提供了一个 PingJsonMessageHandler
,当客户端向服务端发送 ping 消息,服务端接收到后会自动响应 pong 消息,用于 websocket 连接保活。
{
type: "ping"
}
{
type: "pong"
}
2
3
4
5
6
# PlanTextMessageHandler
PlanTextMessgae 的处理器接口定义如下所示:
public interface PlanTextMessageHandler {
/**
* 普通文本消息处理
* @param session 当前接收消息的session
* @param message 文本消息
*/
void handle(WebSocketSession session, String message);
}
2
3
4
5
6
7
8
9
10
handle()
:入参为 webSocketSession 和消息原文,实现此方法自定义处理逻辑
# 2.3 WebSocketSession
每一个客户端和服务端建立了 websocket 连接后,都会产生一个 webScoketSession,通过 WebSocketSession 我们就可以向指定客户端进行发送消息。
为了方便快速的定位到用户对应的 webSocketSession,我们需要给每个 session 分配一个唯一标识。
Plus 使用 WebSocketSessionHolder
使用一个 ConcurrentHashMap 持有了所有连接中的 webSocketSession,并在 websocket 连接建立或者断开时,自动加入或移除对应的 session。
而 map 中的 key 则是通过 SessionKeyGenerator
对象获取的:
public interface SessionKeyGenerator {
/**
* 获取当前session的唯一标识
* @param webSocketSession 当前session
* @return session唯一标识
*/
Object sessionKey(WebSocketSession webSocketSession);
}
2
3
4
5
6
7
8
9
10
用户需要自己实现该接口,并注册到 spring 容器中。
# 2.4 WebSocketMessageSender
消息发送者,用户可以通过该类进行消息广播,或者对指定 websocketSession 进行消息发送。
# 三、配置属性
mate-starter-websocket
提供了以下的属性配置