Skip to content

Tomcat-基础架构

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

简介

Tomcat是Apache软件基金会(Apache Software Foundation)的Jakarta项目中的一个核心项目,由Apache,Sun和其他一些公司及个人共同开发而成。Tomcat服务器是一个免费的开放源代码的Web应用服务器,属于轻量级应用服务器,在中小型系统和并发访问用户不是很多的场合下被普遍使用,是开发和调试JSP程序的首选。Tomcat和Nginx,APache(httpd),lighttpd等Web服务器一样,具有处理HTML页面的功能,另外它还是一个Servlet和JSP容器,独立的Servlet容器是Tomcat的默认模式。不过,Tomcat处理静态HTML的能力不如Nginx/Apache服务器。

核心特性

  1. 轻量级 Servlet/JSP 容器
    • 实现 Java Servlet 和 JSP 规范(如 Tomcat 10 支持 Servlet 6.0 和 JSP 3.0),但不支持完整 Java EE 规范(如 EJB)。
    • 相比 JBoss、WebLogic 等全功能应用服务器,Tomcat 更轻量,适合中小型项目。
  2. 跨平台与开源
    • 基于 Java 开发,支持 Windows、Linux、macOS 等系统,可免费使用和修改。
  3. 基础 HTTP 服务能力
    • 内置 Coyote 连接器处理 HTTP 请求,但静态资源处理性能弱于 Nginx/Apache,常作为动态请求处理器与反向代理配合。

核心组件

Tomcat 采用分层容器设计,核心模块包括:

  1. Connector(连接器)
    • 监听网络端口(如 HTTP 8080、AJP 8009),将请求解析为 ServletRequest 对象传递给 Container。
    • 支持 BIO/NIO/APR 等 I/O 模型,可通过线程池优化并发处理能力。
  2. Container(容器)
    • Engine:顶级容器,管理多个虚拟主机(Host)。
    • Host:代表虚拟主机(如域名),包含多个 Web 应用(Context)。
    • Context:对应一个 Web 应用(如 WAR 包),包含 Servlet 和静态资源。
    • Wrapper:管理单个 Servlet 的生命周期(初始化、执行、销毁)。
  3. 其他关键组件
    • Catalina:Servlet 容器实现,处理请求调度。
    • Jasper:JSP 编译器,将 JSP 动态编译为 Servlet 执行。
    • Cluster:支持会话复制,实现多实例负载均衡与高可用。

主流Java Web容器

服务器开发厂商开源情况核心定位主要特性适用场景
TomcatApache基金会✅ 开源Servlet/JSP容器轻量级、易配置、社区生态完善,支持Servlet/JSP规范中小型Web应用、Spring Boot项目、开发测试环境
ResinCaucho公司✅ 开源高性能JSP/Servlet引擎静态资源处理能力媲美Nginx,动态内容处理速度比Tomcat快3倍,内置负载均衡高并发网站(如163、ku6)、商业级应用
JettyEclipse基金会✅ 开源嵌入式轻量服务器启动快(秒级)、内存占用低(~50MB),原生支持HTTP/2和WebSocket微服务、IoT设备、云原生架构
JBoss/WildFlyRed Hat✅ 开源全栈Java EE服务器支持EJB/JMS/JPA等企业规范,集成Tomcat作为Web容器,集群管理能力强金融/电信等复杂企业系统
WebLogicOracle❌ 商业企业级Java EE服务器高可靠性、强事务支持,与Oracle数据库深度集成大型分布式系统(银行、电信核心业务)
WebSphereIBM❌ 商业集成式中间件平台支持全栈Java EE,扩展性强,配套IBM生态工具链大型企业混合云架构
  • 轻量级/微服务:Jetty或Undertow(内存占用低于Tomcat 60%)。
  • 企业级全栈需求:WildFly(开源)或WebLogic(商业高可用)。
  • 高并发Web站点:Resin(性能最优)或Nginx+Tomcat组合(静态分离)。
  • 云原生开发:Spring Boot默认Tomcat,资源敏感场景可替换为Jetty/Undertow。

Tomcat与JDK关系

