Announcement Announcement Module
Collapse
No announcement yet.
Build-time weaving with @Configurable Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • Build-time weaving with @Configurable

    I have been able to use ajc (1.5.2) to effectively weave aspects declared with the @Aspect annotation. But I don't seem to be getting it to weave beans with the @Configurable annotation.

    I have tried to follow the instructions in the docs, but I am sure that I am missing something.

    I compiled with spring-aspects.jar in my classpath. I added:

    <aop:spring-configured/>

    to my application context. To be safe, I added:

    depends-on="org.springframework.beans.factory.aspectj.Anno tationBeanConfigurerAspect"

    to the first bean that executes on startup. And I added:

    @Configurable( autowire = Autowire.BY_NAME )

    to the domain object that I wanted to wire.

    However, on startup I get a null pointer exception because the dependency was never wired. Do I need to do something else to tell ajc how to weave this class?

  • #2
    I believe that Spring2 still uses CGLIB by default so make sure your class/methods aren't final.

    Not definitive, just a quess.....this all might be a big fat lie

    Comment


    • #3
      Originally posted by cepage
      However, on startup I get a null pointer exception because the dependency was never wired. Do I need to do something else to tell ajc how to weave this class?
      Have you tried getting ajc to print debug information during weaving? That made stuff a whole lot clearer for me when I tried load-time weaving.

      Comment


      • #4
        I have had it working with the lazy-init bean definition.

        It's a great little tool when it works. I am not sure it worked in all classes, but it definitely worked in some of them.

        Comment


        • #5
          You are right, Thomas. My problem is not specific to build-time weaving. The @Configurable stuff is just not working consistently.

          I switched over to using the plain @Configurable() annotation, and explicitly declaring my beans as wired prototypes, and I get the same failures.

          Are there any test cases in the Nightly Build sources that demonstrates @Configurable working? I could use this as a baseline to file a bug report with a working counterexample.

          Comment


          • #6
            I am also having problems with @Configurable.

            For example, take a standard bean class called Order
            Code:
            @Configurable
            public class Order implements Serializable
            {
            private Integer _deliveryMinuteWindowInterval;
            
            public Integer getDeliveryMinuteWindowInterval()
                {
                    return _deliveryMinuteWindowInterval;
                }
            public void setDeliveryMinuteWindowInterval( Integer deliveryMinuteWindowInterval )
                {
                    _deliveryMinuteWindowInterval = deliveryMinuteWindowInterval;
                }
            }
            My XML is defined as:
            Code:
            <aop:spring-configured/>
            
                <bean id="deliveryWindowMinuteInterval" class="java.lang.Integer">
                    <constructor-arg>
                        <value>15</value>
                    </constructor-arg>
                </bean>
            
            <bean class="com.vodori.dolce.component.commerce.model.Order" lazy-init="true">
                   <property name="deliveryMinuteWindowInterval" ref="deliveryWindowMinuteInterval" />
                 </bean>
            However, everytime an order object is created anywhere in the system the deliveryMinuteWindowInterval is null....

            Any ideas? This is using RC3 snapshot from 7-26-2006

            Thanks!

            Comment


            • #7
              Originally posted by GrantGochnauer
              Any ideas? This is using RC3 snapshot from 7-26-2006
              If this is all you have done, you have not made Spring aware of the Configurable annotation. <aop:spring-configured/> is _not_ enough. You either need to use load-time aspectj weaving, or you need to use the aspectj compiler to get compile-time weaving of the aspect related to the @Configurable annotation.

              This is described in several articles on the 'net. I suggest you have a look around for those.

              Comment


              • #8
                Hi cepage -

                Have u followed the instructions in section 7.7.4 ?

                - creation of aop.xml
                - add -javaagent:<path-to-ajlibs>/aspectjweaver.jar as VM arguments

                Regards.
                - Debasish

                Comment


                • #9
                  Originally posted by debasishg
                  Hi cepage -

                  Have u followed the instructions in section 7.7.4 ?

                  - creation of aop.xml
                  - add -javaagent:<path-to-ajlibs>/aspectjweaver.jar as VM arguments
                  Section 6.7.4 specifies that those steps are necessary for load-time weaving, but I am performing build-time weaving. My understanding is that these steps are not necessary for build-time weaving. Thanks for your help, though.

                  Comment


                  • #10
                    So are there any solution here to make this work with build-time weaving? I have AJDT installed and still I get the nullpointer with @Configurable. My domain object is created with the new operator in a AbstractDependencyInjectionSpringContextTests which loads the applicationcontext.

                    Comment


                    • #11
                      I have @Configurable running with both build-time and load-time weaving. Although the LTW version has a problem with the Spring 2.0rc3 because of a bug in AspectJ 1.5.2 (see https://bugs.eclipse.org/bugs/show_bug.cgi?id=153572).

                      I have just perpared a small eclipse project showing the build-time weaving in an Eclipse AJDT project. You need the same configuration in the spring context as with LTW.

                      Code:
                         <aop:spring-configured/>
                          
                          <bean class="com.trivadis.aop.configurable.Address" singleton="false">
                          	<property name="codeRepository" ref="codeRepository"/>
                          </bean>
                          
                      	<bean id="codeRepository" class="com.trivadis.aop.configurable.CodeRepositoryImpl"/>
                      Then you have to add spring-aspects.jar to the AspectJ Aspect Path, because that's where the aspect handling the @Configurable can be found. The same can of course also be done with Maven or Ant.

                      I've uploaded the sample eclipse project with this post. Just run the unit test in ConfigurableTest.

                      Hope it helps!

                      Comment


                      • #12
                        That worked for me. Thanks a lot!

                        Comment


                        • #13
                          Hi!

                          Thank you for posting this description and code example!

                          This made me understand how to make our unittests run from inside eclipse when built by eclipse.

                          Until now the unittests worked just fine when running them from maven. When running them from eclipse we had to let maven do the compiling before running the tests if we had changed any of the classes using @Configurable to get dependencies injected

                          The next step was to make maven generate correct .project og .classpass file for us and we almost do that now with the following in pom.xml:
                          Code:
                                <plugin>
                                  <groupId>org.apache.maven.plugins</groupId>
                                  <artifactId>maven-eclipse-plugin</artifactId>
                                  <configuration>
                                    <projectnatures>
                                      <java.lang.String>org.springframework.ide.eclipse.core.springnature</java.lang.String>
                                      <java.lang.String>org.eclipse.jdt.core.javanature</java.lang.String>
                                      <java.lang.String>org.eclipse.ajdt.ui.ajnature</java.lang.String>
                                    </projectnatures>
                                    <buildcommands>
                                      <buildcommand>org.eclipse.ajdt.core.ajbuilder</buildcommand>
                                    </buildcommands>
                                  </configuration>
                                </plugin>
                          What is missing here is generating the org.eclipse.ajdt.aspectpath attribute for the classpathentry in the .classpath file i.e.

                          Code:
                            <classpathentry kind="var" path="M2_REPO/org/springframework/spring-aspects/2.0.6/spring-aspects-2.0.6.jar">
                               <attributes>
                                  <attribute name="org.eclipse.ajdt.aspectpath" value="true"/>
                               </attributes>
                            </classpathentry>
                          This is not possible today with maven-eclipse-plugin, but there is an issue for this feature in the jira for maven-eclipse-plugin, see

                          http://jira.codehaus.org/browse/MECLIPSE-270

                          Feel free to vote for this issue!

                          btw are we using the following aspectj-maven-plugin configuration:
                          Code:
                                <groupId>org.codehaus.mojo</groupId>
                                  <artifactId>aspectj-maven-plugin</artifactId>
                                  <version>1.0-beta-2</version>
                                  <executions>
                                    <execution>
                                      <goals>
                                        <goal>compile</goal>
                                        <goal>test-compile</goal>
                                      </goals>
                                    </execution>
                                  </executions>
                                  <configuration>
                                    <source>1.5</source>
                                    <target>1.5</target>
                                    <encoding>iso-8859-1</encoding>
                                    <verbose>true</verbose>
                                    <outxml>false</outxml>
                          
                                    <showWeaveInfo>true</showWeaveInfo>
                                    <proceedOnError>true</proceedOnError>
                           
                                    <weaveDependencies>
                                      <weaveDependency>
                                        <groupId>org.springframework</groupId>
                                        <artifactId>spring-aspects</artifactId>
                                      </weaveDependency>
                                    </weaveDependencies>
                          
                                    <aspectLibrarys>
                                      <aspectLibrary>
                                        <groupId>org.springframework</groupId>
                                        <artifactId>spring-aspects</artifactId>
                                      </aspectLibrary>
                                    </aspectLibrarys>
                          
                                  </configuration>
                                </plugin>

                          -Kaj
                          Last edited by kajh; Sep 3rd, 2007, 06:16 AM.

                          Comment


                          • #14
                            My solution to the problem

                            Here is the solution I am using to do weaving - http://anydoby.com/jblog/article.htm?id=61&lng=en

                            Comment


                            • #15
                              Originally posted by kajh View Post
                              Hi!

                              Thank you for posting this description and code example!

                              This made me understand how to make our unittests run from inside eclipse when built by eclipse.

                              Until now the unittests worked just fine when running them from maven. When running them from eclipse we had to let maven do the compiling before running the tests if we had changed any of the classes using @Configurable to get dependencies injected

                              The next step was to make maven generate correct .project og .classpass file for us and we almost do that now with the following in pom.xml:
                              Code:
                                    <plugin>
                                      <groupId>org.apache.maven.plugins</groupId>
                                      <artifactId>maven-eclipse-plugin</artifactId>
                                      <configuration>
                                        <projectnatures>
                                          <java.lang.String>org.springframework.ide.eclipse.core.springnature</java.lang.String>
                                          <java.lang.String>org.eclipse.jdt.core.javanature</java.lang.String>
                                          <java.lang.String>org.eclipse.ajdt.ui.ajnature</java.lang.String>
                                        </projectnatures>
                                        <buildcommands>
                                          <buildcommand>org.eclipse.ajdt.core.ajbuilder</buildcommand>
                                        </buildcommands>
                                      </configuration>
                                    </plugin>
                              What is missing here is generating the org.eclipse.ajdt.aspectpath attribute for the classpathentry in the .classpath file i.e.

                              Code:
                                <classpathentry kind="var" path="M2_REPO/org/springframework/spring-aspects/2.0.6/spring-aspects-2.0.6.jar">
                                   <attributes>
                                      <attribute name="org.eclipse.ajdt.aspectpath" value="true"/>
                                   </attributes>
                                </classpathentry>
                              This is not possible today with maven-eclipse-plugin, but there is an issue for this feature in the jira for maven-eclipse-plugin, see

                              http://jira.codehaus.org/browse/MECLIPSE-270

                              Feel free to vote for this issue!

                              btw are we using the following aspectj-maven-plugin configuration:
                              Code:
                                    <groupId>org.codehaus.mojo</groupId>
                                      <artifactId>aspectj-maven-plugin</artifactId>
                                      <version>1.0-beta-2</version>
                                      <executions>
                                        <execution>
                                          <goals>
                                            <goal>compile</goal>
                                            <goal>test-compile</goal>
                                          </goals>
                                        </execution>
                                      </executions>
                                      <configuration>
                                        <source>1.5</source>
                                        <target>1.5</target>
                                        <encoding>iso-8859-1</encoding>
                                        <verbose>true</verbose>
                                        <outxml>false</outxml>
                              
                                        <showWeaveInfo>true</showWeaveInfo>
                                        <proceedOnError>true</proceedOnError>
                               
                                        <weaveDependencies>
                                          <weaveDependency>
                                            <groupId>org.springframework</groupId>
                                            <artifactId>spring-aspects</artifactId>
                                          </weaveDependency>
                                        </weaveDependencies>
                              
                                        <aspectLibrarys>
                                          <aspectLibrary>
                                            <groupId>org.springframework</groupId>
                                            <artifactId>spring-aspects</artifactId>
                                          </aspectLibrary>
                                        </aspectLibrarys>
                              
                                      </configuration>
                                    </plugin>

                              -Kaj
                              Your solution will also include Spring aspects into the resulting jar file. How do you fix that?

                              Comment

                              Working...
                              X