阿里二面:SpringBoot可以同时处理多少个请求?当场懵了。。。。

SpringBoot以其简洁高效的开发方式和强大的内嵌容器特性,为开发者提供了构建高性能后端服务的便利。然而,当面临高并发场景时,理解并合理配置Spring Boot应用以达到最佳的并发处理能力至关重要。在Spring Boot中,应用程序对HTTP请求的并发处理主要依赖于内嵌的Servlet容器(如Tomcat)。接下来我们以Tomcat为例谈谈这个问题。

本文以SpringBoot2.7.0为例。

在接下来讲解Tomcat工作线程池之前,你可以先了解一下Java线程池的工作原理,请参考这篇文章:Java线程池最全详解

请求处理

我们的程序实际上是运行在Tomcat里的。所以SpringBoot可以处理多少请求,其实也就是看Tomcat可以处理多少请求。Tomcat的工作线程池负责接收并处理这些请求。在SpringBoot中关于Tomcat工作项城池的参数可以在spring-boot-autoconfigure的依赖包中的spring-configuration-metadata.json中有如下四个参数控制Tomcat的工作线程池:

json 复制代码
{
	{  
	  "name": "server.tomcat.threads.max",  
	  "type": "java.lang.Integer",  
	  "description": "Maximum amount of worker threads.",  
	  "sourceType": "org.springframework.boot.autoconfigure.web.ServerProperties$Tomcat$Threads",  
	  "defaultValue": 200  
	},  
	{  
	  "name": "server.tomcat.threads.min-spare",  
	  "type": "java.lang.Integer",  
	  "description": "Minimum amount of worker threads.",  
	  "sourceType": "org.springframework.boot.autoconfigure.web.ServerProperties$Tomcat$Threads",  
	  "defaultValue": 10  
	},
	{  
	  "name": "server.tomcat.max-connections",  
	  "type": "java.lang.Integer",  
	  "description": "Maximum number of connections that the server accepts and processes at any given time. Once the limit has been reached, the operating system may still accept connections based on the \"acceptCount\" property.",  
	  "sourceType": "org.springframework.boot.autoconfigure.web.ServerProperties$Tomcat",  
	  "defaultValue": 8192  
	},
	{  
	  "name": "server.tomcat.accept-count",  
	  "type": "java.lang.Integer",  
	  "description": "Maximum queue length for incoming connection requests when all possible request processing threads are in use.",  
	  "sourceType": "org.springframework.boot.autoconfigure.web.ServerProperties$Tomcat",  
	  "defaultValue": 100  
	}
}

我们来看一下这四个参数的含义:

  • server.tomcat.threads.max:用于配置Tomcat内嵌服务器的工作线程池的最大工作线程数。工作线程用于处理接收到的HTTP请求,处理完毕后将返回到线程池中等待下一个请求。当并发请求数量小于等于 threads.max 时,Tomcat尽可能使用现有的工作线程来处理请求,如果并发请求数量超过了 threads.maxTomcat不再创建新的工作线程,而是将请求放入队列等待。该值可以看做是一个临时工,如果并发请求的数量在threads.min-sparethreads.max之间,就会使用这些临时工线程进行处理。默认值为200。主要关注的是工作线程池,用于处理请求的线程数。适用于调整并发请求的处理能力。

  • server.tomcat.threads.min-spare:确定了工作线程池的最小空闲线程数量,即使没有请求需要处理,也会保持这些线程处于等待状态,以便快速响应新的请求。该值可以看做是一个长期工,如果并发请求数小于min-spare,就会使用这些线程去处理请求。默认值是10,即使没有活跃的请求,Tomcat也会保持至少 10 个空闲线程。

  • server.tomcat.max-connections:用于配置Tomcat内嵌服务器的连接池的最大连接数。即允许同时存在的最大连接数。这个连接数是针对整个连接池的,不仅仅是工作线程的数量。当并发请求数量导致服务器需要创建新的连接时,Tomcat 会检查连接池中的连接数是否已经达到了 max-connections 配置的最大值。如果已经达到最大值,新的连接请求将被放入等待队列中,直到有连接被释放。默认值8192。

  • server.tomcat.accept-count:用于配置Tomcat连接器所允许的最大等待接受连接的请求数(即等待队列)。当所有线程都在处理其他请求时,新的连接请求将会排队等待。如果队列已满,额外的连接将被拒绝。默认值是100。

我们以饭馆的示例去说明这几个参数之间的关系:

