WebSocket在HTTP Proxy下是可以,可是有点小笨拙之处给人造成不便

从规格说明上看,WebSocket毋庸置疑是可以通过HTTP Proxy Server代理访问出去的,不论是非加密的ws://,还是加密的wss://,都应该可以。当然有个通常都满足的前提:HTTP Proxy Server提供socket连接级别的无过滤转接,是所谓的CONNECT命令(而不光是HTTP整体请求响应的转接和过滤)。现实因为如果不提供这个CONNECT命令支持,那么HTTPS网站就用不了(原因一句话说不清,当然通过伪造SSL证书等手段也是可以的,只是需要browser机器这边配合)。总之,HTTP Proxy Server从原理上看,一旦支持了CONNECT命令,那么他后来就对连接中发生的加密内容基本上就是干瞪眼,无法区分到底是不是HTTPS了,从某种意义来说,这是HTTP Proxy Server设计上的一种漏洞。

事实上的确我使用WebSocket一段时间,和http proxy配合也正常,wss(加密)和ws(不加密)两种协议都行,

可有一天在一个http proxy环境下发生问题了!

经过一番疑神疑鬼的调查,最终确定是自动配置script里没有对wss类型提供proxy server ip和port,而只是回答了一个direct (就是不经过proxy server直接连接),所以失败了。

对策很简单,修改pac或者配置一个固定的proxy的ip,port。

memo一下调查经过:

所用工具:socat

