"; */ ?>


12
Oct 10

Running Spring AspectJ Tests with Maven

You need to use a real AspectJ aspect with Spring, where you would like to inject some dependencies into this aspect as a Spring container starts up.

Here is an AspectJ aspect:

@Aspect
public class VeryImportantAspect {
    ...
    public void setSomeDependency( SomeDependency dependency ) {
        this.dependency = dependency;
    }
    ...
}

Now let’s define it as a bean and inject “someDependency”:

<bean id="veryImportantAspect" 
         class="org.dotkam.VeryImportantAspect"
         factory-method="aspectOf">
 
         <property name="someDependency" ref="someDependency"/>
</bean>

Notice factory-method=”aspectOf” that tells Spring to use a real AspectJ ( not Spring AOP ) aspect to create this bean. In reality, if the “VeryImportantAspect” was already woven in, it will have an “aspectOf” method.

Hence if you get this error at some point:

No matching factory method found: factory method 'aspectOf()'

That would mean that the aspect was not woven by AspectJ weaver.

We also need to tell Spring to use load time weaving:

<context:load-time-weaver/>

If you run with the above configuration without doing anything, you would get a following error:

ClassLoader does NOT provide an 'addTransformer(ClassFileTransformer)' method

That tells you ( well not explicitly :) ) to include a “spring-instrument.jar” javaagent.

So at this point two things need to be added: AspectJ weaver and Spring Instrument agent. Build / Continues integration server does not use any IDE, so it is not as simple as downloading AspectJ plugin for IDEA / Eclipse and including VM arguments in Run Configurations… It is simpler: just add the two in your POM file.

Adding an AspectJ plugin:

<plugin>
     <groupId>org.codehaus.mojo</groupId>
     <artifactId>aspectj-maven-plugin</artifactId>
     <version>1.3</version>
     <executions>
         <execution>
             <configuration>
                <source>1.6</source>
                <target>1.6</target>
            </configuration>                     
             <goals>
                 <goal>compile</goal>       <!-- use this goal to weave all your main classes -->
                 <goal>test-compile</goal>  <!-- use this goal to weave all your test classes -->
             </goals>
         </execution>
    </executions>
</plugin>

Adding a Spring Instrument agent to participate in a test execution:

<plugin>
	<groupId>org.apache.maven.plugins</groupId>
	<artifactId>maven-surefire-plugin</artifactId>
	<version>2.4</version>
	<configuration>
            <forkMode>once</forkMode>
            <argLine>
                 -javaagent:"${settings.localRepository}/org/springframework/spring-instrument/${spring.framework.version}/spring-instrument-${spring.framework.version}.jar"
	    </argLine>
            <useSystemClassloader>true</useSystemClassloader>
	</configuration>
</plugin>

And all that work, just too see a couple of lines from Maven:

