在上周三下午时,客户、业务和测试人员同时反溃生产环境登录进入不了系统,我亲自测试时,第一次登录进去了,待退出后再登录时,复现了客户的问题,场景像是请求连接被拒绝了,分析后判断是spring boot的连接数使用完了,于是重启了服务,客户访问都恢复正常。虽然问题暂时解决了,但实质原因还无法确定。根据分析,判断是spring boot服务连接被拒绝,查看配置的最大连接数和最大线程数时,配置为:
#最大连接数
server.tomcat.max-connections=300
#最大线程数
server.tomcat.max-threads=200
为了验证自己的分析,于是将最大连接数和最大线程数都设置为3,如下:
#最大连接数
server.tomcat.max-connections=3
#最大线程数
server.tomcat.max-threads=3
启动服务后,打开4个浏览器(IE、google、火狐、360),在这4个浏览器中,登录IE、google和火狐后,再登录360浏览器时,生产环境的场景复现了;重启服务,再先登录360、火狐、IE后,再登录google时,生产环境的场景同样复现了。
由此断定,spring boot中内嵌的tomcat的最大连接数达到最大值后,在没有连接数释放的情况下,新的请求会被服务器拒绝,即测试验证中第4个浏览器进入不了系统的原因。
由于公司该企业级服务系统的上线,用户量远少于300,就很奇怪连接数为何会被耗尽。
经过进一步排查,是由于系统上线后,用户的登录,支持多个用户共用一个账号,同时单个用户的会话有效期设置为了3天,客户之前在系统中出现过浏览器兼容性问题导致一个客户在一台电脑的多个浏览器上登录,另外业务人员、测试人员都在上面验证着客户的问题,都在占用着连接数,综合以上因素,导致了该系统上300个连接数被耗尽了。
为了解决这个问题,必须对tomcat的最大连接数等参数做优化设置。查询了tomcat的常用参数,其中最大连接数、最大线程数和最大等待数信息如下 :

1)maxThreads(最大线程数)
每一次HTTP请求到达Web服务器,Web服务器都会创建一个线程来处理该请求,该参数决定了应用服务同时可以处理多少个HTTP请求,tomcat默认为200;

2)accepCount(最大等待数)
当调用Web服务的HTTP请求数达到tomcat的最大线程数时,还有新的HTTP请求到来,这时tomcat会将该请求放在等待队列中,这个acceptCount就是指能够接受的最大等待数,默认100.如果等待队列也被放满了,这个时候再来新的请求就会被tomcat拒绝(connection refused);

3)maxConnections(最大连接数)
这个参数是指在同一时间,tomcat能够接受的最大连接数。一般这个值要大于maxThreads+acceptCount。
根据公司用户量及机器配置信息,公司的最大连接数、最大线程数和最大等待数优化为:
#最大连接数
server.tomcat.max-connections=2000
#最大线程数
server.tomcat.max-threads=1000
#最大等待数
server.tomcat.accept-count=800

1)maxThreads(最大线程数)
每一次HTTP请求到达Web服务器,Web服务器都会创建一个线程来处理该请求,该参数决定了应用服务同时可以处理多少个HTTP请求,tomcat默认为200;

2)accepCount(最大等待数)
当调用Web服务的HTTP请求数达到tomcat的最大线程数时,还有新的HTTP请求到来,这时tomcat会将该请求放在等待队列中,这个acceptCount就是指能够接受的最大等待数,默认100.如果等待队列也被放满了,这个时候再来新的请求就会被tomcat拒绝(connection refused);

3)maxConnections(最大连接数)
这个参数是指在同一时间,tomcat能够接受的最大连接数。一般这个值要大于maxThreads+acceptCount。
根据公司用户量及机器配置信息,公司的最大连接数、最大线程数和最大等待数优化为:
#最大连接数
server.tomcat.max-connections=2000
#最大线程数
server.tomcat.max-threads=1000
#最大等待数
server.tomcat.accept-count=800

增加线程是有成本的。JVM中默认情况下在创建新线程时会分配固定大小的线程栈,所以更多的线程异味着更多的内存;
更多的线程会带来更多的线程上下文切换成本。

如果线程占用的资源过大,会导致内存溢出(Cannt’ allocate memory)情况出现。因此需要对JVM及线程的相关参数做合理配置。

在jvm内存调整过程中,我们经常使用的参数就是:

-Xms 为jvm启动时分配的初始堆的大小,也是堆大小的最小值,比如-Xms200m,表示分配200M
-Xmx 为jvm运行过程中分配的最大堆内存,比如-Xmx500m,表示jvm进程最多只能够占用500M内存
-Xss 为jvm启动的每个线程分配的内存大小,默认JDK1.4中是256K,JDK1.5+中是1M