在Firefox/Chrome/IE里,使用加密型WebSocket: new WebSocket(‘wss://x.y.z/test‘),爆出错误说timeout, 而非加密型 new WebSocket(‘ws://x.y.z/test‘) 也报错。

Proxy 配置:

自动: http://proxyserver/config.pac

调查开始:

先搞清楚这个config.pac干什么的,其实是个根据url, host来回答该用什么proxy server的东西,而且是个javascript。例如:

function FindProxyForURL(url, host) {
  if (url.substring(0, 5) == "http:") {
  return "PROXY proxy:80";
} else if (url.substring(0, 6) == "https:") {
  return "PROXY secproxy:8080";
} else {
  return "DIRECT";
}
}

那看了一下就是用secproxy:8080了啊,https都正常访问了,为啥wss出毛病?

当时绕了个弯子,想要看看http proxy内部发生了什么,于是就拿socat工具来做个中转来分析,这是个神器,以后在写一些活用法。

Run:

socat -v tcp-listen:8080,reuseaddr,fork  tcp-connect:secproxy:8080

就是用来做一个假的proxy server,本地的。其中的动作都转接到真的proxy server里去,
然后设定Browser通过这个假的Proxy server访问,于是可以看到其中的来往数据,

内容就省略了。着么折腾了一下也忘了抓取屏幕,忘了是怎么搞的,似乎是server对Websocket的握手请求作出回答后,browser就没有继续请求了,反正意识到自签名的证书会导致问题:WebSocket Server那边的server ssl证书是自签名的,那么可能这边不承认,嗯,的确有人说是,那好,我把证书给作为[可信赖的顶级证书发型者]来加入到系统,哦,https访问网站时的叉号消失了。

着么搞一下,的确wss可以了。

但是回到真环境,发现还是不行,最后用Sysinternal‘s Process Monitor工具追踪网络调用,发现browser居然不通过proxy就直接出去,于是出错了。

去掉自动配置选项,改成固定的proxy的ip,port就好了。

最终,我觉得websocket在选择Proxy server的方法上做的有点傻?居然直接傻乎乎问wss://somesite 该用什么proxy server,而不是聪明的问https://somesite该用什么网站。

转自自己的 http://osexp2003.blogspot.jp/

时间: 2024-10-04 12:27:09

WebSocket在HTTP Proxy下是可以,可是有点小笨拙之处给人造成不便的相关文章

Windwos下连远程linux Hbase小问题

前几天,兴起想仔细玩玩hbase,细细去研究一下,写了个小demo,从win7去连接另一台T510的ubuntu上的hbase.很简单的crud的操作程序,没有看出来什么问题,但是跑起来,硬是好像block住了,不往下执行,eclipse console没有打印任何信息,小红点还一直亮,纳闷之余,看到一些 Opening socket connection to server 192.168.0.xx/192.168.0.xx:2181. Will not attempt to authenti

Vue+WebSocket+ES6+Canvas 制作「你画我猜」小游戏

Vue+WebSocket+ES6+Canvas 制作「你画我猜」小游戏 转载 来源:jrainlau 链接:https://segmentfault.com/a/1190000005804860 项目地址:https://github.com/jrainlau/draw-something 下载 & 运行 git clone [email protected]:jrainlau/draw-something.git cd draw-something && npm install

websocket nova vnc proxy

1. vnc proxy的实现原理 vnc 是nova提供的用来访问虚拟机的一项重要功能,用户可以通过websocket来访问,也可以通过java客户端来访问.通过websket访问虚拟机 的功能已经集成到horizon中,而通过java客户端则需要先安装相应的软件.为了方便用户访问虚拟机,nova通过有一个proxy来实 现,proxy通常放在一个所有人都可以访问的IP地址. vnc访问的实现方法如下,首先是启动一个虚拟机时启用vnc,这可以通过给kvm加上vnc参数即可.这样,kvm就会启动

http与websocket两种协议下的跨域基于ASP.NET MVC--竹子整理

这段时间,项目涉及到移动端,这就不可避免的涉及到了跨域的问题.这是本人第一次接触跨域,有些地方的配置是有点麻烦,导致一开始的不顺. 至于websocket具体是什么意义,用途如何:请百度. 简单说就是建立一个基于互联网的实时通信. 在这里整理下这些内容,方便日后回顾. 一:介绍了WebSocket下的基于SignalR的跨域与不跨域例子 二:简单介绍了Http下的跨域问题 Ⅰ.WebSocket下的跨域 如果使用原生的方法来开发WebSocket应用,还是比较复杂的,不过好在Asp.net给我们

websocket集群情况下Nginx 代理出现的坑

那么问题的背景: A想给B发送socket 消息 ! A这消息 这时候被Nginx 轮询发到了C 服务器上! 擦!   这时候就蛋疼了!   要接收消息那个人在B服务器上!     B就这样苦逼的收不到了! 最简解决方案: 1.我先百度了下,草.发现各种说发  ,什么MQ进行什么的! 反正麻烦! 2,redis 中有一个发布和订阅  !   搞定收工!

WebSocket在Struts2框架下发生配置冲突的问题

前几天完成了聊天功能之后,想把这个功能模块整合进Struts2框架里,却发现WebSocket无法建立连接.弄了两天才发现原因. 我的项目里主要是两个原因: 一. <filter-mapping> <filter-name>struts2</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> 这里Struts2拦截了所有请求,修改方法是:在Struts.xml里添加

新闻频道下栏目新闻的订阅--小算法

频道数据 { 5976 =     ( "<WJNewsChannelModel: 0x170462400>", "<WJNewsChannelModel: 0x170462300>", "<WJNewsChannelModel: 0x170462380>", "<WJNewsChannelModel: 0x170466180>", "<WJNewsChannel

关于微信小程序下拉出现三个小点

包子这天看美团外卖的小程序,再瞅瞅自己的背景色,发现,美团下拉的时候有三个小点,但是我自己的校车徐下拉的时候没有三个小点,很是郁闷,于是各种的找各种的找,发现,这三个小点是微信小程序自带的,你只需要设置一下全局的背景色就ok了,设置全局的背景色在app.json里面设置就行,记住,是设置这个属性backgroundColor,不是这个属性:navigationBarBackgroundColor.....谨记谨记......这个定位我在上次说过了,接了百度地图的api.....

一个关于Windows下SetCursorPos和GetCursorPos的小坑

这两天在做一个编辑特定格式Mesh的小工具,需要检查鼠标的移动,一般来说可以用WM_MOUSEMOVE事件解决的,但是我为了省事用了定时查询+设置的方式,也就是: 1 void Frame(void) 2 { 3 //do something else... 4 5 POINT cursorPos; 6 GetCursorPos(&cursorPos); 7 curMoveX = cursorPos.x - cursorBaseX; 8 curMoveY = cursorPos.y - curs