JAVAWebSocket使⽤时需要注意的地⽅
最近在做⼀个项⽬,需要⽤WebSocket与另外⼀个平台建⽴通讯,来获取项⽬业务需要的实时数据,因此项⽬⼀启动,后台就要与另外⼀个平台建⽴WebSocket连接并且要保证他们的之间有且只有⼀条持续畅通可⽤的连接(就是要保证这条连接不能断开,⼀断开就要尝试进⾏重连),说说我在这个过程中,遇到的⼀些问题以及解决的⽅法:
1、WebSocket连接正常,部分请求⽆响应
原因分析:
服务端/客户端接收到客户端/服务端⼀次性发来的⼏百条或更多的请求,瞬间都堆积在会话的缓冲区,⼜没做多线程处理,并且每接收到⼀条请求还要查询阿⾥云服务器数据库,加上⽹络带宽过⼩,处理⼀条请求就要花费⼏⼗秒;导致线程队列严重堵塞,⽆法及时响应处理后续的其他请求。
解决⽅法:
使⽤了线程池开启多条线程同时进⾏处理,将数据库配置设置为127.0.0.1,这样就不会经过公⽹绕⼀圈回来,这样⼤⼤缩短了⼀条请求处理要花费的时间,由之前的⼏⼗秒缩短为⼏百毫秒。
// 创建线程池
//private static ExecutorService cachedThreadPool = wCachedThreadPool();
private static ExecutorService fixedThreadPool = wFixedThreadPool(3);
注意⼏种线程池的区别,cachedThreadPool只有⾮核⼼线程,最⼤线程数很⼤,它会为每⼀个任务添加⼀个新的线程,它有⼀个超时机制,当空闲的线程超过60s内没有⽤到的话,就会被回收。cachedThreadPool缺点就是没有考虑到系统的实际内存⼤
⼩。fixedThreadPool是⼀个可以指定线程数的线程池,有核⼼的线程,⾥⾯有固定的线程数量,响应的速度快。正规的并发线程,多⽤于服务器。核⼼线程是没有超时机制的,队列⼤⼩没有限制,除⾮线程池关闭了核⼼线程才会被回收。还有singleThreadPoll、scheduledThreadPoll这⾥就不做过多的介绍了。
@OnMessage
public void onMessage(String datas,Session session) {
Runnable t = new Runnable() {
@Override
public void run() {
// TODO Auto-generated method stub
// 业务代码
}
};
//cachedThreadPool.submit(t);
fixedThreadPool.submit(t);
}
注意,要给session加上同步锁,否则会出现多个线程同时往同⼀个session写数据,导致报错的情况。
public void send(String data) throws Exception {
synchronized (session) {
}
}
2、发现WebSocket连接⽼是每隔⼀、两分钟就断开重连
原因分析:
⼀段时间内,WebSocket连接⽆数据传输就会⾃动断开连接
解决⽅法:
增加⼼跳机制维持连接,每隔⼀段时间就向服务端发送⼀次⾃定义请求,或者调⽤sendPing()来保持住连接。
3、WebSocket定时发送sendPing()后,还会反复出现接收/发送⼏个请求就断开连接的情况
原因分析:
⽆论是作服务端还是客户端,发现每次都是接收到同⼀个请求的信息后连接就断开了,经过反复的摸索发现,是由于接收到的这个请求传输的数据量过⼤,超出了WebSocket会话接收信息的缓冲区的⼤⼩(可使⽤MaxTextMessageBufferSize()查看缓冲⼤⼩,默认
为8192),引起的WebSocket连接的异常断开。
解决⽅法:
重新设置WebSocket缓冲区⼤⼩,
int maxSize = 200 * 1024; // 200K
// 可以缓冲的传⼊⼆进制消息的最⼤长度session.setMaxBinaryMessageBufferSize(maxSize); // 可以缓冲的传⼊⽂本消息的最⼤长度
java做什么的session.setMaxTextMessageBufferSize(maxSize);
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论