一个Web服务器如何在单个端口(80)上同时处理多个用户的传入请求?

76

一个Web服务器如何在单个端口(80)上同时处理多个传入请求?

例如: 同时有300k用户想要从www.abcdef.com查看一张图片,该网站分配的IP为10.10.100.100和端口80。那么www.abcdef.com如何处理这些传入用户的负载呢?

一个服务器(分配给IP地址10.10.100.100)能否处理如此庞大的传入用户?如果不能,那么如何将一个IP地址分配给多台服务器来处理这个负载呢?


这里有一个很好的答案(https://dev59.com/SGYs5IYBdhLWcg3wDPit#29045432),回答了类似问题“TCP中端口号的工作原理是什么?” - dumbledad
更好的帮助我理解的是来自网络工程方面的详细解释,链接在这里:https://networkengineering.stackexchange.com/a/39526 - Manohar Reddy Poreddy
5个回答

36

端口号只是一个神奇的数字,它并不对应硬件设备。服务器打开一个“监听”80端口的套接字,并从该套接字“接受”新连接。每个新连接由一个新的套接字表示,其本地端口也是80端口,但远程IP:端口按连接的客户端而定,因此它们不会混淆。因此,在服务器端不需要多个IP地址甚至多个端口。


4
希望没有人会对答案感到困惑,考虑到像这样寻找答案的人并不十分了解两个方面之间的区别,并且是网络世界中的新手。 - Ankur Anand
谢谢你的回答。如果同一个客户端连接到同一个服务器,即两个连接的远程IP:端口也相同,那么服务器如何知道哪个连接是哪个? - Kraken
@Kraken 远程端口对于两个连接来说不能相同。TIME-WAIT 状态会确保这一点。 - user207421

31

来自tcpipguide

使用客户端和服务器套接字标识连接,这为我们在互联网上实现设备之间的多个连接提供了灵活性。例如,繁忙的应用程序服务器进程(如Web服务器)必须能够处理来自多个客户端的连接,否则全球网络将几乎无法使用。由于连接使用客户端套接字以及服务器套接字进行标识,因此这不是问题。同时,Web服务器维护上述连接的同时,可以轻松地与IP地址219.31.0.44上的端口2,199建立另一个连接。这由连接标识符表示:

(41.199.222.3:80, 219.31.0.44:2199). 

事实上,同一个客户端可以向同一台服务器建立多个连接。每个客户端进程将被分配不同的临时端口号,因此即使它们都尝试访问同一个服务器进程(例如41.199.222.3:80处的Web服务器进程),它们也将拥有不同的客户端套接字并表示唯一的连接。这就是让您从计算机向同一网站发起多个同时请求的原因。
TCP会独立地跟踪每个连接,因此每个连接都不知道其他连接的存在。TCP可以处理数百甚至数千个同时连接。唯一的限制是运行TCP的计算机的容量和物理连接的带宽 - 同时运行的连接越多,每个连接就必须共享有限的资源。

9
引用质量较差,混淆了套接字和端口的概念。连接是通过IP地址和端口而非套接字进行标识的。 - user207421
1
@AnshumanKumar TCP套接字由四个元素组成,如果计算协议,则为五个。 - user207421

12

TCP 负责客户端识别
正如 a.m. 所说,TCP 负责客户端的识别,而服务器只会看到每个客户端的“套接字”。
例如一个位于 10.10.100.100 的服务器在监听端口80上的TCP连接(HTTP是基于TCP协议的)。当一个客户端浏览器(位于 10.9.8.7)使用客户端端口27143 连接到服务器时,服务器会看到:“客户端10.9.8.7:27143想要连接,你接受吗?”。然后服务器会接受,并获得一个“句柄”(即套接字),用来管理与该客户端的所有通信,并且该句柄将始终使用正确的TCP头向10.9.8.7:27143发送数据包。

数据包从不同时到达
实际上,物理上只有一条(或两条)连接将服务器与互联网连接起来,因此数据包只能按顺序到达。这就带来了一个问题:纤维最大吞吐量是多少,服务器可以计算和返回多少响应。除了需要消耗 CPU 时间或在响应请求时存在内存瓶颈外,服务器还必须保持某些资源处于活动状态(至少为每个客户端保持一个活动的套接字)直到通信结束,并因此消耗 RAM。为了实现吞吐量的提高,可以采用一些优化方法(不是互斥的),例如非阻塞套接字(以避免流水线/套接字之间的延迟)、多线程(利用更多的 CPU 核心/线程)。

进一步提高请求吞吐量:负载均衡
最后,网站“前端”的服务器通常不会全部自己完成所有工作(特别是更复杂的任务,如数据库查询、计算等),而会将任务延迟或甚至将 HTTP 请求转发到分布式服务器上,同时继续处理尽可能多的每秒请求(例如转发请求)。将工作分配到几个服务器上被称为负载均衡


没有“您是否要接受?”的选项。在应用程序有任何发言之前,TCP 就会接受连接。 - user207421

5

1) 一个Web服务器如何在单个端口(80)上同时处理多个请求?
==> a) Web服务的实例(例如:Spring Boot微服务)在服务器机器上的端口80上运行/监听。
b) 这个Web服务(Spring Boot应用程序)需要一个Servlet容器,如Tomcat。
此容器将配置线程池
c) 每当来自不同用户的请求同时到达时,此容器将为每个传入的请求分配来自池中的一个线程。
d) 由于服务器端Web服务代码将具有Bean(在Java中的情况下),通常是singleton,因此每个与每个请求相关的线程将调用Singleton API,如果需要访问数据库,则需要这些线程的同步,这是通过@transactional注释完成的。这个注释会同步数据库操作。

2) 一个服务器(分配了IP 10.10.100.100)能够处理这么多的并发用户吗?
如果不能,那么如何将一个IP地址分配给多台服务器以处理此负载?
==> 这将由负载均衡器和路由表来处理。


原始问题适用于不需要Servlet容器、线程池、Bean、数据库、事务或负载均衡器的情况。 - user207421
@ krozaine 这与问题无关。 - user207421

-1
答案是:虚拟主机,在HTTP头中是域名的名称,因此Web服务器知道运行哪些文件或发送给客户端。

2
问题中没有提到多个域名。 - user207421

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