JBoss 中的ear 包中类加载顺序控制

最近几天研究Dozer的性能,需要改写Dozer 中的几个类但是又不打算重新编译Dozer的jar 包了, 所以偷懒在genidc-biz-service 工程的src 目录下创建在dozer jar 中相同名称的类包, 图中的"org.dozer", "org.dozer.cache", "org.dozer.converters", 拷贝dozer 源代码中的相关类过来, 然后在这里动手改。

发布的时候, 发现奇怪了, 程序还是在跑Dozer jar 包中的老代码, 我所新添加的代码都没跑到。 以前玩Tomcat的时候, 开源Jar 包下的类就这么干的, 工作好好的。 tomcat  的类文件优先加载级别是

Therefore, from the perspective of a web application, class or resource loading looks in the following repositories, in this order:

    Bootstrap classes of your JVM
    System class loader classes (described above)
    /WEB-INF/classes of your web application
    /WEB-INF/lib/*.jar of your web application
    Common class loader classes (described above)
 

所以web 工程编译出来的class 文件是比lib 包下的jar 文件中的class 文件优先加载的。  

恩,看来Jboss 下的类文件加载不是这么玩的。 咨询谷歌大神, 他告诉我需要以下步骤

1. 修改ear 下的jboss-application.xml, 做如下设置, 它的作用是告诉类加载器强制按照ear 包下的application.xml 中指定的jar 包顺序做加载。

<jboss-app>
  <module-order>strict</module-order>
</jboss-app> 
 

查看了我们的genidc-ear 工程, target 打出来的jboss-application.xml 已经是这样了,

2. 然后在application.xml 中设置加载顺序

<application xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/application_1_4.xsd" version="1.4">
  <display-name>genidc-ear</display-name>
  <module>
    <java>lib/genidc-common-service-3.1.jar</java>
  </module>
  <module>
    <java>lib/genidc-common-presentation-3.1.jar</java>
  </module>
  <module>
    <java>lib/genidc-biz-manager-3.1.jar</java>
  </module>
  <module>
    <java>lib/genidc-biz-model-3.1.jar</java>
  </module>
  <module>
    <java>lib/genidc-biz-service-3.1.jar</java>
  </module>
  <module>
    <java>lib/dozer-5.2.0.jar</java>
  </module>
  <module>
    <ejb>genidc-ejb3-3.1.jar</ejb>
  </module>
</application> 

这里,没有在这里指定的ear 中的其他jar 包, 默认的加载顺序是和这里的jar 包一起按照字母顺序加载, 如果不特别指定dozer加载顺序, 那么因为dozer jar 比genidc-biz-service-3.1.jar 字母序靠前, 所以dozer 中的MappingProcessor.class会先加载, 然后等到加载genidc-biz-service-3.1.jar 中的MappingProcessor.class, 类装载器认为已经加载过, 就跳过了加载。  所以这里只要强行指定这个dozer-5.2.0.jar  比genidc-biz-service-3.1.jar后加载就OK了。   把这个修改了的ear 包放Jboss里,跑起来对了。

3. 且慢, 光这样改还不行, 重新run 下maven, application.xml 又变回去了, 那么这些配置文件的生成肯定和Maven的脚本有关。查看genidc-ear 工程下的pom 有个maven-ear plugin 的配置, 原来, application.xml 中的jar 以及顺序都是它指定, 还有jboss-application.xml 中的module-order 也是这里指定的。 在这里加上dozer 的配置, OK, maven build 出来的application.xml 就是我们想要的了。

 <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-ear-plugin</artifactId>
                <version>2.3.1</version>
                <configuration>
                    <displayName></displayName>
                    <description></description>
                    <version>1.4</version>
                    <defaultLibBundleDir>lib</defaultLibBundleDir>
                    <modules>
                        <jarModule>
                            <groupId>oasis.genidc</groupId>
                            <artifactId>genidc-utility</artifactId>
                            <includeInApplicationXml>false</includeInApplicationXml>
                        </jarModule>
                        <jarModule>
                            <groupId>oasis.genidc</groupId>
                            <artifactId>genidc-common-service</artifactId>
                            <includeInApplicationXml>true</includeInApplicationXml>
                        </jarModule>
                        <jarModule>
                            <groupId>oasis.genidc</groupId>
                            <artifactId>genidc-common-presentation</artifactId>
                            <includeInApplicationXml>true</includeInApplicationXml>
                        </jarModule>
                        <jarModule>
                            <groupId>oasis.genidc</groupId>
                            <artifactId>genidc-biz-manager</artifactId>
                            <includeInApplicationXml>true</includeInApplicationXml>
                        </jarModule>
                        <jarModule>
                            <groupId>oasis.genidc</groupId>
                            <artifactId>genidc-biz-model</artifactId>
                            <includeInApplicationXml>true</includeInApplicationXml>
                        </jarModule>
                        <jarModule>
                            <groupId>oasis.genidc</groupId>
                            <artifactId>genidc-biz-service</artifactId>
                            <includeInApplicationXml>true</includeInApplicationXml>
                        </jarModule>                  
                        <jarModule>
                            <groupId>net.sf.dozer</groupId>
                            <artifactId>dozer</artifactId>
                            <includeInApplicationXml>true</includeInApplicationXml>
                        </jarModule>
                        <ejbModule>
                            <groupId>oasis.genidc</groupId>
                            <artifactId>genidc-ejb3</artifactId>
                        </ejbModule>
                    </modules>
                        <jboss>
                            <version>4.2</version>
                            <module-order>strict</module-order>                       
                        </jboss>
                </configuration>
            </plugin> 

猜你喜欢

转载自wangbt5191-hotmail-com.iteye.com/blog/1614663