未在代理后面连接的 Websockets

2022-09-04 08:14:02

这是很常见的问题,但我找不到解决我的具体情况的方法。我正在使用Glassfish 4.1.1,我的应用程序实现了Websockets。

在客户端,我只需通过以下方式连接到WS服务器:

var serviceLocation = "ws://" + window.location.host + window.location.pathname + "dialog/";
var wsocket = new WebSocket(serviceLocation + token_var);

在服务器端,websockets是通过@ServerEndpoint功能实现的,看起来非常普遍:

@ServerEndpoint(value = "/dialog/{token}", decoders = DialogMessageDecoder.class)
public class DialogWebsoketEndpoint {

    @OnOpen
    public void open(final Session session, @PathParam("token") final String token) { ... }
etc.
}

一切正常,直到客户尝试在代理后面连接的那一刻。使用此测试:http://websocketstest.com/ 我发现客户的计算机在http-proxy 1.1后面工作。他无法连接到websockets,onopen根本就不开火。wsoscket.readyState 永远不会变成 1。

如何调整我的 ServerEndpoint 以使此代码正常工作,即使客户在代理后面连接也是如此?

提前感谢您!

更新:我会在那台计算机上提供带有websocketstest的屏幕截图:enter image description here

在我的计算机上,除了一件事之外,它似乎类似:HTTP代理:不。


答案 1

正如对问题的评论所说,代理似乎不能正确支持Websockets。

这是一个常见问题(一些手机公司有破坏websocket连接的代理),解决方案是使用TLS / SSL连接。

问题出现主要是因为某些代理“正确”(读取:损坏)Websocket请求标头。

但是,当使用TLS / SSL时,代理无法读取标头数据(已加密),从而导致数据在大多数代理上“传递”。

这意味着标头将安全地到达另一端,并且代理将(大多数)忽略连接...这仍然可能导致连接超时问题,但它通常可以解决问题。

编辑

请注意,浏览器将保护客户端不将未加密的内容与加密的内容混合在一起。确保在使用 TLS/SSL 连接时,脚本使用变体启动连接。wswss


答案 2