一、基础组件
1.1 组件介绍
顶级组件:位于整个配置的顶层; Server:表示一个Tomcat实例 (单例的);Server代表整个catalina servlet容器;包含一个或多个service子容器。主要是用来管理容器下各个Serivce组件的生命周期。 Service:代表Tomcat中一组提供服务、处理请求的组件。是一个分组结构,包括多个Connector和一个Container。
容器类:可以包含其它组件的组件; Container是容器的父接口,用于封装和管理Servlet,以及具体处理Request请求,该容器的设计用的是典型的责任链的设计模式,它由四个自容器组件构成,分别是Engine、Host、Context、Wrapper。这四个组件是负责关系,存在包含关系。只包含一个引擎。 Engine 引擎:表示可运行的Catalina的servlet引擎实例,并且包含了servlet容器的核心功能。在一个服务中只能有一个引擎。同时,作为一个真正的容器,Engine元素之下可以包含一个或多个虚拟主机。它主要功能是将传入请求委托给适当的虚拟主机处理。如果根据名称没有找到可处理的虚拟主机,那么将根据默认的Host来判断该由哪个虚拟主机处理。 Host 虚拟主机:作用就是运行多个应用,它负责安装和展开这些应用,并且标识这个应用以便能够区分它们。它的子容器通常是 Context。一个虚拟主机下都可以部署一个或者多个Web App,每个Web App对应于一个Context,当Host获得一个请求时,将把该请求匹配到某个Context上,然后把该请求交给该Context来处理。主机组件类似于Apache中的虚拟主机,但在Tomcat中只支持基于FQDN(完全合格的主机名)的“虚拟主机”。Host主要用来解析web.xml。 Context上下文:代表 Servlet 的 Context,它具备了 Servlet 运行的基本环境,它表示Web应用程序本身。Context 最重要的功能就是管理它里面的 Servlet 实例,一个Context对应于一个Web Application,一个Web Application由一个或者多个Servlet实例组成。 Wrapper包装器: 代表一个 Servlet,它负责管理一个 Servlet,包括的 Servlet 的装载、初始化、执行以及资源回收。Wrapper 是最底层的容器,它没有子容器了,所以调用它的 addChild 将会报错。
连接器组件:连接用户请求至 tomcat; Connector是客户端连接到Tomcat容器的服务点,它为引擎提供协议服务来将引擎与客户端各种协议隔离开来,如HTTP、HTTPS、AJP协议。Connector的基本属性都是它所需要监听的IP地址及端口号,以及所支持的协议。还有一个关键属性就是并发处理传入请求的最大线程数。注意,Connector关键的有 连接器(HTTP HTTPS HTTP1.1 AJP SSL proxy) 运行模式(BIO NIO NIO2/AIO APR)多线程/线程池。
被嵌套类的组件:位于一个容器当中,不能包含其它组件; Valve阀门:类似于Servlet规范中定义的过滤器,用来拦截请求并在将其转至目标之前进行某种处理操作。Valve可以定义在任何容器类的组件中。Valve常被用来记录客户端请求、客户端IP地址和服务器等信息,这种处理技术通常被称作请求转储(request dumping)。请求转储valve记录请求客户端请求数据包中的HTTP首部信息和cookie信息文件中,响应转储valve则记录响应数据包首部信息和cookie信息至文件中。 Logger日志记录器:用于记录组件内部的状态信息,可被用于除Context之外的任何容器中。日志记录的功能可被继承,因此,一个引擎级别的Logger将会记录引擎内部所有组件相关的信息,除非某内部组件定义了自己的Logger组件。 Loader类加载器:负责加载、解释Java类编译后的字节码。 Realm领域:用于用户的认证和授权;在配置一个应用程序时,管理员可以为每个资源或资源组定义角色及权限,而这些访问控制功能的生效需要通过Realm来实现。Realm的认证可以基于文本文件、数据库表、LDAP服务等来实现。Realm的效用会遍及整个引擎或顶级容器,因此,一个容器内的所有应用程序将共享用户资源。同时,Realm可以被其所在组件的子组件继承,也可以被子组件中定义的Realm所覆盖。 Excutor执行器:执行器组件允许您配置一个共享的线程池,以供您的连接器使用。从tomcat 6.0.11版本开始。 Listener监听器:监听已注册组件的生命周期。 Manager会话管理器:用于实现http会话管理的功能,tomcat6种有5种会话管理的manager的实现(standardManager、persisentManager、DeltaManager、BackupManager、SimpleTcpReplicationManager)。会话让使用无状态HTTP协议的应用程序完成通信。会话表示客户端和服务器之间的通信,会话功能是由javax.servlet.http.HttpSession 的实例实现的,该实例存储在服务器上而且与一个唯一的标识符相关联,客户端在与服务器的每次交互中根据请求中的标识符找到它的会话。一个新的会话在客户端请求后被创建,会话一直有效直到一段时间后客户端连接超时,或者会话直接失效例如客户退出访问服务器。 Cluster集群:专用于配置Tomcat集群的元素,可用于Engine和Host容器中。 
1.2 tomcat 配置文件及组件
vim /apps/tomcat/conf/server.xml
<server> #顶级服务器组件,一个 server 表示 tomcat 运行实例。
<service> #这是一种抽象的服务,它把连接器 connector 和处理引擎 engine 结合在一起提供运行和访问。
<connector> #连接器组件,定义如何接收和响应外部请求,8080/8443/8009
<engine> #引擎是核心组件,也是最高级别的容器组件,所有的请求都是通 过处理引擎处理的,引擎提供 jsp 编译、通过 connetctor 接收用户请求,分析用户请 求首部的具体虚拟主机,并将请求转发至虚拟主机。
<Realm> #用于配置安全管理角色,通常读取 tomcat-uesrs.xml 进行验证。
</Realm>
<host> #虚拟主机,用于进行请求的映射处理
<context> #定义上下文配置,用于 web 应用配置,通常配置 session 共享配置
</context>
<Valve pattern="%h %l %u %t "%r" %s %b"/> #单词 Valve 的意思是”阀门”,在 Tomcat 中代表了请求处理流水线上的一个组件,Valve 可 以与 Tomcat 的容器(Engine、Host 或 Context)关联。
</host>
</engine>
</connector>
</service>
</server>
#Context 非必须配置项,因此默认没有添加,具体生产实例如下:
<Context docBase="/apps/tomcat/webapps/SalesManager" sessionCookieDomain=".ceboss.cn" sessionCookiePath="/" path="" reloadable="false" />
<?xml version="1.0" encoding="UTF-8"?>
<Server port="8005" shutdown="SHUTDOWN">
<Listener className="org.apache.catalina.startup.VersionLoggerListener" />
<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" />
<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>
<Service name="Catalina">
<Connector port="8080" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
<Engine name="Catalina" defaultHost="localhost">
<Realm className="org.apache.catalina.realm.LockOutRealm">
<Realm className="org.apache.catalina.realm.UserDatabaseRealm"
resourceName="UserDatabase"/>
</Realm>
resourceName="UserDatabase"/>
</Realm>
<Host name="localhost" appBase="webapps"
unpackWARs="true" autoDeploy="true">
<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs"
prefix="localhost_access_log" suffix=".txt"
pattern="%h %l %u %t "%r" %s %b" />
</Host>
</Engine>
</Service>
</Server>
1.3 访问流程
1.用户在浏览器中输入网址 172.31.7.121:8080/mysite/index.jsp,请求被发送到本 机端口 8080,并有 HTTP/1.1 Connector 接收请求。 2.Connector 把该请求交给其所在 tomcat 中 Service 的 Engine(Container)来继续处 理请求,并等待 Engine 的回复。 3.Engine 获得请求 172.31.7.121:8080/mysite/index.jsp,匹配所有的虚拟主机 Host; 4.Engine 匹配名为 172.31.7.121 的 Host,如果匹配不到就把请求交给 localhost 处 理,因为 localhost 被定义为该 Engine 的默认主机,名为 localhost 的 Host 获得请 求/mysite/index.jsp,匹配它所拥有的所有 Context。 5.path=“/mysite”的 Context 获得请求/index.jsp,在它的 mapping table 中寻找 出对应的 Servlet,Context 匹配到 URL Pattern 为*.jsp 的 Servlet,对应于 JspServlet 类。 6.构造 HttpServletRequest 对象和 HttpServletResponse 对象,作为参数调用 JspServlet 的 doGet()或 doPost(),执行业务逻辑、数据存储等; 7.Context 把执行完之后的 HttpServletResponse 对象返回给 Host。 8.Host 把 HttpServletResponse 对象返回给 Engine。 9.Engine 把 HttpServletResponse 对象返回 Connector。 10.Connector 把 HttpServletResponse 对象返回给客户端源端口并最终在客户端浏 览器渲染页面。 
1.4 配置示 webapp 例
将 webapp 通过手动拷贝、编写脚本、部署工具分发到各 tomcat 的指定目录,然后启动 tomcat,启动成功后 tomcat 即可处理来自于客户端的请求。 在 k8s 环境是基于更新镜像。
mkdir /apps/tomcat/webapps/mysite -p
echo "<h1> lck mysite web page </h1>" > /apps/tomcat/webapps/mysite/index.jsp
chown tomcat.tomcat /apps/tomcat/ -R
systemctl restart tomcat

