Hi,
I'm still trying to see if I can get Spring/AspectJ AOP to work in a
Play environment, just to see if it can be done if nothing else. It's
not quite working yet, but I seem to be making some progress. Would be
interested to hear if anyone has tried this and succeeded.
So far:
- I've swapped to Steve Chaloner's version of the Spring plugin to
get support for namespaces in Spring's config (thanks Steve!) -
https://github.com/schaloner/Play--framework-Spring-module
- I added conf/META-INF/aop.xml with:
<!DOCTYPE aspectj PUBLIC
"-//AspectJ//DTD//EN" "
http://www.eclipse.org/aspectj/dtd/
aspectj.dtd">
<aspectj>
<weaver>
<!-- only weave classes in our application-specific packages -->
<include within="org.example.*" />
</weaver>
<aspects>
</aspects>
</aspectj>
- I have this conf/application-context.xml:
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="
http://www.springframework.org/schema/beans"
xmlns:xsi="
http://www.w3.org/2001/XMLSchema-instance"
xmlns:context="
http://www.springframework.org/schema/context"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
http://www.springframework.org/schema/context
http://www.springframework.org/schema/context/spring-context-3.0.xsd">
<context:load-time-weaver/>
</beans>
- I have a silly test bean:
@Configurable(autowire=Autowire.BY_TYPE)
@Scope("prototype")
public class TestBean {
@Autowired
private ContextRepository contextRepository;
public TestBean() {
System.out.println("Initialising");
}
public void setContextRepository(ContextRepository contextRepository)
{
System.out.println("Setting");
this.contextRepository = contextRepository;
}
public ContextRepository getContextRepository() {
return contextRepository;
}
}
ContextRepository is an interface, and I know Spring knows how to
Autowire it, since I'm using it elsewhere via a standard @Component
and @Autowire property.
- And a controller that just does:
TestBean testBean = new TestBean();
System.out.println("Repo:" + testBean.getContextRepository());
- On first attempt, I got this:
An unexpected error occured caused by exception BeanCreationException:
Error creating bean with name
'org.springframework.context.weaving.AspectJWeavingEnabler#0':
Initialization of bean failed; nested exception is
org.springframework.beans.factory.BeanCreationException: Error
creating bean with name 'loadTimeWeaver': Initialization of bean
failed; nested exception is java.lang.IllegalStateException:
ClassLoader [play.classloading.ApplicationClassloader] does NOT
provide an 'addTransformer(ClassFileTransformer)' method. Specify a
custom LoadTimeWeaver or start your Java virtual machine with Spring's
agent: -javaagent:org.springframework.instrument.jar
- Ok - Play's classloader doesn't support weaving, I'm guessing. So I
added the -javaagent line (with an absolute path to the right
org.springframework.instrument.jar file), after Play's own -javaagent
line.
Now, the error disappears, but Spring never sets my bean property
either. The "Initializing" message is printed, but the "Setting"
message isn't.
- I tried to wire things in XML
<bean name="contextRepository"
class="org.example.repository.ContextRepositoryImpl" />
<bean name="testBean" class="org.example.domain.TestBean"
scope="prototype">
<property name="contextRepository" ref="contextRepository" />
</bean>
- Interestingly, when I change the XML config and reload, I get this
error message in the console:
[ApplicationClassloader@2781b3d4] error can't determine superclass of
missing type
org.springframework.transaction.interceptor.TransactionAspectSupport
[Xlint:cantFindType]
INFO: (Enh120375): AspectJ attempting reweave of 'org/example/
TestBean'
[ApplicationClassloader@2781b3d4] error can't determine annotations of
missing type org.springframework.transaction.annotation.Transactional
when weaving type org.example.TestBean
when weaving classes
when weaving
[Xlint:cantFindType]
[ApplicationClassloader@2781b3d4] error can't determine annotations of
missing type org.springframework.transaction.annotation.Transactional
when weaving type org.example.domain.TestBean
when weaving classes
when weaving
[Xlint:cantFindType]
[ApplicationClassloader@2781b3d4] error can't determine annotations of
missing type org.springframework.transaction.annotation.Transactional
when weaving type org.example.domain.TestBean
when weaving classes
when weaving
[Xlint:cantFindType]
[ApplicationClassloader@2781b3d4] error can't determine annotations of
missing type org.springframework.transaction.annotation.Transactional
when weaving type org.example.domain.TestBean
when weaving classes
when weaving
[Xlint:cantFindType]
[ApplicationClassloader@2781b3d4] error can't determine annotations of
missing type org.springframework.transaction.annotation.Transactional
when weaving type org.example.domain.TestBean
when weaving classes
when weaving
[Xlint:cantFindType]
[ApplicationClassloader@2781b3d4] error can't determine annotations of
missing type org.springframework.transaction.annotation.Transactional
when weaving type org.example.domain.TestBean
when weaving classes
when weaving
[Xlint:cantFindType]
Martin