Tomcat 并发调优
6/Aug 2014
一. Linux系统配置
1. 增大最大打开文件数限制
$ sudo vim /etc/sysctl.conf
# add "fs.file-max = 8061540"
$ sudo vim /etc/security/limit.conf
# add "* soft nofile 8192" and "* hard nofile 16384"
2. 优化网络
$ sudo vim /etc/sysctl.conf
优化后的内容如下:
net.ipv4.ip_forward = 0
# Controls source route verification
net.ipv4.conf.default.rp_filter = 1
# Do not accept source routing
net.ipv4.conf.default.accept_source_route = 0
# Controls the System Request debugging functionality of the kernel
kernel.sysrq = 0
# Controls whether core dumps will append the PID to the core filename
# Useful for debugging multi-threaded applications
kernel.core_uses_pid = 1
# Controls the use of TCP syncookies
net.ipv4.tcp_syncookies = 1
# Controls the maximum size of a message, in bytes
kernel.msgmnb = 65536
# Controls the default maxmimum size of a mesage queue
kernel.msgmax = 65536
# Controls the maximum shared segment size, in bytes
kernel.shmmax = 68719476736
# Controls the maximum number of shared memory segments, in pages
kernel.shmall = 4294967296
vm.swappiness = 0
kernel.core_pattern = /tmp/corefile/core-%e-%p-%t
net.ipv4.tcp_tw_reuse = 1
net.ipv4.tcp_tw_recycle = 1
net.ipv4.tcp_fin_timeout = 5
net.ipv4.tcp_max_syn_backlog = 65536
net.core.netdev_max_backlog = 32768
net.core.somaxconn = 32768
net.core.wmem_default = 8388608
net.core.rmem_default = 8388608
net.core.rmem_max = 16777216
net.core.wmem_max = 16777216
net.ipv4.tcp_timestamps = 0
net.ipv4.tcp_synack_retries = 2
net.ipv4.tcp_syn_retries = 2
net.ipv4.tcp_mem = 94500000 915000000 927000000
net.ipv4.tcp_max_orphans = 3276800
net.ipv4.ip_local_port_range = 2000 65535
net.ipv4.tcp_max_tw_buckets = 5000
net.ipv4.netfilter.ip_conntrack_max = 1000000
二. Tomcat内存优化
Tomcat内存优化主要是对 Tomcat 启动参数优化,我们可以在 Tomcat 的启动脚本 catalina.sh 中设置 JAVA_OPTS 参数
-server: 启用jdk的server版,一定要作为第一个参数,在多个CPU时性能佳
-Xms: 初始Heap大小,使用的最小内存,cpu性能高时此值应设的大一些
-Xmx: java heap最大值,使用的最大内存
上面两个值是分配JVM的最小和最大内存,取决于硬件物理内存的大小,建议均设为物理内存的一半。
-XX:PermSize:设定内存的永久保存区域
-XX:MaxPermSize:设定最大内存的永久保存区域
-XX:MaxNewSize:
-Xss 15120 这使得JBoss每增加一个线程(thread)就会立即消耗15M内存,而最佳值应该是128K,默认值好像是512k.
+XX:AggressiveHeap 会使得 Xms没有意义。这个参数让jvm忽略Xmx参数,疯狂地吃完一个G物理内存,再吃尽一个G的swap。
-Xss:每个线程的Stack大小
-verbose:gc 现实垃圾收集信息
-Xloggc:gc.log 指定垃圾收集日志文件
-Xmn:young generation的heap大小,一般设置为Xmx的3、4分之一
-XX:+UseParNewGC :缩短minor收集的时间
-XX:+UseConcMarkSweepGC :缩短major收集的时间
提示:此选项在Heap Size 比较大而且Major收集时间较长的情况下使用更合适。
三. Tomcat并发优化
1.Tomcat连接相关参数
在Tomcat配置文件conf/server.xml 中的Connector配置中
acceptCount:允许的最大连接数
enableLookups:是否反查域名,取值为: true 或 false 。为了提高处理能力,应设置为 false
connectionTimeout:网络连接超时,单位:毫秒。设置为 0 表示永不超时,这样设置有隐患的。通常可设置为 30000 毫秒。
其中和最大连接数相关的参数为maxProcessors 和 acceptCount。如果要加大并发连接数,应同时加大这两个参数。
2.调整连接器connector的并发处理能力
maxThreads 客户请求最大线程数
minSpareThreads Tomcat初始化时创建的 socket 线程数
maxSpareThreads Tomcat连接器的最大空闲 socket 线程数
enableLookups 若设为true, 则支持域名解析,可把 ip 地址解析为主机名
redirectPort 在需要基于安全通道的场合,把客户请求转发到基于SSL 的 redirectPort 端口
acceptAccount 监听端口队列最大数,满了之后客户请求会被拒绝(不能小于maxSpareThreads)
connectionTimeout 连接超时
URIEncoding URL统一编码
3.Tomcat缓存优化
compression 打开压缩功能
compressionMinSize 启用压缩的输出内容大小,这里面默认为2KB
compressableMimeType 压缩类型
connectionTimeout 定义建立客户连接超时的时间. 如果为 -1, 表示不限制建立客户连接的时间
结合以上方面,对server.xml的现有配置为:
<Connector port="9027"
maxHttpHeaderSize="8192"
maxThreads="2048"
minSpareThreads="256"
enableLookups="false"
compression="on"
compressionMinSize="2048"
compressableMimeType="text/html,text/xml,text/javascript,text/css,text/plain"
connectionTimeout="20000"
URIEncoding="utf-8"
acceptCount="2048"
redirectPort="8443"
disableUploadTimeout="true"
executor="tomcatThreadPool" />
<Executor name="tomcatThreadPool"
namePrefix="catalina-exec-"
maxThreads="2048"
minSpareThreads="512"
prestartminSpareThreads="true" />
四. Tomcat Native
Tomcat可以使用APR来提供超强的可伸缩性和性能,更好地集成本地服务器技术。APR(Apache Portable Runtime)
是一个高可移植库,它是Apache HTTP Server 2.x的核心。APR有很多用途,包括访问高级IO功能(例如sendfile,
epoll和OpenSSL),OS级别功能(随机数生成,系统状态等等),本地进程管理(共享内存,NT管道和UNIX sockets)。这些功能可以
使Tomcat作为一个通常的前台WEB服务器,能更好地和其它本地web技术集成,总体上让Java更有效率作为一个高性能web服务器
平台而不是简单作为后台容器。
在产品环境中,特别是直接使用Tomcat做WEB服务器的时候,应该使用Tomcat Native来提高其性能。
说白了,就是如何 在Tomcat中使用JNI的方式来读取文件以及进行网络传输。这个东西可以大大提升Tomcat对静态文件的处理性能,同时如果你使用了HTTPS方式 传输的话,也可以提升SSL的处理性能。
- a. 安装 apr
$ sudo ./configure --prefix=/opt/apr
$ sudo make
$ sudo make install
- b. 安装 apr-iconv
$ sudo ./configure --prefix=/opt/apr-iconv --with-apr=/opt/apr
$ sudo make
$ sudo make install
- c. 安装 apr-util
$ sudo ./configure --prefix=/opt/apr-util --with-apr=/opt/apr --with-apr-iconv=/opt/apr-iconv/bin/apriconv
$ sudo make
$ sudo make install
- d. 安装 tomcat-native
$ cd $TOMCAT_HOME/bin/tomcat-native-1.1.30-src/jni/native
$ ./configure --with-apr=/opt/apr --with-java-home=/usr/lib/jvm/java-7-openjdk-i386/
$ sudo make
$ sudo make install
五. 总结
为了提高Tomcat的并发处理能力,我从以上几个方面进行了逐步的增量调优,每次优化或者做出改变之后,都从Client用ab模拟并发,观察QPS等指标,并同时在Server端监控各种系统信息:
sudo /opt/apache/bin/ab -n 50000 -c 2000 http://192.168.1.2:9027/performance/test.jsp
目前比较好的测试结果如下:
Server Software: Apache-Coyote/1.1
Server Hostname: 192.168.1.2
Server Port: 9027
Document Path: /performance/test.jsp
Document Length: 253 bytes
Concurrency Level: 2000
Time taken for tests: 4.089 seconds
Complete requests: 50000
Failed requests: 0
Total transferred: 25100000 bytes
HTML transferred: 12650000 bytes
Requests per second: 12227.55 [#/sec] (mean)
Time per request: 163.565 [ms] (mean)
Time per request: 0.082 [ms] (mean, across all concurrent requests)
Transfer rate: 5994.36 [Kbytes/sec] received
Connection Times (ms)
min mean[+/-sd] median max
Connect: 9 77 138.5 54 1070
Processing: 15 81 51.7 76 617
Waiting: 11 59 34.4 57 608
Total: 40 158 148.6 127 1221
Percentage of the requests served within a certain time (ms)
50% 127
66% 147
75% 177
80% 180
90% 196
95% 219
98% 662
99% 1105
100% 1221 (longest request)
但在调优时发现,无论怎样提高各种参数的阈值,并发性都不会再得到明显的提高,有时反而会降低。而且在设置JAVA_OPTS时,-Xms, -Xmx超过2048m时,就会提示超过内存限制。在网路上看到以下内容可以解释这个问题:
`JVM`内存限制于实际的最大物理内存,假设物理内存无限大的话,`JVM`内存的最大值跟操作系统有很大的关系。
简单的说就32位处理器虽然可控内存空间有4GB,但是具体的操作系统会给一个限制,这个限制一般是2GB-3GB(一般
来说`Windows`系统下为1.5G-2G,`Linux`系统下为2G-3G),而64bit以上的处理器就不会有限制了。