Catalina 架构
Tomcat 是一个由一系列可配置的组件构成的 Web 容器,而 Catalina 可以看做是一个 Tomcat 实例
Tomcat 由以下几个部分组成 :
在源码上也可证明这一点 :
Tomcat 本质上就是一款 Servlet 容器, 因此 Catalina 才是 Tomcat 的核心 , 其他模块都是为 Catalina 提供支撑的。 比如 : 通过 Coyote 模块提供链接通信,Jasper 模块提供JSP 引擎,Naming 提供 JNDI 服务,Juli 提供日志服务
Catalina 结构
可以将 Catalina 看作为 Server,而 Server 表示着整个服务器。Server 管理多个 Service,每个 Service 都包含着多个连接器组件 Connector(Coyote 实现)和一个容器组件 Container。在 Tomcat 启动的时候,会初始化一个 Catalina 的实例
组件 | 作用 |
---|---|
Catalina | 负责解析 Tomcat 的配置文件 , 以此来创建服务器 Server |
Server | Catalina 服务器表示整个 Server , 用于管理 Servlet 容器以及其它组件 |
Service | 它将若干个 Connector 组件绑定到一个 Container(Engine)上 |
Connector | 连接器,处理与客户端的通信,它负责接收客户请求,然后转给相关的 Container 处理,最后向客户返回响应结果 |
Container | 容器,负责处理用户的 servlet 请求,并返回对象给 web 用户的模块 |
Container 其实就是 Engine, 表示整个 Catalina 的 Servlet 引擎
组件 | 描述 |
---|---|
Engine | 用来管理多个虚拟站点,一个 Service 最多只能有一个 Engine,但是可包含多个 Host |
Host | 虚拟主机,或者说一个站点,需要绑定域名 (通过域名确定主机),一个 Host 下可包含多个 Context |
Context | 表示一个 Web 应用程序, 一个Context 可包含多个 Wrapper |
Wrapper | 包装了一个 Servlet |
查看他们的类结构 :
其中 Lifecycle 接口定义了三个方法 :init
, start
, stop
, destroy
所以各个组件的生命周期都需要经历三个过程: 初始化, 启动, 停止, 销毁
查看 Tomcat 的 conf 目录下的 web.xml 配置文件, 就会发现, 每个标签中的子元素和上图吻合
类加载器架构
Tomcat 6 版本之前, 可以设置三组目录 : /common
, /server
, /shared
. 默认不一定是开放的, 可能只有 /lib
目录存在, 在加上 Web 应用程序自身的到 /WEB-INF/*
目录, 一共四组, 他们的含义分别是 :
- /common : 类库可被 Tomcat 和所有的 Web 应用程序共同使用
- /server : 类库可被 Tomcat 使用,对所有的 Web 应用程序都不可见
- /shared : 类库可被所有的 Web 应用程序共同使用,但对 Tomcat 自己不可见
- /webapp/WEB-INF : 类库仅仅可以被该 Web 应用程序使用,对 Tomcat 和其他 Web 应用程序都不可见
为了支持这套目录结构,并对目录里面的类库进行加载和隔离,Tomcat 自定义了多个类加载器,这些类加载器按照经典的双亲委派模型来实现,其关系下图所示 :
它们分别加载 /common
, /server
, /shared
和 /webapp/WEB-INF
下的 Java 类库, Jsp 类加载器对应一个 Jsp 文件 (当检测到 Jsp 文件被修改时, 直接替换目前的 JSP 类加载器的实例, 以实现 热部署
) , 所以,WebApp 类加载器和 JSP 类加载器通常会存在多个实例
Tomcat 6 之后, 将 /common
, /server
, /shared
默认合并到一个 /lib
目录, 这个目录的 Java 类库当前与以前的 /common
目录中 Java 类库中的作用
如果默认配置无法满足需求, 可以在 /conf/catalina.properties
配置文件中指定 server.loader
和 shared.loader
的方式 (会分别创建 Catalina 类加载器实例和 Shared 类加载器实例) 启动原来完整的加载器架构