Tomcat基础升华学习

2024-01-13 00:36
文章标签 基础 学习 tomcat 升华

本文主要是介绍Tomcat基础升华学习,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

01 What is Tomcat

1.1 Tomcat官网

官网 :https://tomcat.apache.org

1.2 Understand

为什么说Tomcat是Servlet之类技术的实现?
在我们的理解中,Tomcat可以称为Web容器或者Servlet容器
不妨通过手写一个Tomcat来推导一下

1.2.1 创建Tomcat类

Java是一门面向对象的开发语言

//这就是我们写的Tomcat
class MyTomcat{
....
}
1.2.2 Web容器

在这里插入图片描述
在这里插入图片描述
使用命令查看相关指标

01 查看tomcat进程pid
ps -ef | grep tomcat
02 查看进程的信息
cat /pro/pid/status
03 查看进程的cpu和内存
top -p pid

使用工具查看相关指标

jconsole、jvisualvm、arthas、psi-probe等

1.1 优化思路

1.1.1 conf/server.xml核心组件

Server
官网描述 :Server interface which is rarely customized by users. 【pass】
Service
官网描述 :The Service element is rarely customized by users. 【pass】
Connector
官网描述 :Creating a customized connector is a significant effort. 【 need 】
Engine
官网描述 :The Engine interface may be implemented to supply custom Engines, though this is uncommon.
【pass】
Host
官网描述 :Users rarely create custom Hosts because the StandardHost implementation provides significant
additional functionality. 【pass】
Context
官网描述 :The Context interface may be implemented to create custom Contexts, but this is rarely the case
because the StandardContext provides significant additional functionality. 【 maybe 】
Context既然代表的是web应用,是和我们比较接近的,这块我们考虑对其适当的优化
conclusion:Connector and Context

1.1.2 conf/server.xml非核心组件

官网 :https://tomcat.apache.org/tomcat-8.0-doc/config/index.html
Listener
Listener(即监听器)定义的组件,可以在特定事件发生时执行特定的操作;被监听的事件通常是Tomcat的启动和停止。

<Listener className="org.apache.catalina.core.AprLifecycleListener" SSLEngine="on" />
<!--监听内存溢出-->
<Listener className="org.apache.catalina.core.JreMemoryLeakPreventionListener" />
<Listener className="org.apache.catalina.mbeans.GlobalResourcesLifecycleListener" />
<Listener className="org.apache.catalina.core.ThreadLocalLeakPreventionListener" />

