IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 网络协议 -> java webSocket wss踩坑总结 -> 正文阅读

[网络协议]java webSocket wss踩坑总结

一、前言

之前项目中有一套http环境下的webSocket前后台项目(ws协议);
突然测试环境要切换成https,导致webSocket通信遇到了问题(wss协议)。

以下是遇到的问题与解决方法个人总结。

二、问题与解决方法

1.问题概述:vconsole中只报错WebSocket Open Error,但是没有具体错误原因。

问题详情:前端项目是vue移动端app项目,其中有vconsole可以查看debug时控制台打印的信息;
切换为https后,前端代码执行建立webSocket连接的代码时,建立失败,报错WebSocket Open Error(这个错误是自己定义的),但是没有错误原因;
此时后台没有任何日志打印。

解决方法:想办法把app访问的网页url获取到,使用chrome浏览器访问,在F12中,找到了错误信息:

SecurityError: Failed to construct 'WebSocket': An insecure WebSocket connection may not be initiated from a page loaded over HTTPS.

翻译为, 可能无法从通过HTTPS加载的页面启动不安全的WebSocket连接

终于找到了报错语句,进入下一步。

2.问题描述:An insecure WebSocket connection may not be initiated from a page loaded over HTTPS

问题详情:之前在http环境,前端建立webSocket连接使用的url是没有问题的,样例为:

ws://123.123.123.123:20000/webSocket

而现在,由于是 https环境,因此再使用 ws协议,就会报这个错。

解决方法:把ws改为 wss即可,样例如下:

wss://123.123.123.123:20000/webSocket

3.问题描述:修改为wss后,依然无法建立webSocket连接,依然无法从vconsole中找到错误详情;使用chrome进行测试,才发现新的错误信息。

问题详情:新的错误如下:

im.js:1993 WebSocket connection to 'wss://123.123.123.123:20000/webSocket' failed: Error in connection establishment: net::ERR_CERT_COMMON_NAME_INVALID

其中,im.js是前端项目中的一个js文件;
错误信息是: net::ERR_CERT_COMMON_NAME_INVALID

解决方法:这个错误大概意思是说,用一个错误的域名访问了某个节点的https资源(可能是Host错误导致)。

(1)分析发现,chrome打开的前端测试页面的 url为域名形式的,样例如下:

https://xxx.xxx.com/result.html

(2)而在这个result.html页面中,引入了im.js文件;在im.js文件中,执行了建立webSocket连接的前端代码;建立连接代码中,访问后台webSocket的 url为IP形式的:

wss://123.123.123.123:20000/webSocket

(3)虽然服务器的ip就是123.123.123.123,域名就是xxx.xxx.com,但是由于服务器是https的,https证书中配置的是*.xxx.com(证书中配置的域名应该是不能自己修改的);
chrome中访问https://xxx.xxx.com,会提示连接是 安全的;
chrome中访问https://123.123.123.123,会提示连接是 不安全的。

(4)应该是,由于chrome测试时,当前页面url为https://xxx.xxx.com,因此发送报文的Host参数也为xxx.xxx.com;
而此时发送wss://123.123.123.123:20000/webSocket的请求,就会因为Host与请求资源的url不一致导致报错(123.123.123.123 != xxx.xxx.com),即使服务器的ip与域名就是123.123.123.123 与xxx.xxx.com也不行。

(5)所以,把 wss的url从ip改为域名,才解决了 net::ERR_CERT_COMMON_NAME_INVALID问题。样例如下:

//这个不行
//wss://123.123.123.123:20000/webSocket
//这个可以
wss://xxx.xxx.com:20000/webSocket

三、其它笔记

1.本次服务器从http变为https遇到的问题中(ws变为wss)大部分是前端需要修改的
Java后台WebSocket服务端的代码不需要修改,还是用的ws连接时的代码(Java后台WebSocket服务端代码不区分ws与wss)**

Java后台WebSocket代码主要语句如下:

//这个配置webSocket连接用的url
@ServerEndpoint("/webSocket")

//连接建立,这个方法会被调用
@OnOpen
public void onOpen(WsSession session, EndpointConfig config){//自己写处理逻辑}

//连接关闭,这个方法会被调用
@OnClose
public void onClose(){/*自己写处理逻辑*/}

//前端给后台发来byte数组格式的消息,这个方法会被调用
@OnMessage
public void onMessage(byte[] message){/*自己写处理逻辑*/}

//前端给后台发来String格式的消息,这个方法会被调用
@OnMessage
public void onMessage(String message){/*自己写处理逻辑*/}

//前端给后台发来String格式的消息,这个方法会被调用
@OnError
public void onError(WsSession session, Throwable error){/*自己写处理逻辑*/}

2.从http变为https遇到的问题中(ws变为wss)nginx的配置也不用专门为https修改,使用之前http(ws)时的即可

nginx可用样例如下:

upstream websocket_cluster {
  server 10.1.2.3:20000;
}

server {
  listen 20000;
  server_name 123.123.123.123;

#因为是测试服务器,虽然是https,但是不用专门配置ssl等参数也可以使用
#ssl on;  
  access_log /home/user/nginx/logs/websocket.log main;
  error_log /home/user/nginx/logs/websocket.error.log;
  
  location /webSocket {
    expires -1;
    proxy_set_header Host $http_host;
    
    proxxy_pass http://websocket_cluster/webSocket;
    proxy_redirect off;
    proxy_read_timeout 18000;
    proxy_connect_timeout 18000;
    proxy_send_timeout 18000;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    client_max_body_size 2g;
    
    proxy_http_bersion 1.1;
    proxy_set_header Upgrade $http_upgrade;
    proxy_set_header Connection "upgrade";
    
  }
  
}

说明:
(1)前端访问wss://xxx.xxx.com:20000/webSocket时,dns服务器会把xxx.xxx.com转为123.123.123.123,然后就会访问到这个nginx

(2)根据nginx的配置,20000端口的请求,访问的后缀为/webSocket,可以转发到http://websocket_cluster/webSocket,即http://10.1.2.3:20000/webSocket

(3)Java的WebSocket后台部署在10.1.2.3服务器上,开启的端口是20000,使用了注解@ServerEndpoint("/webSocket"),然后收到前端建立webSocket连接的请求后,@OnOpen注解标注的方法就会被执行了

(4)Java后台后续收到前端发来的消息后,@OnMessage注解标注的方法就会被执行了。

(5)Java后台可以获取到WsSession对象,用来主动给前端发送消息。(这也是webSocket的主要功能,后台主动给前端发消息)

(6)nginx日志中,发现,建立webSocket连接时,日志中并不会打印信息;只有关闭webSocket连接时,日志中才会增加一行记录

(7)nginx中,webSocket主要的配置就是这两个:

    proxy_set_header Upgrade $http_upgrade;
    proxy_set_header Connection "upgrade";
  网络协议 最新文章
使用Easyswoole 搭建简单的Websoket服务
常见的数据通信方式有哪些?
Openssl 1024bit RSA算法---公私钥获取和处
HTTPS协议的密钥交换流程
《小白WEB安全入门》03. 漏洞篇
HttpRunner4.x 安装与使用
2021-07-04
手写RPC学习笔记
K8S高可用版本部署
mySQL计算IP地址范围
上一篇文章      下一篇文章      查看所有文章
加:2022-03-04 15:57:23  更:2022-03-04 15:59:09 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 7:41:36-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码