html5 http的轮询和Websocket原理

一、HTTP的轮询 Web客户端与服务器之间基于Ajax(http)的常用通信方式,分为 短连接 与 长轮询 。 短连接:客户端和服务器每进行一次HTTP操作,就建立一次连接,任务结束就中断连接。 长轮询:客户端像传统轮询一样从服务器请求数据。然而,如果服务器没有可以立即返回给客户端的数据,则不会立刻返回一个空结果,而是保持这个请求等待数据到来(或者恰当的超时:小于ajax的超时时间),之后将数据作为结果返回给客户端。 长轮询机制如下图所示: 二、Websocket基本概念 WebSocket 是 HTML5 开始提供的一种在单个 TCP 连接上进行全双工通讯的协议。 WebSocket 使得客户端和服务器之间的数据交换变得更加简单,允许服务端主动向客户端推送数据。在 WebSocket API 中,浏览器和服务器只需要完成一次握手,两者之间就直接可以创建持久性的连接,并进行双向数据传输。 在 WebSocket API 中,浏览器和服务器只需要做一个握手的动作,然后,浏览器和服务器之间就形成了一条快速通道。两者之间就直接可以数据互相传送。 现在,很多网站为了实现推送技术,所用的技术都是 Ajax 轮询。轮询是在特定的的时间间隔(如每1秒),由浏览器对服务器发出HTTP请求,然后由服务器返回最新的数据给客户端的浏览器。这种传统的模式带来很明显的缺点,即浏览器需要不断的向服务器发出请求,然而HTTP请求可能包含较长的头部,其中真正有效的数据可能只是很小的一部分,显然这样会浪费很多的带宽等资源。 HTML5 定义的 WebSocket 协议,能更好的节省服务器资源和带宽,并且能够更实时地进行通讯。 浏览器通过 JavaScript 向服务器发出建立 WebSocket 连接的请求,连接建立以后,客户端和服务器端就可以通过 TCP 连接直接交换数据。 当你获取 Web Socket 连接后,你可以通过 send() 方法来向服务器发送数据,并通过 onmessage 事件来接收服务器返回的数据。 三、Websocket 握手原理: Websocket的握手原理大致可分为以下步骤: 第一步:客户端发起HTTP请求连接 第二步:服务端从请求头中取出Sec-WebSocket-Key的值 第三步:给Sec-WebSocket-Key值 拼接一个magic_string 的到一个新的value 第四步:给新的value先做 sha1加密 再做 base64加密 第五步:拼接一个响应头 第六步:服务器将拼好的响应头发送给客户端 第七步:客户端解密Sec-WebSocket-Accept得到Sec-WebSocket-Key判断是否握手成功 代码实现: import socket,base64,hashlib # 创建socket连接 sock = socket.socket(socket.AF_INET,socket.SOCK_STREAM) # 绑定端地址和口号 sock.bind(('127.0.0.1',9527)) # 监听 sock.listen(5) # 获取客户端socket对象 conn,address = sock.accept() # 获取客户端的【握手】信息 data = conn.recv(1024) print(data) def get_headers(data): """从请求头中取出Sec-WebSocket-Key对应的值并返回""" header_dict = {} header_str = data.decode("utf8") for i in header_str.split("\r\n"): if str(i).startswith("Sec-WebSocket-Key"): return i.split(":")[1].strip() # 得到Sec-WebSocket-Key对应的值 ws_key = get_headers(data) # 魔法字符串magic string为:258EAFA5-E914-47DA-95CA-C5AB0DC85B11 magic_string = '258EAFA5-E914-47DA-95CA-C5AB0DC85B11' # 拼接 socket_str = ws_key + magic_string # sha1加密 socket_str_sha1 = hashlib.sha1(socket_str.encode("utf8")).digest() # base64加密 socket_str_base64 = base64.b64encode(socket_str_sha1) # 拼接响应头 response_tpl = "HTTP/1.1 101 Switching Protocols\r\n" \ "Upgrade:websocket\r\n" \ "Connection: Upgrade\r\n" \ "Sec-WebSocket-Accept: %s\r\n" \ "WebSocket-Location: ws://127.0.0.1:9527\r\n\r\n" % (socket_str_base64.decode("utf8")) # 服务器发送响应头到客户端 conn.send(response_tpl.encode("utf8")) # 客户端服务端建立长连接循环接收发送数据 while True: msg = conn.recv(8096) print(msg)

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


HTML5和CSS3实现3D展示商品信息的代码
利用HTML5中的Canvas绘制笑脸的代码
Html5剪切板功能的实现
如何通过HTML5触摸事件实现移动端简易进度条
Html5移动端获奖无缝滚动动画实现
关于HTML5和CSS3实现机器猫的代码
HTML5使用DOM进行自定义控制
使用HTML5 Canvas绘制阴影效果的方法
使用PHP和HTML5 FormData实现无刷新文件上传
如何解决HTML5 虚拟键盘出现挡住输入框的问题
HTML5中div和section以及article的区别分析
html5和CSS 实现禁止IOS长按复制粘贴功能
html5 touch事件实现触屏页面上下滑动
canvas 模拟实现电子彩票刮刮乐的代码
HTML5 Plus 实现手机APP拍照或相册选择图片上传的功能
Android自定义环形LoadingView效果
HTML5 canvas绘制五角星的方法
html5使用html2canvas实现浏览器截图
使用Canvas处理图片的方法介绍
利用Canvas模仿百度贴吧客户端loading小球的方法