WebSocket消息是否会丢失?

21

我正在开发一个Java WebSocket客户端应用程序,并且必须确保客户端接收到服务器发送的每个消息。由于WebSocket基于TCP协议,因此一旦连接中断,是否可能会丢失某些消息(一旦它们从服务器发送)?这种情况不应该发生,因为WebSocket基于TCP协议。


1
无论是接收到信息,还是完全失去连接。 - user253751
但是如果我完全失去连接,那么WebSocket客户端终端点就不再起作用了,对吧?这就是为什么我建立了一个重新连接处理程序,每30秒发送一次ping/pong消息来检查连接是否仍然存在,如果没有,它会尝试创建到服务器的新连接。 - Adrian Krebs
2
收到并不代表已阅读。 - symbiont
4个回答

24

这是可能发生的。TCP保证数据包的顺序,但在底层网络出现不可恢复的问题时,即使从服务器发送了所有数据包,也不能保证所有数据包都会到达客户端。想象一下,当您的应用程序与服务器通信时,在最糟糕的时机有人拔掉了LAN电缆或关闭了WiFi接入点,TCP也无法克服这样的麻烦。

为确保从服务器发送的每个WebSocket消息都能到达客户端,您必须在应用程序层实现某种形式的SYN / ACK。


2
看起来你在暗示未到达的TCP数据包可能不会被注意到。问题不是在应用层吗?硬件已经发送了ACK,但应用程序在读取接收到的消息之前崩溃了。 - symbiont
1
应用层ACK足以确保丢包率完全为0%吗?我们正在开发一个应用程序,即使是0.001%的丢包率也会引起严重问题。谢谢! - ch271828n
@symbiont 这正是我所想的,据我所知,TCP确实保证传输,但这个答案表明它并不保证。我的理解是,由于Websockets使用异步(发送即忘记)通信模型,它无法在应用层面上保证传输,但是如果TCP连接仍然打开,操作系统/硬件仍会重新传输丢失的数据包/帧(provided the TCP connection is still open)。 - chomba

3
TCP是一种可靠的协议——数据包将按正确顺序由远端的更高级应用层接收(这与UDP是一种“发送并希望”的协议相对)。通常情况下,TCP应该用于需要所有数据在远端正确到达的连接。而UDP则用于可以丢失一个数据包而没有重大问题的情况(例如流媒体服务、NTP更新)。

1
在我的游戏中,为了对抗丢失的Web Socket消息,我为每个消息添加了一个int/long ID。当客户端检测到它接收到的ID序列有问题时,客户端将请求从服务器获取新数据以便正确恢复。

1
你在考虑WebRTC吗?WebSockets应该在套接字内按顺序传递消息。 - Jayen
Websockets 使用 TCP 作为传输协议,确保数据包的正确交付和排序。您是否意味着在应用层中使用某种机制来确定哪个响应是针对哪个请求的? - Aritra Sur Roy

0
TCP 有一个叫做“控制流”(Control Flow)的东西,这意味着它提供可靠、有序和经过错误检查的传输。换句话说,TCP 是一种协议,不断检查数据是否到达。
该协议有不同的机制来确保这一点。您可以在下面的链接中看到 TCP 和 UDP(没有控制流)之间的区别。 TCP 和 UDP 的区别

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接