Spring boot中最大连接数、最大线程数与最大等待数在生产中的异常场景的更多相关文章

  1. spring boot(三):Spring Boot中Redis的使用

    spring boot对常用的数据库支持外,对nosql 数据库也进行了封装自动化. redis介绍 Redis是目前业界使用最广泛的内存数据存储.相比memcached,Redis支持更丰富的数据结 ...

  2. Spring Boot:Spring Boot 中 Redis 的使用

    Redis 介绍 Redis 是目前业界使用最广泛的内存数据存储.相比 Memcached,Redis 支持更丰富的数据结构,例如 hashes, lists, sets 等,同时支持数据持久化.除此 ...

  3. (转)Spring Boot(三):Spring Boot 中 Redis 的使用

    http://www.ityouknow.com/springboot/2016/03/06/spring-boot-redis.html Spring Boot 对常用的数据库支持外,对 Nosql ...

  4. Spring Boot(三):Spring Boot 中 Redis 的使用

    Spring Boot 对常用的数据库支持外,对 Nosql 数据库也进行了封装自动化. Redis 介绍 Redis 是目前业界使用最广泛的内存数据存储.相比 Memcached,Redis 支持更 ...

  5. Spring Boot中使用Redis小结

    Spring Boot中除了对常用的关系型数据库提供了优秀的自动化支持之外,对于很多NoSQL数据库一样提供了自动化配置的支持,包括:Redis, MongoDB, 等. Redis简单介绍 Redi ...

  6. Spring Boot中的事务是如何实现的

    本文首发于微信公众号[猿灯塔],转载引用请说明出处 今天呢!灯塔君跟大家讲: Spring Boot中的事务是如何实现的 1. 概述 一直在用SpringBoot中的@Transactional来做事 ...

  7. springboot(三):Spring boot中Redis的使用

    spring boot对常用的数据库支持外,对nosql 数据库也进行了封装自动化. redis介绍 Redis是目前业界使用最广泛的内存数据存储.相比memcached,Redis支持更丰富的数据结 ...

  8. 初识在Spring Boot中使用JPA

    前面关于Spring Boot的文章已经介绍了很多了,但是一直都没有涉及到数据库的操作问题,数据库操作当然也是我们在开发中无法回避的问题,那么今天我们就来看看Spring Boot给我们提供了哪些疯狂 ...

  9. Spring Boot中通过CORS解决跨域问题

    今天和小伙伴们来聊一聊通过CORS解决跨域问题. 同源策略 很多人对跨域有一种误解,以为这是前端的事,和后端没关系,其实不是这样的,说到跨域,就不得不说说浏览器的同源策略. 同源策略是由Netscap ...

随机推荐

  1. audio小记

    写H5活动页的需要音频,图标旋转停止保持当时的旋转角度,这样视觉体验效果好: 之前写法是点击pause()就直接停止动画,后来发现了animation有个比较好的属性animation-play-st ...

  2. setTimeout中第一个参数

    永远不要传递字符串作为setTimeout的第一个参数!!!记住第一个参数只允许函数,或者匿名函数!因为传递字符串有陷阱啊!!它就是披着羊皮的eval啊!!而且上下文会变成全局啊!! 第一个参数为可执 ...

  3. Java---变量和基本数据类型

    变量 在Java中,变量分为两种:基本类型的变量和引用类型的变量. 在Java中变量必须先定义后使用,在定义变量的时候可以给它一个初始值.如果不写初始值,默认为0或空. 变量的一个重要特点是可以重新赋 ...

  4. Windows和ubuntu下更改pip国内镜像

    windows下更改pip国内镜像 # 在C:\Users\admin路径下创建pip文件夹,然后创建pip.ini文件, 并在文件下写入 [global] index-url = http://py ...

  5. FFMPEG第一次学习

    习惯用OneNote笔记,直接复制了,链接和一些命令放在最下面了 里面的库文件是我下的雷神的课件文件,我传到了自己github,链接也放最后了 转载自:https://blog.csdn.net/le ...

  6. [个人配置] VSCode Better Comments 扩展配置、高亮注释插件

    在VSCode IDE中,我的代码注释一般都有高亮颜色,那要怎么安装这个插件呢?

  7. Java学习day32

    生产与消费者问题:假设仓库中只能存放一件产品,生产者将生产出来的产品放入仓库,消费者从仓库中取走产品:如果仓库中没有产品,生产者就将产品放入仓库,否则就停止生产等待:如果仓库中有产品,消费者就取走,否 ...

  8. el-tree小知识点

    <el-tree ref="tree" :props="props" :data="initData" node-key=" ...

  9. 论文阅读 Continuous-Time Dynamic Network Embeddings

    1 Continuous-Time Dynamic Network Embeddings Abstract ​ 描述一种将时间信息纳入网络嵌入的通用框架,该框架提出了从CTDG中学习时间相关嵌入 Co ...

  10. js常用框架原理

    (function(){         //存储已经创建的模块     var moduleMap = {};     //判断是否已经加载过     var fileMap   = {};     ...