1.5 企业 webapp 结构
webapp 体系机构: webapp 有特定得到组织结构,是一种层次型目录结构,通常包含了 servlet 代 码文件、jsp 页面文件、类文件、部署描述符文件等,一般会打包成归档格式。
/web 应用程序的目录: WEB-INF:是 webapp 的私有资源目录,此目录里面的文件是不允许通过浏览器访问的,通常 web.xml 和tontext.xml 均放置于此目录。 WEB-INF/classes:此 webapp 自己提供的类,即不是 tomcat 自身提供的类 WEB-INF/lib:此 webapp 自有的能够被打包为 jar 格式的类
二、Manager App 使用
tomcat manager 是 Tomcat 自带的、使用 HTML 界面的、管理 Tomcat 自身以及部署在 tomcat 上的应用的一个 web 应用,它支持的功能包括:
通过 war 包部署新应用。
在服务器上指定的路径部署新应用。
列出当前部署的 Web 应用程序,以及当前这些 Web 应用程序处于活动状态的会话信息。
重新加载现有 Web 应用程序。
列出操作系统和 JVM 属性。
列出可用的全局 JNDI 资源。
启动已停止的应用程序。
停止现有应用程序。
取消部署已部署的 Web 应用程序并删除其所在目录文件。

2.1 manager app 角色介绍
Manager app 功能默认没有开启,需要单独在配置文件中开启并重启 tomcat 服务,支持的角色如下
manager-gui-访问 HTML 界面。
manager-status-仅访问“服务器状态”页面。
manager-script —访问本文档中描述的工具友好的纯文本界面以及“服务器状 态”页面。
manager-jmx-访问 JMX 代理界面和“服务器状态”页面。
manager(已弃用)—结合了以上四个角色,允许在允许上述角色之一的任何地 方访问。不要使用它。使用以上特定的管理员 角色之一或它们的组合。
注意事项:如果不开启角色认证则无法进行配置管理 
2.2 manager app 账号授权
支持的账户认证方式
1.JDBCRealm 用户授权信息存储于某个关系型数据库中,通过 JDBC 驱动获取信息 验证。
2.DataSourceRealm 用户授权信息存储于关于型数据中,通过 JNDI 配置 JDBC 数据 源的方式获取信息验证。
3.JNDIRealm 用户授权信息存储在基于 LDAP 的目录服务的服务器中,通过 JNDI 驱动获取并验证。
4.UserDatabaseRealm 默 认 的 配 置 方 式 , 信 息 存 储 于 XML 文 档 中 conf/tomcat-users.xml。
5.MemoryRealm 用户信息存储于内存的集合中,对象集合的数据来源于 xml 文档 conf/tomcat-users.xml。
6.JAASRealm 通过(JAAS,Java Authentication and Authorization Service,Java 验证和 授权 API)框架访问授权信息。
UserDatabaseRealm 认证实现
vim /apps/tomcat/conf/server.xml
<GlobalNamingResources>
<!-- Editable user database that can also be used by
UserDatabaseRealm to authenticate users
-->
<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>
<Realm className="org.apache.catalina.realm.UserDatabaseRealm" resourceName="UserDatabase"/>
vim /apps/tomcat/conf/tomcat-users.xml
-->
<role rolename="mamager-gui"/>
<user username="magedu" password="magedu123" roles="manager-gui"/>
</tomcat-users>
2.3 定义 IP 访问控制
默认情况下,tomcat 读取 context.xml 文件,但是 context.xml 默认仅允许本机 127.0.0.1 访问, 因此需要授权访问地址
vim /apps/tomcat/webapps/manager/META-INF/context.xml
allow="127\.\d+\.\d+\.\d+|::1|0:0:0:0:0:0:0:1"
allow="\d+\.\d+\.\d+.\d+|127\.\d+\.\d+\.\d+|::1|0:0:0:0:0:0:0:1" />
注意事项:修改完以上两步重启 tomcat,如果只修改了 context.xml 不需要重启可以直接生效。
systemctl restart tomcat
2.4 登录 manager app 界面

