WebSocket TCP数据包聚集在一起?

时间:2012-11-14 05:30:50

标签: javascript html5 networking tcp websocket

关于JavaScript& PHP WebSocket TCP数据包聚集,下面以示例为例。

出于某种原因,当我在VPS上快速发送数据包,或通过指向我的IP地址的域访问我的本地主机时,多个数据包将聚集在一起。我试图流式传输,例如,每秒20(@ 100byte)个数据包。在服务器端,它们确实以稳定的速率发送,恰好每50ms发送一次,每秒20次。 但是,当他们到达客户端时,客户端仅处理大约每1/4秒的新消息。导致新数据包仅以每秒4次的速度接收...

是什么导致这些数据包聚集在一起?当所有内容都通过localhost时不会发生此问题。奇怪的是,它在iPhone的iOS Mobile Safari上顺畅流畅,完全没有问题。但是,它在PC Safari上根本不起作用(因为我还没有将其设置为使用旧的Hixie-76 WebSocket格式正常工作,我假设Mobile Safari已经在使用较新的RFC 6455或更新的JavaScript编译器)我尝试过多个托管公司,每次都有完全相同的结果。

请参阅下面的示例,托管在InMotion的VPS上: http://www.hovel.me/script/serverControl.php

(点击左侧的[连接],然后点击右侧的[查看游戏])。

每次接收的当前数据包将大约跳5次,因为每1/4秒一次接收每5个数据包。但是,我已经看到了可以发送恒定,快速数据包流的示例。 是什么导致这个聚集在一起/数据包相互等待?

编辑:这与Nagle's algorithm有关,后者收集&将小包一起发送?我将努力试图在PHP中绕过这一点。 即使在PHP中设置了这个TCP_NODELAY,问题仍然存在。为什么它适用于iPhone但不适用于PC仍然让我失望......
编辑:在注册表中将TCPNoDelay和TcpAckFrequency设置为1会修复此问题,但我不能指望每个用户都这样做。必须有客户端,面包和&黄油JavaScript方式。

我如何才能复制node.js' " socket.setNoDelay(true)",不使用node.js?

2 个答案:

答案 0 :(得分:3)

那是TCP。它通过节省IP数据包来帮助您。部分原因是由于Nagle算法,但其中一部分也可能是由中间网络引起的。

答案 1 :(得分:3)

最后,客户端没有识别Nagle的算法被禁用,以及它的确认频率仍被设置在200ms左右,这导致中间网络将以下数据包保存在缓冲区中。每次客户端收到消息时,手动向服务器发送确认消息,将导致网络立即“唤醒”并继续处理下一个数据包,而不是将它们保存在缓冲区中。

例如:

conn = new WebSocket(url);
conn.onmessage = function(evt){
    Server.send('ACKNOWLEDGE BYTES'); // Send ACK to server immediately
    dispatch('message', evt.data); //Do regular event procedures
};

此临时解决方案可行,但这将使带宽使用率几乎翻倍,以及其他网络问题。直到我可以让客户端上的WebSocket正确地为服务器确认“备用”,并且网络立即推送消息,这样可以更快地获取数据包而不会出现缓冲区软件问题。