mermaid
graph TD
    %% Tomcat在Java运行环境中的位置
    subgraph Java_Runtime_Environment
        JDK["JDK (开发工具包)"] --> JRE
        JRE["JRE (运行环境)"] --> JVM
        JVM["JVM (Java虚拟机)"] --> OS
    end
    
    OS["OS (操作系统)"] --> Tomcat
    Tomcat["Tomcat"] --> Web_App["Servlet/JSP Web应用"]
    
    %% 开发工具依赖关系
    IDE["Java开发工具
    (Eclipse/IntelliJ等)"] --> JDK
    
    %% 样式定义
    classDef jdk fill:#F5B7B1,stroke:#333
    classDef jre fill:#A9DFBF,stroke:#333
    classDef jvm fill:#F9E79F,stroke:#333
    classDef os fill:#F4D03F,stroke:#333
    classDef tomcat fill:#5DADE2,stroke:#333,color:white
    classDef ide fill:#1F618D,stroke:#333,color:white
    classDef app fill:#7D3C98,stroke:#333,color:white
    
    class JDK jdk
    class JRE jre
    class JVM jvm
    class OS os
    class Tomcat tomcat
    class IDE ide
    class Web_App app
  • JDKJREJVMOS:Tomcat运行在Java运行时环境之上

  • JRE提供核心类库,JVM执行字节码,OS提供底层资源管理

  • 运行原理:

    bash
    [浏览器请求] 
     OS接收网络请求 
     Tomcat(Java进程) 
     JVM加载Servlet类 
     JRE执行字节码 
     返回HTML响应

Tomcat-目录结构

核心目录概览

bash
apache-tomcat-10.1.x/
├── bin/            # 控制脚本
├── conf/           # 全局配置
├── lib/            # 共享类库
├── logs/           # 运行日志
├── webapps/        # 应用部署
├── work/           # 运行时缓存
├── temp/           # 临时文件
├── LICENSE         # 许可证
└── NOTICE          # 版权声明

关键目录解析

bin/ - 控制中心

  • 核心脚本
    • startup.sh/startup.bat:启动服务(内部调用 catalina
    • shutdown.sh/shutdown.bat:安全停止服务
    • catalina.sh/catalina.bat:核心控制脚本,支持调试/运行参数(如 debugversion
    • configtest.sh/configtest.bat:配置文件语法检查工具
  • 环境配置
    • setenv.sh/setenv.bat:自定义 JVM 参数(如 CATALINA_OPTS="-Xms512m -Xmx1024m"

conf/ - 配置中枢

  • server.xml:主配置文件
    • 定义端口(<Connector port="8080">)、线程池、虚拟主机(<Host>
    • 修改需重启生效
  • web.xml:全局 Servlet 配置(默认 MIME 类型、会话超时)
  • context.xml:数据源(JDBC)、JNDI 资源定义
  • tomcat-users.xml:管理角色配置(如 manager-guiadmin-gui
  • logging.properties:日志级别(FINE/INFO)和输出格式控制

webapps/ - 应用仓库

  • 默认应用
    • ROOT/:根路径应用(http://localhost:8080
    • manager/:管理控制台(需权限)
    • examples/:官方示例(JSP/Servlet)
  • 部署方式
    • 直接放置 WAR 包(自动解压)
    • 创建应用目录(含 WEB-INF/classes

lib/ - 共享类库

  • 核心 JAR
    • servlet-api.jar:Servlet 规范实现
    • jsp-api.jar:JSP 编译支持
    • tomcat-jdbc.jar:数据库连接池
  • 扩展性:第三方 JAR 放入此目录可被所有应用共享

logs/ - 监控与诊断

  • 关键日志
    • catalina.out:标准输出(启动/运行时信息)
    • localhost_access_log.[date].txt:访问日志(格式:IP - - [时间] "请求" 状态码 响应大小
    • manager.[date].log:管理操作审计
  • 排查技巧
    • tail -f catalina.out 实时监控启动问题

work/ - 运行时缓存

  • JSP 编译
    • 存放 JSP 转换后的 Servlet 源文件和 .class 文件(路径示例:work/Catalina/localhost/ROOT/org/apache/jsp/index_jsp.class
  • 故障处理:修改 JSP 未生效时,清理此目录强制重新编译

temp/ - 临时文件

  • 存储上传文件、会话持久化数据等,Tomcat 自动管理,无需手动干预

核心配置文件解析

server.xml - 服务器全局配置

Tomcat的主配置文件,定义服务器架构和核心组件:

xml
<Server port="8005" shutdown="SHUTDOWN">
  <Service name="Catalina">
    <!-- HTTP连接器配置 -->
    <Connector 
      port="8080" 
      protocol="HTTP/1.1"
      maxThreads="200"         <!-- 最大工作线程数 -->
      minSpareThreads="10"     <!-- 最小空闲线程 -->
      acceptCount="100"        <!-- 等待队列长度 -->
      connectionTimeout="20000"
      redirectPort="8443" />
    
    <!-- AJP连接器(用于集成Apache) -->
    <Connector port="8009" protocol="AJP/1.3" />
    
    <Engine name="Catalina" defaultHost="localhost">
      <Host name="localhost" appBase="webapps"
            unpackWARs="true" autoDeploy="true">
        <!-- 上下文参数 -->
        <Context path="/myapp" docBase="myapp" reloadable="true" />
      </Host>
    </Engine>
  </Service>
</Server>

关键组件说明

  • <Connector>:定义请求处理协议(HTTP/AJP)及并发参数
  • <Executor>:线程池配置(需在<Connector>中通过executor属性引用)
  • <Host>:虚拟主机配置,支持多域名部署
  • <Context>:应用级配置(也可在独立context.xml中定义)

常用Connector参数

参数默认值作用
maxThreads200最大并发线程数
acceptCount100等待队列容量
compressionoff启用GZIP压缩
SSLEnabledfalse启用HTTPS加密

web.xml - 应用部署描述符

位于conf/(全局)或应用WEB-INF/(应用级),定义Servlet规范相关配置:

xml
<web-app>
  <!-- Servlet定义 -->
  <servlet>
    <servlet-name>MyServlet</servlet-name>
    <servlet-class>com.example.MyServlet</servlet-class>
    <load-on-startup>1</load-on-startup> <!-- 启动顺序 -->
  </servlet>
  
  <!-- URL映射 -->
  <servlet-mapping>
    <servlet-name>MyServlet</servlet-name>
    <url-pattern>/api/*</url-pattern>
  </servlet-mapping>
  
  <!-- 过滤器配置 -->
  <filter>
    <filter-name>EncodingFilter</filter-name>
    <filter-class>com.example.UTF8Filter</filter-class>
  </filter>
  <filter-mapping>
    <filter-name>EncodingFilter</filter-name>
    <url-pattern>/*</url-pattern>
  </filter-mapping>
  
  <!-- 会话超时(分钟) -->
  <session-config>
    <session-timeout>30</session-timeout>
  </session-config>
</web-app>

context.xml - 应用上下文配置

分三个作用域:

  1. 全局 (conf/context.xml):影响所有应用
  2. Host级 (conf/Catalina/localhost/context.xml):影响单虚拟主机
  3. 应用级 (webapps/myapp/META-INF/context.xml):仅影响当前应用

典型配置

xml
<Context>
  <!-- 数据源配置 -->
  <Resource 
    name="jdbc/TestDB" 
    type="javax.sql.DataSource"
    maxTotal="100"             <!-- 连接池最大连接数 -->
    maxIdle="30"               <!-- 最大空闲连接 -->
    username="dbuser"
    password="dbpass"
    driverClassName="com.mysql.jdbc.Driver"
    url="jdbc:mysql://localhost:3306/test" />
  
  <!-- 监控资源变更 -->
  <WatchedResource>WEB-INF/web.xml</WatchedResource>
</Context>

tomcat-users.xml - 权限管理

定义管理界面(如Manager App)的访问角色:

xml
<tomcat-users>
  <role rolename="manager-gui"/>     <!-- 控制台GUI权限 -->
  <role rolename="admin-gui"/>       <!-- 管理员GUI权限 -->
  <user username="admin" password="s3cret" roles="admin-gui,manager-gui"/>
</tomcat-users>

安全建议:生产环境限制manager-gui角色的IP访问。

Tomcat-优化

Gzip压缩

在Tomcat的server.xml文件中,找到对应http-nio-8080<Connector>标签,添加或修改以下参数以启用Gzip压缩

xml
<Connector port="8080" protocol="HTTP/1.1"
           connectionTimeout="20000"
           redirectPort="8443"
           compression="on"
           compressionMinSize="2048"
           compressableMimeType="text/html,text/xml,text/javascript,text/css,text/plain,application/json"
           noCompressionUserAgents="gozilla, traviata" />

参数说明

  • compression:可选值on(开启)、off(关闭)、force(强制压缩所有数据)。
  • compressionMinSize:默认2KB,过小的文件压缩可能适得其反。
  • compressableMimeType:需根据实际响应类型调整,例如动态内容如JSON需显式添加application/json
  • noCompressionUserAgents:不压缩的浏览器代理

静态资源缓存

web.xml中配置缓存大小,减轻磁盘I/O压力

xml
<Resources cachingAllowed="true" cacheMaxSize="102400" />

线程池优化

server.xml中独立配置<Executor>提升并发能力

xml
<Executor 
  name="tomcatThreadPool" 
  namePrefix="catalina-exec-"
  maxThreads="500" 
  minSpareThreads="50"
  maxQueueSize="100" />

<!-- 引用线程池 -->
<Connector executor="tomcatThreadPool" port="8080" />

核心参数

  • maxThreads:建议设为CPU核心数的2-4倍(IO密集型应用)。
  • minSpareThreads:保持最小空闲线程(如50)以减少创建开销。
  • acceptCount:队列长度建议为maxThreads的50%-100%

JVM调优参数

Tomcat最吃内存,只要内存足够,这只猫就跑的很快。如果系统资源有限,那就需要进行调优,提高资源使用率。

catalina.sh的路径为:/usr/local/tomcat/bin/catalina.sh,声明位置,不要放在后边

shell
JAVA_OPTS="-Djava.awt.headless=true -Dfile.encoding=UTF-8 -server -Xms1024m -Xmx1024m -XX:NewSize=512m -XX:MaxNewSize=512m -XX:PermSize=512m -XX:MaxPermSize=512m"

内存设置

  • -Xms-Xmx:设为相同值(如4G)避免动态扩展开销。
  • -XX:MetaspaceSize:调整元空间初始大小(如256m)

GC策略

  • 吞吐量优先:-XX:+UseParallelGC
  • 低延迟优先:-XX:+UseG1GC并设置-XX:MaxGCPauseMillis=200

JVM核心参数优化表

参数类型参数名作用说明推荐值注意事项
堆内存设置-Xms初始堆大小(JVM启动时分配)-Xmx相同,设为物理内存的50%-70%避免运行时动态扩容产生性能波动,例如-Xms4g -Xmx4g
-Xmx最大堆大小(JVM可扩展上限)
-Xmn新生代大小(Young Generation)占堆内存的1/3~1/4(如堆4G时设1G)过小易引发Minor GC频繁,过大会压缩老年代空间
垃圾回收策略-XX:+UseG1GC启用G1垃圾回收器(低延迟)JDK9+默认,堆>6G时首选配合-XX:MaxGCPauseMillis=200设置目标停顿时间
-XX:+UseConcMarkSweepGC启用CMS回收器(并发标记清除)JDK8及以下老年代低延迟方案需搭配-XX:CMSInitiatingOccupancyFraction=75设定触发阈值
-XX:+PrintGCDetails打印详细GC日志生产环境必开,配合-Xloggc:/path/gc.log用于诊断GC频率与停顿时间
永久代/元空间-XX:PermSize永久代初始大小(JDK7-)JDK8+已废弃JDK8+使用元空间替代,参数改为-XX:MetaspaceSize=256m
-XX:MaxPermSize永久代最大大小
-XX:MaxMetaspaceSize元空间最大大小(JDK8+)建议1GB~2GB不受堆内存限制,但需监控防止泄漏
线程与栈配置-Xss单个线程栈大小128k~1M(默认1M)过小导致栈溢出,过大限制总线程数(经验上限5000线程)
-XX:ParallelGCThreads并行GC线程数等于CPU核心数仅影响并行/并发回收器
高级调优参数-XX:SurvivorRatioEden区与Survivor区比例(如8表示Eden:S0:S1=8:1:1)默认8,可微调至6~10影响对象晋升老年代速度
-XX:NewRatio新生代与老年代比例(如2表示新生代:老年代=1:2)默认2,高临时对象场景可调至1-Xmn冲突时以-Xmn优先
-XX:+DisableExplicitGC禁用System.gc()手动触发生产环境建议启用防止外部调用引发Full GC
-XX:+HeapDumpOnOutOfMemoryErrorOOM时自动生成堆转储文件必开,配合-XX:HeapDumpPath=/path/用于事后分析内存泄漏

安全加固

  • 禁用自动部署<Host autoDeploy="false">
  • 关闭目录列表:在web.xml中设置<init-param><param-name>listings</param-name><param-value>false</param-value></init-param>
  • 启用HSTS:在server.xml<Connector>中添加hstsEnabled="true"
  • 删除示例应用:清理 webapps/examples/webapps/docs/减少攻击面
  • 修改关闭指令:避免默认 SHUTDOWN指令(server.xml中的 <Server port="8005" shutdown="NEW_PASSWORD">
  • 限制管理界面:在 tomcat-users.xml限制manager-gui角色的IP访问

日志管理

  • 定期轮转日志(如 Log4j 配置),避免 catalina.out过大占满磁盘

安装配置与部署

Oracle下载地址:https://www.oracle.com/cn/java/technologies/downloads/

安装JDK

bash
# 解压
tar xvf jdk-8u281-linux-x64.tar.gz -C /usr/local
chown root:root /usr/local/jdk1.8.0_281

# 设置环境变量
cat >> /etc/profile << "EOF"
export JAVA_HOME=/usr/local/jdk1.8.0_281
export JRE_HOME=${JAVA_HOME}/jre
export CLASSPATH=.:${JAVA_HOME}/lib:${JRE_HOME}/lib:$CLASSPATH
export JAVA_PATH=${JAVA_HOME}/bin:${JRE_HOME}/bin
export PATH=$PATH:${JAVA_PATH}
EOF

source /etc/profile

# 查看版本
java -version

安装 Tomcat

bash
# Tomcat下载:
https://dlcdn.apache.org/tomcat/tomcat-9/v9.0.108/bin/apache-tomcat-9.0.108.tar.gz

# 解压
tar xf apache-tomcat-9.0.108.tar.gz -C /usr/local/
mv /usr/local/apache-tomcat-9.0.108 /usr/local/tomcat
# 可选的操作
echo 'export TOMCAT_HOME=/usr/local/tomcat' >>/etc/profile
source /etc/profile

Tomcat 操作

bash
# 启动程序
/usr/local/tomcat/bin/startup.sh
# 关闭程序
/usr/local/tomcat/bin/shutdown.sh

Tomcat-管理war包

基础单实例

bash
# 上传war包到tomcat管理目录中,tomcat会自动解压memtest目录
/usr/local/tomcat/webapps/memtest.war
# 浏览器请求
http://192.168.148.101:8080/memtest/meminfo.jsp

Tomcat多实例

复制Tomcat目录

bash
# 比如8080单独的服务,8090单独的服务
cp -a /usr/local/tomcat /usr/local/tomcat_8080
cp -a /usr/local/tomcat /usr/local/tomcat_8090

修改服务配置文件

bash
vi /usr/local/tomcat_8090/conf/server.xml
# 修改tomcat服务端口
<Server port="8006" shutdown="SHUTDOWN">
# 对外提供服务的端口
<Connector port="8090" protocol="HTTP/1.1"
# 网站域名及网页根目录路径
<Host name="localhost" appBase="webapps"

启动多实例

bash
/usr/local/tomcat_8080/bin/startup.sh
/usr/local/tomcat_8090/bin/startup.sh

# 检测端口
ss -antup | grep java

Tomcat集群

nginx 负载均衡

nginx
upstream tomcats{
    ip_hash;
    server 192.168.148.101:8080;
    server 192.168.148.102:8080;
}
server {
    listen 8080;
    server_name localhost;

    location / {
	proxy_pass http://tomcats;
        # 核心头设置
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;

            # 连接优化
            proxy_http_version 1.1;
            proxy_set_header Connection "";
    }
}