登录后的界面  应用程序管理功能 
2.5 基于 manager app 部署 webapp
通过 manager app 管理界面部署 webapp,即不需要修改配置文件,有如下两种实现方式: 第一种是填写服务器上已经存在的目录和 index 文件,第二中是基于构建好的 war 包部署。 
部署方式一:通过目录部署
由于webapp通常以目录的形式存在,因此在宿主机创建目录并生成web页面进行部署演示。
mkdir /data/tomcat/site2 -p
chown tomcat.tomcat /data/tomcat/ /apps/ -R
echo "<h1>lck site2 web page</h1>" > /data/tomcat/site2/index.jsp
 部署成功后,会有如下信息,并且会将代码自动 copy 到 tomcat 定义好 appBase 目录并可以 直接访问  注意事项: 可以通过 manager app 卸载此 webapp,卸载后立即将 appBase 目录中的 site3 目录删除, 但是重启tomcat 不会删除 site2 目录。
部署方式二:通过自定义 war 包部署
war 包通常由开发构建好再交给运维部署
mkdir site3
echo "<h1>lck site3 web page</h1>" > /root/site3/index.jsp
zip site3.war index.jsp
 部署成功  访问 web 
[root@centos7 ~]
total 8
drwxr-x--- 15 tomcat tomcat 4096 Aug 2 23:15 docs
drwxr-x--- 7 tomcat tomcat 99 Aug 2 23:15 examples
drwxr-x--- 6 tomcat tomcat 79 Aug 2 23:15 host-manager
drwxr-x--- 6 tomcat tomcat 114 Aug 2 23:15 manager
drwxr-xr-x 2 tomcat tomcat 23 Aug 3 23:52 mysite
drwxr-x--- 3 tomcat tomcat 223 Aug 2 23:15 ROOT
drwxr-x--- 2 tomcat tomcat 23 Aug 4 02:02 site2
drwxr-x--- 3 tomcat tomcat 39 Aug 4 02:17 site3
-rw-r----- 1 tomcat tomcat 181 Aug 4 02:17 site3.war
2.6 手动部署开源项目 jenkins war 包部署
https://www.jenkins.io/zh/download/ https://mirrors.tuna.tsinghua.edu.cn/jenkins/
ll /apps/tomcat/webapps/jenkins.war