Global Resources
GlobalNamingResources元素定义了全局资源,通过配置可以看出,该配置是通过读取$TOMCAT_HOME/
conf/tomcat-users.xml实现的。
The GlobalNamingResources element defines the global JNDI resources for the [Server]
(https://tomcat.apache.org/tomcat-8.0-doc/config/server.html)

<GlobalNamingResources>
<Resource name="UserDatabase" auth="Container"
type="org.apache.catalina.UserDatabase"
description="User database that can be updated and saved"
factory="org.apache.catalina.users.MemoryUserDatabaseFactory"
pathname="conf/tomcat-users.xml" />
</GlobalNamingResources>

Valve

<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs"
prefix="localhost_access_log" suffix=".txt"
pattern="%h %l %u %t &quot;%r&quot; %s %b" />

Realm
Realm,可以把它理解成“域”;Realm提供了一种用户密码与web应用的映射关系,从而达到角色安全管理的作用。在本例
中,Realm的配置使用name为UserDatabase的资源实现。而该资源在Server元素中使用GlobalNamingResources配置
A Realm element represents a “database” of usernames, passwords, and roles (similar to
Unix groups) assigned to those users.

<Realm className="org.apache.catalina.realm.LockOutRealm">
<!-- This Realm uses the UserDatabase configured in the global JNDI
resources under the key "UserDatabase". Any edits
that are performed against this UserDatabase are immediately
available for use by the Realm. -->
<Realm className="org.apache.catalina.realm.UserDatabaseRealm"
resourceName="UserDatabase"/>
</Realm>
1.1.3 conf/web.xml

全局的web.xml文件有些标签用不到的,可以删除掉。

1.1.4 JVM层面

因为Tomcat运行起来本身就是一个Java进程,所以这块可以参照JVM部分的优化思路。

1.2 配置优化

1.2.1 减少web.xml/server.xml中标签

最终观察tomcat启动日志[时间/内容],线程开销,内存大小,GC等
DefaultServlet
官网 :User Guide->Default Servlet
The default servlet is the servlet which serves static resources as well as serves the directory listings (if
directory listings are enabled)

<servlet><servlet-name>default</servlet-name><servlet-class>org.apache.catalina.servlets.DefaultServlet</servlet-class><init-param><param-name>debug</param-name><param-value>0</param-value></init-param><init-param><param-name>listings</param-name><param-value>false</param-value></init-param><load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping><servlet-name>default</servlet-name><url-pattern>/</url-pattern>
</servlet-mapping>

JspServlet

<servlet><servlet-name>jsp</servlet-name><servlet-class>org.apache.jasper.servlet.JspServlet</servlet-class><init-param><param-name>fork</param-name><param-value>false</param-value></init-param><init-param><param-name>xpoweredBy</param-name><param-value>false</param-value></init-param><load-on-startup>3</load-on-startup>
</servlet>
<servlet-mapping><servlet-name>jsp</servlet-name><url-pattern>*.jsp</url-pattern><url-pattern>*.jspx</url-pattern>
</servlet-mapping>

welcome-list-file

<welcome-file-list><welcome-file>index.html</welcome-file><welcome-file>index.htm</welcome-file><welcome-file>index.jsp</welcome-file>
</welcome-file-list>

mime-mapping移除响应的内容
支持的下载打开类型

<mime-mapping><extension>123</extension><mime-type>application/vnd.lotus-1-2-3</mime-type>
</mime-mapping>
<mime-mapping><extension>3dml</extension><mime-type>text/vnd.in3d.3dml</mime-type>
</mime-mapping>

session-config
默认jsp页面有session,就是在于这个配置

<session-config><session-timeout>30</session-timeout>
</session-config>
1.2.2 调整优化server.xml中标签
1.2.2.1 Connector标签

protocol属性

<Connector port="8080" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />

对于protocol=“HTTP/1.1”,查看源码
构造函数

public Connector(String protocol) {
setProtocol(protocol);
}

setProtocol(protocol)因为配置文件中传入的是HTTP/1.1
并且这里没有使用APR

else {if ("HTTP/1.1".equals(protocol)) {setProtocolHandlerClassName("org.apache.coyote.http11.Http11NioProtocol");} else if ("AJP/1.3".equals(protocol)) {setProtocolHandlerClassName("org.apache.coyote.ajp.AjpNioProtocol");} else if (protocol != null) {setProtocolHandlerClassName(protocol);}
}

发现这里调用的是Http11NioProtocol,也就是说明tomcat8.0.x中默认使用的是NIO
使用同样的方式看tomcat7和tomcat8.5,你会发现tomcat7默认使用的是BIO,tomcat8.5默认使用的是NIO
针对BIO和NIO的方式进行压测
(1)BIO
来到tomcat官网Configuration/HTTP/protocol

org.apache.coyote.http11.Http11Protocol - blocking Java connector
org.apache.coyote.http11.Http11NioProtocol - non blocking Java NIO connector
org.apache.coyote.http11.Http11Nio2Protocol - non blocking Java NIO2 connector
org.apache.coyote.http11.Http11AprProtocol - the APR/native connector.

(2)NIO
tomcat8.0中默认使用的是NIO
(3)APR
调用本地方法库进行IO操作
executor属性
最佳线程数公式 😦(线程等待时间+线程cpu时间)/线程cpu时间) * cpu数量

The Executor represents a thread pool that can be shared between components in Tomcat.
Historically there has been a thread pool per connector created but this allows you to
share a thread pool, between (primarily) connector but also other components when those get
configured to support executors

默认的可以查看StandardExecutor类
设置一些属性
官网:https://tomcat.apache.org/tomcat-8.0-doc/config/http.html
(1)acceptCount:达到最大连接数之后,等待队列中还能放多少连接,超过即拒绝,配置太大也没有意义

The maximum queue length for incoming connection requests when all possible request
processing threads are in use. Any requests received when the queue is full will be
refused. The default value is 100.

(2)maxConnections
达到这个值之后,将继续接受连接,但是不处理,能继续接受多少根据acceptCount的值
BIO:maxThreads
NIO/NIO2:10000 ——— AbstractEndpoint.maxConnections
APR:8192

The maximum number of connections that the server will accept and process at any given
time. When this number has been reached, the server will accept, but not process, one
further connection. This additional connection be blocked until the number of connections
being processed falls below maxConnections at which point the server will start accepting
and processing new connections again. Note that once the limit has been reached, the
operating system may still accept connections based on the acceptCount setting. The default
value varies by connector type. For BIO the default is the value of maxThreads unless an
Executor is used in which case the default will be the value of maxThreads from the
executor. For NIO and NIO2 the default is 10000. For APR/native, the default is 8192.
Note that for APR/native on Windows, the configured value will be reduced to the highest
multiple of 1024 that is less than or equal to maxConnections. This is done for performance
reasons.
If set to a value of -1, the maxConnections feature is disabled and connections are not
counted.

