流程分析
Websocket客户端与Websocket服务器端
前端浏览器和后端服务器的连接通信
HTTP与Websocket对比
服务器端编码
1.引入pom依赖
XML
<!--webSocket-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-websocket</artifactId>
</dependency>
- 编写配置类
java
@Configuration
public class WebSocketConfig
{
@Bean
public ServerEndpointExporter serverEndpointExporter()
{
return new ServerEndpointExporter();
}
}
3.编写服务代码
java
import java.io.IOException;
import java.util.concurrent.ConcurrentHashMap;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Component;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import javax.websocket.*;
import javax.websocket.server.PathParam;
import javax.websocket.server.ServerEndpoint;
/**
* WebSocket服务器设置
*/
@ServerEndpoint(value = "/wsServer/{userId}")
@Component
public class WebSocketServer
{
// concurrent包的线程安全Set,用来存放每个客户端对应的MyWebSocket对象。
public static ConcurrentHashMap<String, WebSocketServer> webSocketMap = new ConcurrentHashMap<>();
public static ConcurrentHashMap<String, WebSocketServer> typeMap = new ConcurrentHashMap<>();
// 与某个客户端的连接会话,需要通过它来给客户端发送数据
private Session session;
// 接收userId
private String userId = "";
/**
* 连接建立成功调用的方法
*/
@OnOpen
public void onOpen(Session session, @PathParam("userId") String userId)
{
this.session = session;
this.userId = userId;
if (webSocketMap.containsKey(userId))
{
webSocketMap.remove(userId);
webSocketMap.put(userId, this);
} else
{
webSocketMap.put(userId, this);
}
try
{
sendMessage("我是服务端,你连接成功了!");
} catch (IOException e)
{
e.printStackTrace();
}
}
/**
* 连接关闭调用的方法
*/
@OnClose
public void onClose()
{
if (webSocketMap.containsKey(userId))
{
webSocketMap.remove(userId);
}
}
/**
* 收到客户端消息后调用的方法
*/
@OnMessage
public void onMessage(String message, Session session)
{
if (StringUtils.isNotBlank(message))
{
try
{
// 解析发送的报文
JSONObject jsonObject = JSON.parseObject(message);
String type = (String) jsonObject.get("type");
if (typeMap.containsKey(type))
{
typeMap.remove(type);
typeMap.put(type, this);
} else
{
typeMap.put(type, this);
}
} catch (Exception e)
{
e.printStackTrace();
}
}
}
/**
* 发生错误时调用
*/
@OnError
public void onError(Session session, Throwable error)
{
error.printStackTrace();
}
/**
* 实现服务器主动推送
*/
public void sendMessage(String message) throws IOException
{
this.session.getBasicRemote().sendText(message);
}
/**
* 发送自定义消息
*/
public static void sendInfo(String message, @PathParam("userId") String userId) throws IOException
{
if (StringUtils.isNotBlank(userId) && webSocketMap.containsKey(userId))
{
webSocketMap.get(userId).sendMessage(message);
}
}
}
4.状态变更通知前端
java
// 通过WebSocket通知前端人员下发状态变更
try
{
// 通过map获取对应的session
WebSocketServer.typeMap.get("userId").sendMessage(封装的消息体);
} catch (IOException e)
{
throw new RuntimeException(e);
}