我们把Tomcat比作一家热门的餐厅,每个顾客都是一个请求。餐厅里一直有一部分厨师一直待命,无论有没有顾客,确保随时能够处理点单。这部分厨师就是min-spare(长期工) ,当餐厅遇到一些大的宴会时,餐厅老板就会从外面找过来一批厨师帮忙,这部分厨师就是临时工,临时工+长期工就是(max) 。餐厅的座位就表示同时最大可以容纳啊就餐的顾客人数,即max-connections。假如某时餐厅生意火爆,餐厅的座位都坐满以后,此时餐厅就会想办法在餐厅门口放上一排座椅,可以让后来的顾客在这里等待,假如里面有顾客吃完,这时外面等待的顾客就可以进去用餐。如果餐厅门口的座椅也做满,再来的顾客就会离开。

假如上述就是那家餐厅,2个绿色框代表长期工厨师即min-spare,3个红色框代表临时工厨师,共有5名厨师,即max数量,5个棕色的队列即餐厅椅子数量,即5个max-connections,餐厅最多可以容忍5名顾客吃饭,2个橘色队列代表门口等待区椅子数量,即2个accept-count。假如此时来了4个客人,那就可以区餐厅吃饭,如果来了7个客人,那么有5个客人进去吃饭,2个客人在门口等待,如果来了8个客人,那么有5个客人进去吃饭,2个客人在门口等待,剩下1个客人就会直接离开。

示例

我们创建一个SpringBoot项目,我们将上述四个参数分别修改为如下:

properties 复制代码
server.tomcat.accept-count=2  
server.tomcat.max-connections=5  
server.tomcat.threads.max=5  
server.tomcat.threads.min-spare=2

然后我们在定义一个接口,用于模拟客户端请求:

java 复制代码
@RestController  
@RequestMapping("test")  
public class TestMaxRequestController {  
  
    @GetMapping("maxRequest")  
    @ResponseBody  
    public String testMaxRequest() throws InterruptedException {  
        System.out.println("当前请求线程: "+Thread.currentThread().getName());  
        Thread.sleep(2000);  
        return "Hello World";  
    }  
}

我们启动项目,使用JVisualVM监测一下此时项目中的线程数为2个:

此时我们使用Apifox发起一个请求,观察线程数没有增长。我们在使用Apifox中模拟3个线程同时请求,发现此时线程数变成5个:

我们继续增加线程数到7个,我们发现线程数还是5个,因最大线程数等于5个:

后台请求全部成功:

我们继续增加线程数到8个,此时线城数依然是5个,设置请求超时时间为1秒,但是有一个请求失败:


服务端只处理了7个请求:

结论

SpringBoot可以同时处理多少个请求,需要看其内嵌的Sevlet处理线程的能力,以Tomcat为例,即Tomcat可以处理多少请求,这需要看配置文件中设置的server.tomcat.accept-count以及server.tomcat.max-connections的大小。Tomcat同时可以处理的请求为server.tomcat.accept-count加上 server.tomcat.max-connections。实际生产应用中我们需要根据服务器,硬件的配置等综合因素考虑后,调节这两个值,确保应用程序能够处理预期的并发量。

本文已收录于我的个人博客:码农Academy的博客,专注分享Java技术干货,包括Java基础、Spring Boot、Spring Cloud、Mysql、Redis、Elasticsearch、中间件、架构设计、面试题、程序员攻略等

相关推荐
_风中无我。4 分钟前
深圳行,面试笔记!
笔记·面试·职场和发展
许彰午8 分钟前
02-手写链表、栈、队列——不依赖任何集合框架
数据结构·链表·面试
qq_589568109 小时前
springbootweb案例,出现访问 http://localhost:8080/list 一直处于浏览器运转阶段
java·网络协议·http·list·springboot
AI人工智能+电脑小能手12 小时前
【大白话说Java面试题】【Java基础篇】第30题:JDK动态代理和CGLIB动态代理有什么区别
java·开发语言·后端·面试·代理模式
头发够用的程序员12 小时前
C++和Python面试经典算法汇总(一)
开发语言·c++·python·算法·容器·面试
云泽80814 小时前
二叉树高阶笔试算法题精讲(二):非递归遍历与序列构造全解析
c++·算法·面试
Cosolar15 小时前
大型语言模型(LLM)微调与量化技术全指南——从预训练到高效部署
人工智能·后端·面试
沪漂阿龙15 小时前
深度硬核!2026年NLP面试最全指南:从Word2Vec到Transformer,大模型时代算法工程师通关秘籍
自然语言处理·面试·word2vec
xsgbbx20 小时前
Agent Skills 实战:用 SKILL.md 把 Claude Code 从助手变成队友
面试
knight_9___20 小时前
LLM工具调用面试篇6
人工智能·python·面试·职场和发展·llm·agent