我正在处理一个由许多WAR文件组成的多模块项目。这些项目使用Spring 4.0.5来管理依赖关系,并使用带有加载时编织的AspectJ 1.8.5来支持AOP(Spring基本的AOP支持在这个项目中不够)。此外,META-INF目录中有一个aop.xml,配置非常简单:
<aspectj>
<aspects>
<!--No need to specify any aspect here-->
</aspects>
<weaver options="-XnoInline -verbose">
<include within="com.myproject..*" />
</weaver>
</aspectj>
AOP主要用于为各种服务和DAO(用@Service和@Repository注释)提供事务行为(用spring的@Transactional注释)。例如:
@Service(value = "alertService")
public class AlertServiceImpl implements IAlertService, Serializable {
...
@Transactional(rollbackFor = Exception.class)
@Override
public Alert createAlert(Alert alert) {
alertDAO.create(alert);
return alert;
}
...
}
或者一个抽象的Base DAO,应用程序的其余DAO从中继承
@Repository
public abstract class BaseDAO<E extends IBusinessObject, PK extends Serializable> {
...
@Transactional(readOnly = true)
public <C extends E> C findFirstByFields(Class<C> type, String[] fields, Object[] values, String[] dependencies)
throws ModelException {
List<C> list = findAllByFields(type, fields, values, null, null, 1, null);
if (list.isEmpty()) {
return null;
} else {
C obj = list.get(0);
loadDependencies(obj, dependencies);
return obj;
}
}
...
}
最后,该项目使用maven进行构建,并在JBossEAP 6.1上运行。
因此,使用此配置,在构建和部署WAR文件时,一切都可以正常工作。但是,如果我只在其中一个WAR文件中构建一个简单的EAR文件,那么加载时编织会编织除BaseDAO之外的所有类。
我已经为此奋斗了很多年,我唯一能得到的是,在应用程序启动时,编织在这两种情况下几乎是一样的,只是在EAR中,BaseDAO没有编织。我不明白为什么。你知道为什么会发生这种事吗?
p.D.:当从WAR:启动应用程序时,启用AspectJ编织日志显示了这一点
...
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.services.CommonService$AjcClosure1'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.services.CommonService$AjcClosure3'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.services.CommonService$AjcClosure5'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.subproject.services.Repository$AjcClosure1'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.model.dao.BaseDAO$AjcClosure1'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.model.dao.BaseDAO$AjcClosure3'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.model.dao.BaseDAO$AjcClosure5'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.model.dao.BaseDAO$AjcClosure7'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.subproject.model.dao.LastDocumentNumberDAO$AjcClosure1'
...
但是当在内部启动EAR时,BaseDAO类被完全忽略:
...
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.services.CommonService$AjcClosure1'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.services.CommonService$AjcClosure3'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.commons.services.CommonService$AjcClosure5'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.subproject.services.Repository$AjcClosure1'
ServerService Thread Pool -- 227 ? [ModuleClassLoader@1b3a9e75] debug generating class 'com.myproject.subproject.model.dao.LastDocumentNumberDAO$AjcClosure1'
...
最后我们找到了问题所在。它在jboss-deployment-structure.xml中。项目中的每一场战争都有自己的jboss-deployment-structure.xml,但有一些例外:
<jboss-deployment-structure>
<deployment>
<!-- Exclusions allow you to prevent the server from automatically adding some dependencies -->
<exclusions>
<module name="org.apache.log4j" />
<module name="org.slf4j" />
<module name="org.apache.commons.logging" />
<module name="org.log4j" />
<module name="org.jboss.logging" />
<module name="org.javassist" />
<module name="org.hibernate.validator" />
<module name="org.jboss.ws.cxf" />
</exclusions>
<exclude-subsystems>
<subsystem name="webservices" />
</exclude-subsystems>
</deployment>
</jboss-deployment-structure>
但在EAR部署中,EAR的特定jboss-deployment-structure.xml丢失了,因此类加载器以一种非常不同的方式工作,从而产生了我在问题中提出的问题。只需在EAR的META-INF中放入jboss-deployment-structure.xml(EAR,即WAR的组合)就解决了这个问题。
希望这能帮助到有类似问题的人。