为多个请求重用相同的套接字连接

Reusing the same socket connection for multiple requests

这个问题可能有点跑题,但我不知道还能问哪里。我正在阅读此 https://github.com/msgpack-rpc/msgpack-rpc/blob/master/spec.md 并看到该规范包括能够使用相同的连接发送乱序消息。

我之前做过TCP socket编程的唯一方法就是在一个socket上同步发送请求,比如我会打开一个socket到127.0.0.1,通过那个socket向那个服务器发送请求然后等待以获得回应。当我收到对我发送的请求的响应时,我通过在客户端调用 close() 并在响应请求后在服务器上调用 close() 来关闭该连接。


作为背景,我正在使用 libevent 开发一个 C++ 项目来做一些与 RPC 系统非常相似的事情,所以我想知道我应该在底层传输中使用什么请求响应套接字周期系统。

在 C++ thrift 中,有一个名为 open() 的客户端方法(大概)会打开一个连接并保持打开状态,直到您调用 close()。这在被抽象掉的系统中如何工作?例如,在我上面包含的那个 messagepack-RPC link 中。最好的行动方案是什么?如果存在 none,则打开一个连接,发送请求,并在处理完所有先前的请求后关闭该连接(在服务器上,在响应所有未决请求时调用 close())?或者我们是否必须以某种方式尝试使该连接在超出请求生命周期的一段时间内保持活动状态?服务器和客户端如何知道那个时间段是什么?例如,我们是否应该在套接字上注册一个读取事件处理程序并在 recv() returns 0?

时关闭连接

如果这是一个不同系统以不同方式解决的问题,那么有人可以指导我找到一个资源,我可以使用它来阅读保持连接活动的可能模式(最好是在事件驱动系统中)吗?例如,我读到 HTTP 服务器始终保持连接打开,这是为什么呢?保持每个连接都打开是否意味着服务器实际上会泄漏内存?

很抱歉这个看似基本的问题,我以前只做过非常简单的TCP套接字编程,所以我可能不知道事情是如何完成的。

  1. 在客户端使用连接池。
  2. 客户端中有一个后台线程在超时后使空闲连接过期。
  3. 编写服务器,使其可以在每个接受的套接字上处理多个请求,即循环读取请求并发送响应,直到对等方关闭连接,或读取请求发生读取超时,或发生套接字错误。
  4. 不要从任何一方发送关闭消息。关闭套接字就足够了。
  5. 不要使用应用程序 ping 消息来保持连接。如果对等点或中间路由器认为连接太昂贵以致于在一段时间后终止它们,那么您没有任何业务试图愚弄它。

这就是大多数 HTTP 实现的工作方式。注意两端的超时,以控制每一端的空闲资源使用。