(3)maxThreads:最大工作线程数,也就是用来处理request请求的,默认是200,如果自己配了executor,并且和
Connector有关联了,则之前默认的200就会被忽略,取决于CPU的配置。监控中就可以看到所有的工作线程是什么
状态,通过监控就能知道开启多少个线程合适.

The maximum number of request processing threads to be created by this Connector, which
therefore determines the maximum number of simultaneous requests that can be handled. If
not specified, this attribute is set to 200. If an executor is associated with this
connector, this attribute is ignored as the connector will execute tasks using the executor
rather than an internal thread pool. Note that if an executor is configured any value set
for this attribute will be recorded correctly but it will be reported (e.g. via JMX) as -1
to make clear that it is not used.

(4)minSpareThreads
最小空闲线程数

The minimum number of threads always kept running. This includes both active and idle
threads. If not specified, the default of 10 is used. If an executor is associated with
this connector, this attribute is ignored as the connector will execute tasks using the
executor rather than an internal thread pool. Note that if an executor is configured any
value set for this attribute will be recorded correctly but it will be reported (e.g. via
JMX) as -1 to make clear that it is not used.

可以实践一下,Connector配合自定义的线程池

<Connector executor="tomcatThreadPool"
port="8080" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
<Executor name="tomcatThreadPool" namePrefix="catalina-exec-"
maxThreads="150" minSpareThreads="4"/>

其实这块最好的方式是结合BIO来看,因为BIO是一个request对应一个线程
值太低,并发请求多了之后,多余的则进入等待状态。
值太高,启动Tomcat将花费更多的时间。
比如可以改成250。
enableLookups
设置为false
删掉AJP的Connector

1.2.2.2 Host标签

autoDeploy :Tomcat运行时,要用一个线程拿出来进行检查,生产环境之下一定要改成false

This flag value indicates if Tomcat should check periodically for new or updated web
applications while Tomcat is running. If true, Tomcat periodically checks the appBase and
xmlBase directories and deploys any new web applications or context XML descriptors found.
Updated web applications or context XML descriptors will trigger a reload of the web
application. The flag's value defaults to true. See Automatic Application Deployment for
more information.
1.2.2.3 Context标签

reloadable:false
reloadable:如果这个属性设为true,tomcat服务器在运行状态下会监视在WEB-INF/classes和WEB-INF/lib目录下
class文件的改动,如果监测到有class文件被更新的,服务器会自动重新加载Web应用。
在开发阶段将reloadable属性设为true,有助于调试servlet和其它的class文件,但这样用加重服务器运行负荷,建议
在Web应用的发存阶段将reloadable设为false。

Set to true if you want Catalina to monitor classes in /WEB-INF/classes/ and /WEB-INF/lib
for changes, and automatically reload the web application if a change is detected. This
feature is very useful during application development, but it requires significant runtime
overhead and is not recommended for use on deployed production applications. That's why the
default setting for this attribute is false. You can use the Manager web application,
however, to trigger reloads of deployed applications on demand.

1.3 启动速度优化

删除没用的web应用
因为tomcat启动每次都会部署这些应用
关闭WebSocket
websocket-api.jar和tomcat-websocket.jar
随机数优化
设置JVM参数:-Djava.security.egd=file:/dev/./urandom
多个线程启动Web应用

<Host startStopThreads="0">
</Host>

1.4 其他方面的优化

Connector
配置压缩属性compression=“500”,文件大于500bytes才会压缩
数据库优化
减少对数据库访问等待的时间,可以从数据库的层面进行优化,或者加缓存等等各种方案。
开启浏览器缓存,nginx静态资源部署

1.5 常见问题排查

1.5.1 CPU使用率过高

可能原因
GC频繁或者创建了很多业务线程
排查
哪些线程比较消耗CPU,或者多线程上下文频繁切换
解决思路
top -H -p pid 查看某个Java进程各个线程使用CPU的情况,找到哪个线程占用CPU比较高
jstack pid 打印出线程信息,定位到上述的线程名称

1.5.2 拒绝连接

java.net.BindException: Address already in use: JVM_Bind
端口被占用,可以使用netstat -an 查看端口占用情况,关闭对应的进程或者tomcat换端口
java.net.ConnectException: Connection refused: connect
ping一下服务端的IP,可能服务端机器有问题
java.net.SocketException: Too many open files
可能在高并发的情况下,创建的Socket过多,文件句柄不够用了,可以关闭无用的句柄,如果都有用,可以增加文件
句柄数:ulimit -n 10000

这篇关于Tomcat基础升华学习的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/599686

相关文章

HarmonyOS学习(七)——UI(五)常用布局总结

自适应布局 1.1、线性布局(LinearLayout) 通过线性容器Row和Column实现线性布局。Column容器内的子组件按照垂直方向排列,Row组件中的子组件按照水平方向排列。 属性说明space通过space参数设置主轴上子组件的间距,达到各子组件在排列上的等间距效果alignItems设置子组件在交叉轴上的对齐方式,且在各类尺寸屏幕上表现一致,其中交叉轴为垂直时,取值为Vert