定义 IP 访问控制
vim /apps/tomcat/webapps/host-manager/META-INF/context.xml
allow="127\.\d+\.\d+\.\d+|::1|0:0:0:0:0:0:0:1" />
allow="\d+\.\d+\.\d+.\d+|127\.\d+\.\d+\.\d+|::1|0:0:0:0:0:0:0:1" />
host-manager 账户授权
使用和 manager app 相同的授权文件,即/apps/tomcat/conf/tomcat-users.xml,但是需要配置 admin-gui 的权限
vim /apps/tomcat/conf/tomcat-users.xml
-->
<role rolename="mamager-gui"/>
<role rolename="admin-gui"/>
<user username="magedu" password="magedu123" roles="manager-gui,admin-gui"/>
</tomcat-users>
修改完以上两步重启 tomcat,如果只修改了 context.xml 不需要重启可以直接生效
systemctl restart tomcat
登录 host-manager 界面
 登录界面  权限错误的界面  登录成功的界面  列出虚拟机 
三、Host Manager 使用
3.1 host manager 账户授权
vim /apps/tomcat/conf/tomcat-users.xml
-->
<role rolename="mamager-gui"/>
<role rolename="admin-gui"/>
<user username="lck" password="lck123" roles="manager-gui,admin-gui"/>
</tomcat-users>
systemctl restart tomcat
3.2 定义 IP 访问控制
vim /apps/tomcat/webapps/host-manager/META-INF/context.xml
allow="\d+\.\d+\.\d+.\d+|127\.\d+\.\d+\.\d+|::1|0:0:0:0:0:0:0:1" />
systemctl restart tomcat
3.3 登录 host-manager 界面
  登陆成功的界面  列出所有的虚拟机 
四、Tomcat Host 高级应用
4.1 单站点
配置文件
vim /apps/tomcat/conf/server.xml
<Host name="localhost" appBase="/data/tomcat/webapps"
unpackWARs="true" autoDeploy="true"
xmlValidation="false" xmlNamespaceAware="false">
</Host>
一般以下两个功能不选择开启,把true改为fail
unpackWARs="true"
jar autoDeploy="true"
echo "<h1>magedu mysite1 web page" > /data/tomcat/webapps/mysite1/index.jsp
访问 URL:10.0.0.14:8080/mysite1/index.jsp
4.2 多站点
vim /apps/tomcat/conf/server.xml
<Host name="www.site1.net" appBase="/data/tomcat"
unpackWARs="true" autoDeploy="true">
<Context path="" docBase="site1" reloadable="true" />
<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs" prefix="site1_access" suffix=".log" pattern="%h %l %u %t "%r" %s %b" />
</Host>
<Host name="www.site2.net" appBase="/data/tomcat"
unpackWAPs="true" autoDeploy="true">
<Context path="" docBase="site2" reloadable="true" />
<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs" prefix="site2_access." suffix=".log" pattern="%h %l %u %t "%r" %s %b" />
</Host>
echo "site1" > /data/tomcat/site1/index.jsp
echo "site2" > /data/tomcat/site2/index.jsp
访问 URL: www.site1.net:8080/site1/index.jsp www.site2.net:8080/site2/index.jsp
|