我遇到了一個奇怪的問題,我很難追查到。我有一個類(ServiceErrorInterceptor)定義爲@Aspect
,它通過XML配置實例化爲單例bean。 XML配置允許我注入它的依賴bean。JUnit編織錯誤Spring AOP Bean
在我的正常工作流程中,一切正常。方面類正確實例化,每當調用通知時,注入的bean就像我所期望的那樣。
但是,當我運行我的JUnit測試時,所有注入的bean都是空的。這使我得出這樣的結論,即建議是從一個不同的bean調用的,而不是由Spring實例化的單一bean。爲了進一步驗證我的假設,我在實例化過程中調用的setter上放置了一個斷點,並且如果我在我的建議中放置了斷點,請參閱bean id與bean id不同。
是否有一些特殊的配置,我必須在我的JUnit類中啓用才能解決這個問題?我的測試類已經被標註有:
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = {
"classpath:spring/applicationContext-base.xml",
"classpath:spring/applicationContext-calculateServices.xml",
"classpath:spring/applicationContext-dom.xml"})
public class LendingSimulationServiceImplTest {
...
...
}
我已經通過日誌看(我啓用了春天跟蹤日誌),但沒有看到任何脫穎而出。在這裏發佈整個日誌可能會過度。如果在日誌的特定部分有價值,請讓我知道,我會發布它。
我能夠發佈我的代碼的方面,我的junit和我的配置,如果這是有幫助的。
應用context.xml的片段:
<!-- SPRING ASPECT BEAN. POINTCUT DEFINED IN BEAN WITH ANNOTATION -->
<bean id="serviceErrorInterceptor" class="com.cws.cs.lendingsimulationservice.error.ServiceErrorInterceptor" scope="singleton">
<property name="errorMessageProvider" ref="resourceBundleProviderImpl"/>
<property name="defaultLocale">
<util:constant static-field="java.util.Locale.ENGLISH" />
</property>
</bean>
任何建議,將不勝感激。
編輯
我的bean被實現爲:
@Aspect
public class ServiceErrorInterceptor {
/**
* Logger
*/
private static final Logger logger = LoggerFactory.getLogger(ServiceErrorInterceptor.class);
/**
* SOAP Header data
*/
@Autowired
private SOAPHeaderData soapHeaderData;
public ServiceErrorInterceptor(){
int x = 0;
x=x+1;
}
/**
* Exception Interceptor.
* @param ex
*/
@AfterThrowing(pointcut = "execution(* com.cws.cs.lendingsimulationservice.process.CalculatorProcess.calculate (..))", throwing = "ex")
public void errorInterceptor(Exception ex) {
if (logger.isDebugEnabled()) {
logger.debug("Error Message Interceptor started");
}
}
我的聚甲醛的相關部分:
<!-- Aspect Oriented Programming (AOP) Framework (depends on spring-core,
spring-beans) Define this if you use Spring AOP APIs (org.springframework.aop.*) -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-aop</artifactId>
<version>${org.springframework.version}</version>
</dependency>
<!-- Support for AspectJ Annotations -->
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>${org.aspectj}</version>
</dependency>
我已經做了進一步的調試,並把一個斷點在假構造函數,我得到如下結果:
- 使用@Aspect和XML配置,構造函數被調用兩次(不同的bean ID)
- 如果我刪除@Aspect註釋,那麼它只被調用一次。
- 如果離開@Aspect但刪除XML配置,則甚至不會調用構造函數。
- 如果我將@Component註釋與@Aspect結合使用(但沒有任何XML配置),那麼這個bean會被構造兩次。
- 然而,奇怪的是,對於XML配置@Component和@Aspect註釋和,構造函數仍然只調用兩次。
那麼爲什麼要同時使用XML配置和@Aspect註釋會導致構造函數被兩次不同的bean ID調用兩次?
我進一步驗證,如果我將整個AOP定義移動到XML配置中(移除@Aspect和@Pointcut註釋),那麼這個bean只構造一次。
編輯完
感謝,
埃裏克
不可以。唯一的註釋是@Aspect。另外,如果有一個額外的bean,它將在Spring日誌中顯示爲一個重複的bean定義。日誌中沒有任何東西。我只是意識到我正在使用AspectJ以及其他方面編織其他類的其他方面,但我不知道如何或爲什麼會影響任何東西。 – 2012-04-13 01:05:05
您是否可以確認您在Spring AOP中使用了@Aspect註釋,而不是使用AspectJ編譯時間或加載時間織入,如果是編譯時或加載時編織,那麼注入到某個方面的依賴關係有點不同:使用aspectOf工廠方法 - http://static.springsource.org/spring/docs/3.1.x/spring-framework-reference/html/aop.html – 2012-04-13 13:45:20
我在Spring AOP中使用@Aspect註釋。我添加了一些AspectJ編織的其他方面,但已經從pom和包中刪除它們。去除AJ沒有任何區別。我用更多的信息編輯了我的問題。謝謝! – 2012-04-13 15:46:55