我对HTTP轮询,长轮询,HTTP流和WebSockets的理解
我在SO和网上阅读了很多关于我的问题标题中关键字的帖子,并从中学到了很多。 我读到的一些问题与具体的实施挑战有关,而另一些则关注一般概念。 我只想确保我理解了为什么技术X是相对于技术Y而言发明的所有概念和理由。 所以在这里:
Http轮询:基本上是AJAX,使用XmlHttpRequest。
Http Long Polling: AJAX,但服务器保留响应,除非服务器有更新,只要服务器有更新,它就发送它,然后客户端可以发送另一个请求。 缺点是需要来回发送附加头数据,导致额外开销。
Http Streaming:类似于长轮询,但服务器以“Transfer Encoding:chunked”的头部响应,因此我们不需要在每次服务器发送一些数据(并因此保存额外的头部开销)时发起新的请求。 这里的缺点是我们必须“理解”并找出数据的结构来区分服务器发送的多个块。
Java Applet,Flash和Silverlight:它们提供了通过tcp / ip连接套接字服务器的能力,但由于它们是插件,因此开发人员不希望依赖它们。
WebSockets:它们是以下列方式尝试解决上述方法短缺的新API:
我还有其他重大差异吗? 我很抱歉,如果我重新询问或将已经存在的许多问题合并成一个问题,但我只想从SO和网络上关于这些概念的所有信息中完全理解。
谢谢!
有比你确定的更多的差异。
双面打印/方向:
按延迟递增(近似):
CORS(跨源支持):
本机二进制数据(键入数组,blob):
降低效率的带宽:
移动设备支持:
Javascript的使用复杂性(从最简单到最复杂)。 无可否认,复杂性措施有些主观。
另外请注意,有一个W3C提议标准化HTTP流,称为Server-Sent Events。 它目前还处于演化的早期阶段,旨在提供一个标准的JavaScript API,与WebSockets相媲美。
来自其他人的一些很好的答案涵盖了很多理由。 这里有一点额外的。
WebSockets相对于Java Applets,Flash或Silverlight等插件的唯一优势在于WebSocket本身嵌入到浏览器中,并且不依赖于插件。
如果你认为你可以使用Java Applets,Flash或Silverlight建立套接字连接,那么是的,这是可能的。 但是由于限制,你不会看到经常部署在真实世界中。
例如,中介可以并关闭该流量。 WebSocket标准被设计为与现有的HTTP基础设施兼容,因此不容易受到诸如防火墙和代理之类的中介干扰。
而且,WebSocket可以使用端口80和443而不需要专用端口,这要归功于协议设计尽可能与现有的HTTP基础设施兼容。
这些套接字替代品(Java,Flash和Silverlight)难以在跨源架构中安全使用。 因此,人们经常尝试将它们用于交叉来源将容忍这种不安全感,而不是去做安全的努力。
他们还可能需要打开额外的“非标准”端口(管理员不愿意这么做)或需要管理的策略文件。
简而言之,使用Java,Flash或Silverlight进行套接字连接的问题已经足够,以至于您看不到它经常部署在严重的体系结构中。 Flash和Java已经具备了这种功能,至少可以使用10年,但它并不普遍。
WebSocket标准能够以全新的方式开始,考虑到这些限制,并希望从中吸取一些教训。
当WebSocket连接无法建立时(例如,在旧浏览器中运行或中介干扰时),一些WebSocket实现使用Flash(或可能使用Silverlight和/或Java)作为它们的后备。
尽管针对这些情况的某种回退策略是明智的,甚至是必要的,但大多数使用Flash等的策略都会遇到上述缺陷。 它不一定是这样的 - 有一些解决方法可以实现使用Flash,Silverlight等安全的支持跨源的连接 - 但大多数实现不会那么做,因为这并不容易。
例如,如果您依靠WebSocket进行跨源连接,那么这将工作正常。 但是,如果您在旧浏览器或防火墙/代理中运行,并且依赖于Flash,那么作为您的后备,您会发现很难做到同样的跨源连接。 当然,除非你不关心安全性。
这意味着很难有一个统一的架构适用于本地和非本地连接,除非您准备投入相当多的工作或者使用一个已经完成的框架。 在一个理想的架构中,你不会注意到这些连接是否是本地的; 您的安全设置可以在两种情况下使用; 您的群集设置仍然有效; 您的容量规划仍然存在; 等等。
WebSockets相对于HTTP流的唯一优势在于,您无需努力“理解”并解析收到的数据。
这不像打开HTTP流那样简单,并且随着数据流过几分钟,几小时或更长时间就会回来。 不同的客户端行为不同,你必须管理它。 例如,有些客户端会缓冲数据,而不会将其释放到应用程序,直到达到某个阈值。 更糟糕的是,有些人在连接关闭之前不会将数据传递给应用程序。
因此,如果您要将多条消息发送到客户端,则例如,客户端应用程序可能会收到数据,直到收到50条消息的数据为止。 这不是太实时。
当WebSocket不可用时,HTTP流传输可以成为可行的替代方案,但它不是万能的。 在真实世界的情况下,它需要很好的理解才能在网络的恶劣环境中以稳健的方式工作。
我还有其他重大差异吗?
还有一件事还没有人提到,所以我会提出来。
WebSocket协议被设计成为更高级别协议的传输层。 虽然您可以发送JSON消息或什么 - 而不是直接通过WebSocket连接,它也可以携带标准或自定义协议。
例如,你可以通过WebSocket完成AMQP或XMPP,就像人们已经完成的那样。 因此,客户可以从AMQP代理接收消息,就好像它直接连接到代理本身(在某些情况下)。
或者,如果您有一个现有的服务器和一些自定义协议,则可以通过WebSocket传输它,从而将该后端服务器扩展到Web。 通常,已经锁定在企业中的现有应用程序可以扩大使用WebSocket的范围,而无需更改任何后端基础架构。
(当然,你希望能够安全地做到这一点,所以请与供应商或WebSocket提供商联系。)
有些人把WebSocket称为Web的TCP。 因为就像TCP传输更高级别的协议一样,WebSocket也是如此,但与Web基础结构兼容。
因此,尽管通过WebSocket直接发送JSON(或其他)消息总是可能的,但也应该考虑现有的协议。 因为对于你想要做的很多事情,可能有一个协议已经被认为可以做到。
我很抱歉,如果我重新询问或将已经存在的许多问题合并成一个问题,但我只想从SO和网络上关于这些概念的所有信息中完全理解。
这是一个很好的问题,答案都非常丰富!
如果我可能会问一个额外的事情:我在某个地方发现了一个文章,它说http流可能也会被代理缓存,而websocket则不会。 那是什么意思?
(StackOverflow限制评论回复的大小,所以我不得不在这里回答,而不是内联。)
那是个很好的观点。 要理解这一点,请考虑传统的HTTP场景......想象一下,浏览器打开了一个网页,所以它请求http://example.com。 服务器用包含该页面的HTML的HTTP进行响应。 然后浏览器看到页面中有资源,所以它开始请求CSS文件,JavaScript文件和图像。 它们都是静态文件,对于所有请求它们的客户端都是相同的。
某些代理会缓存静态资源,以便来自其他客户端的后续请求可以从代理获取这些静态资源,而不必一直回到中央Web服务器以获取它们。 这是缓存,从您的中央服务卸载请求和处理是一个很好的策略。
因此,客户#1请求http://example.com/images/logo.gif。 该请求会通过代理一直到中央Web服务器,该服务器会提供logo.gif。 当logo.gif通过代理时,代理将保存该图像并将其与http://example.com/images/logo.gif地址相关联。
当客户端#2出现并且还请求http://example.com/images/logo.gif时,代理可以返回图像,并且不需要通信回到中心的网络服务器。 这给最终用户提供了更快的响应,这总是很棒,但这也意味着中心的负载较低。 这可以转化为降低硬件成本,降低网络成本等等。所以这是一件好事。
在Web服务器上更新logo.gif时出现问题。 代理将继续为旧图像提供服务,但不知道有新图像。 这会导致整个过程到期,因此代理只会在“过期”之前将图像缓存一小段时间,并且下一个请求会通过代理传递给Web服务器,然后Web服务器会刷新代理的缓存。 还有更高级的解决方案,中央服务器可以推送到已知的缓存等等,而且事情可以变得非常复杂。
这与你的问题有什么关系?
您询问了HTTP服务器将HTTP流式传输到客户端的情况。 但是,流传输HTTP就像普通的HTTP一样,除非您不停止发送数据。 如果Web服务器提供图像,它会将HTTP发送到最终结束的客户端:您发送了整个图像。 如果你想发送数据,它是完全一样的,但服务器只是发送一个很长的时间(比如它是一个庞大的巨大图像),甚至永远不会完成。
从代理的角度来看,它不能区分静态资源(如图像)的HTTP或HTTP流的数据。 在这两种情况下,客户端都提出了服务器请求。 代理人记得该请求以及回复。 下一次请求进入时,代理服务器会提供相同的响应。
因此,如果您的客户提出股票价格请求并获得响应,则下一个客户端可能会发出相同的请求并获取缓存的数据。 可能不是你想要的! 如果你要求股票价格,你想要最新的数据,对吧?
所以这是一个问题。
有技巧和解决方法来处理这样的问题,这是事实。 很明显,你可以让HTTP流式传输工作,因为它现在正在使用。 这对于最终用户来说都是透明的,但是开发和维护这些架构的人们必须跳过这些环节并付出代价。 这会导致过度复杂的体系结构,这意味着更多的维护,更多的硬件,更多的复杂性,更多的成本。 这也意味着开发人员经常不得不关注他们应该只关注应用程序,GUI和业务逻辑时不应该做的事情 - 他们不应该关心底层通信。
链接地址: http://www.djcxy.com/p/44695.html上一篇: My Understanding of HTTP Polling, Long Polling, HTTP Streaming and WebSockets