[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESSFUL
[INFO] ------------------------------------------------------------------------

06
Oct 10

Humans + Software = Zero

FACT:

Humans are stateful and mutable beings that have no problems processing many things concurrently and share state with others + they are usually “coupled”

GOAL:

And yet in software design we strive for being stateless, immutable and decoupled.


CONCLUSION I:

Humans should not design software

CONCLUSION II:

If humans were designed by software, that project sucked ( according to the GoF teachings )

CONCLUSION III:

Humans are not software, they are maybe… hardware

CONCLUSION IV:

Good software is going to lead to the race of Inhumans

CONCLUSION V:

Humans + Software = 0


26
Sep 10

Money Making Project

For the past several years most of my projects were based on Spring and Hibernate. And what I keep seeing is how people struggle to understand how the two are working together.

So going from project to project, I have to repeat the same spiel over and over again to get people up to speed.

Since I believe that the most effective way to LEARN is to DO, I create simple examples for people to play with / to complete / to analyze, etc..

So “Money Making Project” is one of such examples. It comfortably lives at github’s luxury apartments, so anybody can “git clone” / “fork” and play with it.

Besides making money, this project also demos things such as:

A way to structure a project

Maven based structure ( hence can be easily used by gradle ). Configuration and property files organized under “META-INF/conf”, “META-INF/props”, etc..

A way to separate Spring configs

“tx-spring-config.xml”, “persistence-spring-config.xml”, “service-spring-config.xml”, “repository-spring-config.xml” and “application-context.xml” that includes them all

Properties via PropertyPlaceholderConfigurer

<context:property-placeholder location="classpath:META-INF/props/env.properties"/>

Hibernate overall configuration file

That is injected into AnnotationSessionFactoryBean

Hibernate Named Queries

That are linked to the Hibernate overall config

<mapping resource="META-INF/conf/hibernate/mapping/startup-bank-named-queries.xml"/>

Spring’s DAO / Hibernate Exception Translation

Via @Repository and “PersistenceExceptionTranslationPostProcessor”

Simple CRUD Repository

public interface MoneyRepository {
 
    public void make( MoneyRoll moneyRoll );        // C
    public MoneyRoll find( Long id );                       // R
    public void update( MoneyRoll moneyRoll );     // U
    public void takeOut( MoneyRoll moneyRoll );    // D
}

with a Hibernate based implementation

Transaction Management with Spring AOP

Declarative, on a Service Level, using “aop:config”, “tx:advice” namespaces

Spring Testing

With SpringJUnit4ClassRunner, ContextConfiguration, etc..

Using Embeded in-memory H2 Database for Testing

<jdbc:embedded-database id="dataSource" type="H2"/>

Hibernate Logging

Most useful hibernate “log4j.logger” properties

Demoing how important Transaction is for Hibernate Sessions

“HibernateSessionNotBoundToThreadIntegrationTest” for the second (after LazyInitializationException ) most common Hibernate exception: “No Hibernate Session bound to thread, and configuration does not allow creation of non-transactional one here”


10
Sep 10

Spring Expression Language: Calling a Method with Parameters

Have you ever wanted to win $1,000,000 with a single SpEL ( Spring Expression Language ) call? Well, now you can, and here is how.

Let’s say there is a Lottery that deposits money to a winner’s bank account and congratulates the winner:

private class Lottery {
    // ...
    public String congratulateWinner( String name, BigDecimal amount, Date date ) {
    	String now = new SimpleDateFormat( "MM-dd-yyyy" ).format( date );
    	String cash = new DecimalFormat( "$#,###,###" ).format( amount.doubleValue() );
 
    	return "Congratulations " + name + "! " +
    	       "Today is " + now + ", and it's your lucky day, because " +
    	       "you just won " + cash + "!";
    }
}

Here is how to make Anatoly win money with SpEL:

"congratulateWinner( 'Anatoly', #amount, #date )"

( of course, let’s not forget to set an amount to at least a million dollars ).

And here is a million dollar unit test:

@Test
public void shouldInvokeMethodWithParameters() {
 
    Lottery lottery = new Lottery();
 
    GregorianCalendar calendar = new GregorianCalendar();
    calendar.set( 2010, 8, 10 );
 
    BigDecimal amount = BigDecimal.valueOf( 1000000.00 );
 
    // letting SPEL know about the "lottery", the "amount" won, and the "date"
    EvaluationContext context = new StandardEvaluationContext( lottery );
    context.setVariable( "amount", amount );
    context.setVariable( "date", calendar.getTime() );
 
    ExpressionParser parser = new SpelExpressionParser();
 
    // using '#' to identify a variable ( NOTE: #this, #root are reserved variables )
    Expression exp = parser.parseExpression( "congratulateWinner( 'Anatoly', #amount, #date )" );
 
    String congratulations = ( String ) exp.getValue( context );	
    assertEquals( "Congratulations Anatoly! " + 
                  "Today is 09-10-2010, and it's your lucky day, because you just won $1,000,000!", 
                  congratulations );
}

(!) Do not write code that does not earn you money :)


09
Sep 10

Check If The Aspect Was Applied

Let’s say you have an aspect defined that will be applied to a class:

<bean id="someComponent"
      class="org.dotkam.SomeComponent" />
 
<aop:config>
	<aop:aspect ref="someAspect">
		<aop:around method="someMethod"
                            pointcut="execution(public * org.dotkam.SomeComponent.*(..))" />
	</aop:aspect>
</aop:config>

and you of course have “proxy-target-class” set to “true”:

<aop:aspectj-autoproxy proxy-target-class="true"/>

Here is how to check if the aspect was applied:

import static org.junit.Assert.assertTrue;
import net.sf.cglib.proxy.Enhancer;
 
  ... ...
@Resource(name="someComponent")
SomeComponent someComponent
 
  ... ...
assertTrue( Enhancer.isEnhanced( someComponent.getClass() ) );

Behind the scenes it is enhanced with CGLIB’s Enhancer that has a convenient isEnhanced method.

Useful when developing aspects.

NOTE: The above is true given, of course, that this is THE ONLY aspect applied to this component.