[刘阳Java]_Spring中IntrospectorCleanupListener的用途【补充】_第16讲
这篇文章不是我自己原创的,但是为了后期的阅读,所以我收录网上的一篇文章。为了尊重作者的版权,转载地址先放上来,大家也可以去访问他的原始文章。http://jadyer.cn/2013/09/24/spring-introspector-cleanup-listener/
1. 简介
JDK中的 java.beans.Introspector 的用途是:发现 Java 类是否符合 JavaBean 规范。如果有的框架或程序用到了 Introspector,那么就会启用一个系统级的缓存,里面存放一些曾加载并分析过的 JavaBean 引用。当服务器关闭时,由于缓存中存放着这些 JavaBean 引用,故垃圾回收器无法回收 Web 容器中的 JavaBean 对象,使得内存变大。而 org.springframework.web.util.IntrospectorCleanupListener 就是专门用来处理 Introspector 内存泄漏问题的辅助类,IntrospectorCleanupListener 会在 Web 服务器停止时清理 Introspector 缓存,使那些 Javabean 能被垃圾回收器正确回收。当然 Spring 自身不会出现这种问题:因为 Spring 在加载并分析完一个类之后会马上刷新 JavaBeans Introspector 缓存,但有些程序和框架在使用了 JavaBeans Introspector 之后,没有进行清理工作(比如Quartz、Struts),最后导致内存泄漏
2. 总结
- 此监听器可以解决 java.beans.Introspector 导致内存泄漏的问题
- 它应该配置在 web.xml 中与 Spring 相关监听器中的第一个位置(也要在ContextLoaderListener的前面)
3. 大家可以参考一下下面的web.xml配置
<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" version="2.5"> <!-- Web容器加载顺序ServletContext==>context-param==>listener==>filter==>servlet --> <!-- 使用ContextLoaderListener时需要告诉它Spring配置文件的位置,它默认会去找/WEB-INF/applicationContext.xml 不过可以设置contextConfigLocation参数,来为上下文载入器指定一个或多个Spring配置文件 注意:contextConfigLocation参数是一个用逗号分隔的路径列表,其路径是相对于Web系统的根路径的 --> <context-param> <param-name>contextConfigLocation</param-name> <param-value>/WEB-INF/jadyer-servlet.xml, classpath:applicationContext-*.xml</param-value> </context-param> <!-- 防止发生java.beans.Introspector内存泄露,应将它配置在ContextLoaderListener的前面 --> <listener> <listener-class>org.springframework.web.util.IntrospectorCleanupListener</listener-class> </listener> <!-- 配置上下文载入器,载入除DispatcherServlet载入的配置文件之外的其它上下文配置文件 最常用的上下文载入器是一个Servlet监听器,其名称为ContextLoaderListener --> <listener> <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class> </listener> <!-- SpringMVC的前端控制器 当DispatcherServlet载入后,它将从一个XML文件中载入Spring的应用上下文,该XML文件的名字取决于<servlet-name> 这里DispatcherServlet将试图从一个叫做springmvc-servlet.xml的文件中载入应用上下文,其默认位于WEB-INF目录下 不过也可以让它去找别的配置文件,修改方法为:配置局部的<init-param>参数 --> <servlet> <servlet-name>jadyer</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <!-- <init-param> <param-name>contextConfigLocation</param-name> <param-value>classpath:applicationContext.xml</param-value> </init-param> --> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>jadyer</servlet-name> <url-pattern>/</url-pattern> </servlet-mapping> <filter> <filter-name>CharacterEncodingFilter</filter-name> <filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class> <init-param> <param-name>encoding</param-name> <param-value>UTF-8</param-value> </init-param> <init-param> <param-name>forceEncoding</param-name> <param-value>true</param-value> </init-param> </filter> <filter-mapping> <filter-name>CharacterEncodingFilter</filter-name> <url-pattern>/*</url-pattern> </filter-mapping> </web-app>