springmvc使用websocket入门
什么是websocket?
websocket是一种长连接协议,它可以在浏览器和服务器之间建立一个不受限的双向实时通信的通道。
与http协议的区别
- http协议是短链接协议,一次请求对应一次响应。
- http协议下,如果浏览器不主动请求,服务器就没法发送数据给浏览器。
- http协议需要三次握手,websocket协议只需要一次就能发送消息。
springmvc使用websocket
博主接手的业务系统中,有一个springmvc项目使用到了websocket,所以这里使用了springmvc来整合websocket。
导入websocket依赖
在springmvc的基础依赖上添加websocket依赖。
<properties>
<spring-version>4.3.7.RELEASE</spring-version>
</properties>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-websocket</artifactId>
<version>${spring-version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-messaging</artifactId>
<version>${spring-version}</version>
</dependency>
配置websoket处理器
public class MySocketHandler extends TextWebSocketHandler {
private static ConcurrentHashMap<String, WebSocketSession> users = new ConcurrentHashMap<>();
private static Logger logger = LoggerFactory.getLogger(MySocketHandler.class);
@Override
public void afterConnectionEstablished(WebSocketSession webSocketSession) throws Exception {
//建立连接
users.put(webSocketSession.getId(), webSocketSession);
}
@Override
public void handleMessage(WebSocketSession webSocketSession, WebSocketMessage<?> webSocketMessage) throws Exception {
String message = webSocketMessage.getPayload().toString();
logger.info(webSocketSession + "---->" + webSocketMessage + ":"+ message);
TextMessage textMess = new TextMessage(message);
webSocketSession.sendMessage(textMess);
}
@Override
public void handleTransportError(WebSocketSession webSocketSession, Throwable throwable) throws Exception {
logger.info("handleTransportError=====================");
if(users.get(webSocketSession.getId()) != null){
users.remove(webSocketSession.getId());
}
}
@Override
public void afterConnectionClosed(WebSocketSession webSocketSession, CloseStatus closeStatus) throws Exception {
//连接建立完毕
logger.info("用户: " + webSocketSession.getRemoteAddress() + " is leaving, because:" + closeStatus);
if(users.get(webSocketSession.getId()) != null){
users.remove(webSocketSession.getId());
}
}
@Override
public boolean supportsPartialMessages() {
return false;
}
}
创建websocket配置类
@Configuration
@EnableWebSocket
public class WebSocketServerConfig implements WebSocketConfigurer {
@Override
public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) {
// 添加拦截地址以及相应的websocket消息处理器
registry.addHandler(new MySocketHandler(), "/websocket")
.addInterceptors(new MyHandshakeInterceptor())
.setAllowedOrigins("*");
registry.addHandler(new MySocketHandler(), "/sockJs")
.addInterceptors(new MyHandshakeInterceptor())
.setAllowedOrigins("*")
.withSockJS();
}
}
编写前端页面
这里如果浏览器不支持websocket的话,可以通过sockjs来实现。这里我新建了一个message.html,页面内容如下所示。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>websocket</title>
</head>
<style type="text/css">
#div {
color: red;
}
</style>
<body>
<h1>webSocket</h1>
<div id="div">
</div>
<script type="text/javascript" src="./js/sockjs.js"></script>
<script type="text/javascript">
var div = document.getElementById('div');
var prefix = "ws://127.0.0.1:8088/";
var websocketUrl = prefix + 'websocket';
var sockJSUrl = prefix + 'socketJs';
var socket = null;
if ('WebSocket' in window) {
socket = new WebSocket(websocketUrl);
}
else {
socket = new SockJS(sockJSUrl);
}
socket.onopen = function(event){
console.log(event);
socket.send('websocket client connect test');
}
socket.onclose = function(event){
console.log(event);
}
socket.onerror = function(event){
console.log(event);
}
socket.onmessage = function(event){
console.log(event)
div.innerHTML += ('接受到服务器消息:' + event.data);
}
</script>
</body>
</html>