Websocket 中的 sub-protocol 和 extensions 的关系

本文解释了WebSocket中的Sub-protocol和Extensions概念,通过将它们分别比作定制XMLschema和压缩文件,阐述了Sub-protocol由服务器实现且不可外部引用,而Extensions负责外部数据处理。它们在数据传输中的顺序是payload->extensions->sub-protocol->WebSocket.
摘要由CSDN通过智能技术生成

当时看 RFC6455 的时候,对 Sub-protocol 和 Extensions 感到很困惑,子协议是客户端提交几个子协议的列表(带优先序),交给服务器判断要使用那一个协议,然后再由服务器返回一个选中的子协议给客户端。而扩展则是客户端提交一个扩展列表(带顺序和参数)给服务器,然后由服务器决定要使用那些扩展,然后返回一个扩展列表给客户端(带顺序和参数)。

在文档中对这两个部分的描述并不是很清晰,并没有明确的举例说明这两个部分该如何使用,在搜索相关的资料的时候,在mozila的开发者网站上发现了这篇文章:

Writing WebSocket servers - Web APIs | MDN

其中提到:

Think of an extension as compressing a file before emailing it to someone. Whatever you do, you're sending the same data in different forms. The recipient will eventually be able to get the same data as your local copy, but it is sent differently. That's what an extension does. WebSockets defines a protocol and a simple way to send data, but an extension such as compression could allow sending the same data but in a shorter format.

Think of a subprotocol as a custom XML schema or doctype declaration. You're still using XML and its syntax, but you're additionally restricted by a structure you agreed on. WebSocket subprotocols are just like that. They do not introduce anything fancy, they just establish structure. Like a doctype or schema, both parties must agree on the subprotocol; unlike a doctype or schema, the subprotocol is implemented on the server and cannot be externally referred to by the client.

里面用压缩软件来举例说明了扩展的作用,同时用XML语法来类比子协议。同时强调了,子协议是服务器实现的,客户端不能从外部引用。如果从这个角度来看,子协议应该就是对 payload 的内部处理方式(代码级别),而扩展则是对 payload 的外部处理方式(程序级别)。

而处理的顺序则已经标明:

payload -> extensions (in order) -> sub-protocol -> webscoket

以上。

在 LayaAir ,可以通过设置 `Socket` 对象的 `protocols` 属性来添加 `Sec-WebSocket-Protocol` 头部。例如: ```javascript const socket = new Socket(); socket.protocols = ['protocol1', 'protocol2']; ``` 其,`protocols` 是一个数组,包含了要使用的协议名称。在连接到 WebSocket 服务器时,LayaAir 会在握手请求添加 `Sec-WebSocket-Protocol` 头部,以告知服务器使用的协议。 以下是完整代码示例: ```javascript import Socket = Laya.Socket; const socket = new Socket(); socket.protocols = ['protocol1', 'protocol2']; socket.on(Laya.Event.OPEN, this, onSocketOpen); socket.on(Laya.Event.MESSAGE, this, onSocketMessage); socket.on(Laya.Event.CLOSE, this, onSocketClose); socket.on(Laya.Event.ERROR, this, onSocketError); socket.connect('ws://localhost:8080', 8080); function onSocketOpen() { console.log('WebSocket connected'); } function onSocketMessage(data) { console.log('Received message:', data); } function onSocketClose() { console.log('WebSocket closed'); } function onSocketError(e) { console.error('WebSocket error:', e); } // 发送消息 socket.send('Hello, WebSocket!'); // 关闭连接 socket.close(); ``` 在上述示例,我们通过设置 `socket.protocols` 属性来添加 `Sec-WebSocket-Protocol` 头部。在服务端,需要检查客户端发送过来的 `Sec-WebSocket-Protocol` 头部,以确定客户端请求使用的协议是否被支持。若支持,则服务端需要在握手响应添加 `Sec-WebSocket-Protocol` 头部,以告知客户端使用的协议。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值