Ilya-AI分享的他在OpenAI学习到的15个提示工程技巧

Ilya(不是本人,claude AI)在社交媒体上分享了他在OpenAI学习到的15个Prompt撰写技巧。 以下是详细的内容: 提示精确化:在编写提示时,力求表达清晰准确。清楚地阐述任务需求和概念定义至关重要。例:不用"分析文本",而用"判断这段话的情感倾向:积极、消极还是中性"。 快速迭代:善于快速连续调整提示。熟练的提示工程师能够灵活地进行多轮优化。例:从"总结文章"到"用

【前端学习】AntV G6-08 深入图形与图形分组、自定义节点、节点动画(下)

【课程链接】 AntV G6:深入图形与图形分组、自定义节点、节点动画(下)_哔哩哔哩_bilibili 本章十吾老师讲解了一个复杂的自定义节点中,应该怎样去计算和绘制图形,如何给一个图形制作不间断的动画,以及在鼠标事件之后产生动画。(有点难,需要好好理解) <!DOCTYPE html><html><head><meta charset="UTF-8"><title>06

学习hash总结

2014/1/29/   最近刚开始学hash,名字很陌生,但是hash的思想却很熟悉,以前早就做过此类的题,但是不知道这就是hash思想而已,说白了hash就是一个映射,往往灵活利用数组的下标来实现算法,hash的作用:1、判重;2、统计次数;

零基础学习Redis(10) -- zset类型命令使用

zset是有序集合,内部除了存储元素外,还会存储一个score,存储在zset中的元素会按照score的大小升序排列,不同元素的score可以重复,score相同的元素会按照元素的字典序排列。 1. zset常用命令 1.1 zadd  zadd key [NX | XX] [GT | LT]   [CH] [INCR] score member [score member ...]

【机器学习】高斯过程的基本概念和应用领域以及在python中的实例

引言 高斯过程(Gaussian Process,简称GP)是一种概率模型,用于描述一组随机变量的联合概率分布,其中任何一个有限维度的子集都具有高斯分布 文章目录 引言一、高斯过程1.1 基本定义1.1.1 随机过程1.1.2 高斯分布 1.2 高斯过程的特性1.2.1 联合高斯性1.2.2 均值函数1.2.3 协方差函数(或核函数) 1.3 核函数1.4 高斯过程回归(Gauss

【学习笔记】 陈强-机器学习-Python-Ch15 人工神经网络(1)sklearn

系列文章目录 监督学习:参数方法 【学习笔记】 陈强-机器学习-Python-Ch4 线性回归 【学习笔记】 陈强-机器学习-Python-Ch5 逻辑回归 【课后题练习】 陈强-机器学习-Python-Ch5 逻辑回归(SAheart.csv) 【学习笔记】 陈强-机器学习-Python-Ch6 多项逻辑回归 【学习笔记 及 课后题练习】 陈强-机器学习-Python-Ch7 判别分析 【学

系统架构师考试学习笔记第三篇——架构设计高级知识(20)通信系统架构设计理论与实践

本章知识考点:         第20课时主要学习通信系统架构设计的理论和工作中的实践。根据新版考试大纲,本课时知识点会涉及案例分析题(25分),而在历年考试中,案例题对该部分内容的考查并不多,虽在综合知识选择题目中经常考查,但分值也不高。本课时内容侧重于对知识点的记忆和理解,按照以往的出题规律,通信系统架构设计基础知识点多来源于教材内的基础网络设备、网络架构和教材外最新时事热点技术。本课时知识

【Linux 从基础到进阶】Ansible自动化运维工具使用

Ansible自动化运维工具使用 Ansible 是一款开源的自动化运维工具,采用无代理架构(agentless),基于 SSH 连接进行管理,具有简单易用、灵活强大、可扩展性高等特点。它广泛用于服务器管理、应用部署、配置管理等任务。本文将介绍 Ansible 的安装、基本使用方法及一些实际运维场景中的应用,旨在帮助运维人员快速上手并熟练运用 Ansible。 1. Ansible的核心概念

线性代数|机器学习-P36在图中找聚类

文章目录 1. 常见图结构2. 谱聚类 感觉后面几节课的内容跨越太大,需要补充太多的知识点,教授讲得内容跨越较大,一般一节课的内容是书本上的一章节内容,所以看视频比较吃力,需要先预习课本内容后才能够很好的理解教授讲解的知识点。 1. 常见图结构 假设我们有如下图结构: Adjacency Matrix:行和列表示的是节点的位置,A[i,j]表示的第 i 个节点和第 j 个