最近关于Tomcat AJP协议漏洞的问题比较火爆,相信好多人都不太了解AJP是怎么一回事,在这里我也是在网上搜集了一些资料,在这里汇总一下
Tomcat最主要的功能是提供Servlet/JSP容器,尽管它也可以作为独立的Java Web服务器,它在对静态资源(如HTML文件或图像文件)的处理速度,以及提供的Web服务器管理功能方面都不如其他专业的HTTP服务器,如IIS和Apache服务器。
因此在实际应用中,常常把Tomcat与其他HTTP服务器集成。对于不支持Servlet/JSP的HTTP服务器,可以通过Tomcat服务器来运行Servlet/JSP组件。
当Tomcat与其他HTTP服务器集成时,Tomcat服务器的工作模式通常为进程外的Servlet容器,Tomcat服务器与其他HTTP服务器之间通过专门的插件来通信。关于Tomcat服务器的工作模式的概念可以参考本书1.4节。
本章首先讨论Tomcat与HTTP服务器集成的一般原理,然后介绍Tomcat与Apache以及IIS集成的详细步骤。
一、 Tomcat与HTTP服务器集成的原理
Tomcat服务器通过Connector连接器组件与客户程序建立连接,Connector组件负责接收客户的请求,以及把Tomcat服务器的响应结果发送给客户。默认情况下,Tomcat在server.xml中配置了两种连接器:
<!-- Define a non-SSL Coyote HTTP/1.1
Connector on port 8080 -->
<Connector port="8080"
maxThreads="150"
minSpareThreads="25"
maxSpareThreads="75"
enableLookups="false"
redirectPort="8443"
acceptCount="100"
debug="0"
connectionTimeout="20000"
disableUploadTimeout="true" />
<!-- Define a Coyote/JK2 AJP 1.3
Connector on port 8009 -->
<Connector port="8009"
enableLookups="false"
redirectPort="8443" debug="0"
protocol="AJP/1.3" />
第一个连接器监听8080端口,负责建立HTTP连接。在通过浏览器访问Tomcat服务器的Web应用时,使用的就是这个连接器。
第二个连接器监听8009端口,负责和其他的HTTP服务器建立连接。在把Tomcat与其他HTTP服务器集成时,就需要用到这个连接器。
Web客户访问Tomcat服务器上JSP组件的两种方式如图所示。
图22-1 Web客户访问Tomcat服务器上的JSP组件的两种方式
在图22-1中,Web客户1直接访问Tomcat服务器上的JSP组件,他访问的URL为http://localhost:8080/index.jsp。Web客户2通过HTTP服务器访问Tomcat服务器上的JSP组件。假定HTTP服务器使用的HTTP端口为默认的80端口,那么Web客户2访问的URL为http://localhost:80/index.jsp 或者 http://localhost/index.jsp。
下面,介绍Tomcat与HTTP服务器之间是如何通信的。
二、JK插件
Tomcat提供了专门的JK插件来负责Tomcat和HTTP服务器的通信。应该把JK插件安置在对方的HTTP服务器上。当HTTP服务器接收到客户请求时,它会通过JK插件来过滤URL,JK插件根据预先配置好的URL映射信息,决定是否要把客户请求转发给Tomcat服务器处理。
假定在预先配置好的URL映射信息中,所有"/*.jsp"形式的URL都由Tomcat服务器来处理,那么在图22-1的例子中,JK插件将把客户请求转发给Tomcat服务器,Tomcat服务器于是运行index.jsp,然后把响应结果传给HTTP服务器,HTTP服务器再把响应结果传给Web客户2。
对于不同的HTTP服务器,Tomcat提供了不同的JK插件的实现模块。本章将用到以下JK插件:
与Windows下的Apache HTTP服务器集成:mod_jk_2.0.46.dll
与Linux(RedHet)下的Apache HTTP服务器集成:mod_jk.so-ap2.0.46-rh72..46-rh72
与IIS服务器集成:isapi_redirect.dll
总结理解(重要)
关于这个协议,一直不太明白,网上的博客讲的也都是千篇一律。 都说ajp协议是tomcat为了动静资源处理分离时,通过该协议可以将css、js等静态资源请求转发到Apache的http服务器处理,提高并发量。但是在优化tomcat时,没有用到Apache服务器,则需要将其禁用。 那么问题来了,如果前端用的是Nginx(配置的端口是80)直接转发到tomcat8080端口,并没有通过ajp协议的8009端口吧,那么禁用掉这个配置为何能提高tomcat性能呢?
ajp13是一个二进制的TCP传输协议,相比HTTP这种纯文本的协议来说,效率和性能更高,也做了很多优化。显然,浏览器并不能直接支持AJP13协议,只支持HTTP协议。所以实际情况是,通过Apache的proxy_ajp模块进行反向代理,暴露成http协议给客户端访问。所以这么来看实际跟动静分离没一毛钱关系,你如果没做动静分离的设置,那么单纯反向代理AJP13协议也没太大的意义。
其他支持AJP协议的代理服务器当然也可以用这种做法。但是实际情况是,支持AJP代理的服务器非常少,比如目前很火爆的Nginx就没这个模块。因此tomcat的配置大部分都是关闭AJP协议端口的,因为除了Apache之外别的http server几乎都不能反代AJP13协议,自然就没太大用处了。
原文参考: