Staged Spring Context project has found a home

del.icio.us TRACK TOP
Posted on April 10th, 2008 by Kaare Nilsen. Filed in Uncategorized.
No comments yet. Be the first to comment!

I have gotten some positive feedbacks on the project, which I very much appreciate, and found myself in need for a place where people could read documentation and files issues. So I have created a redmine instance on my machine where you could do just that. http://projects.kaare-nilsen.com/projects/show/1

One important thing to mention is that I have changed from using Subversion to using mercurial as source control management, and the new url for the source code is now https://hg.kaare-nilsen.com/staged-spring

AspectJ maven plugin 1.0 released

del.icio.us TRACK TOP
Posted on April 7th, 2008 by Kaare Nilsen. Filed in Open Source, aspectJ.
No comments yet. Be the first to comment!

I am happy to announce the release of the AspectJ plugin version 1.0 for Maven 2.

This release provides:

  • AspectJ 1.5.4 compiler support for Maven2
  • Generating LTW descriptors
  • Ajdoc reports for Maven 2

For instructions on how to use the plugin, refer to it’s web site at: http://mojo.codehaus.org/aspectj-maven-plugin

Stage aware spring contexts part II

del.icio.us TRACK TOP
Posted on April 6th, 2008 by Kaare Nilsen. Filed in Open Source.
No comments yet. Be the first to comment!

As we have seen in the previous post with the @Stage annotation or the StagedSingletonFactoryBean, you can by using them choose between different implementation of Spring bean at runtime. But sometimes it is not the implementation you would like to switch between but the internal configuration of a particular class.

To support this, we have the StagedProperties class. It is a class in where you can register multiple property files used for looking up staged values for a given property key using stage as a prefix to separate values.

Property file layout

Each property file may have several entries for one key each prefixed by the stage it should apply. If no value found for the stage we are running in, it falls back on the key with no prefix. As shown in the following example

#
# myApp properties
#
myKey=default value
development.myKey=development value
test.myKey=test value
production.myKey=production value
custom.myKey=custom value

You are also allowed to use keys in the values, and it will be resolved and replaced with the value of the corresponding key as shown here :

#
# myApp properties
#
baseUrl=http://localhost
development.baseUrl=http://dev.arktekk.no
test.baseUrl=http://test.arktekk.no
production.baseUrl=http://arktekk.no

customerServiceEndpoint=${baseUrl}/services/customerService
orderServiceEndpoint=${baseUrl}/services/mockCustomerService

Configuring and using staged properties in Java


StagedProperties properties
  = new StagedProperties("myProperties.properties");
String myValue = properties.getProperty("myKey");

There are also constructors taking a list of property files, or you may use the registerPropertiesmethod to register more files. The StagedProperties class uses Spring resource loader to load the property files so you can use all the Spring supported urls, as e.g. classpath:myProperties.properties.

Use in Spring beans

In my opinion I do like spring beans that tries to configure them selves as much as possible. I think there are way to much use of Spring configuration files to configure ordinary properties like database url’s, service end points and so on. So what I would prefer is that we configure a StagedProperties bean in Spring, and then use the Spring autowiring support to get it injected unto other spring beans, and then use the InitializingBean inteface or the new support for the @PostConstruct annotation In this way we only need to configure our spring beans, in the case that the default values does not work in our application. This is best explained in the 2 part example below.

Configuring the StagedProperties bean

First we need to configure our properties in Spring by adding this xml snippet

<bean id="stagedProperties"
     class="no.arktekk.stagedspring.properties.StagedProperties">
  <property name="propertyFiles">
    <list>
      <value>no/arktekk/stagedspring/properties/test1.properties</value>
    </list>
  </property>
</bean>

Using in beans

Then it is time to get it injected, and utilized in a spring bean

public class SpringBean {
  @Autowired private StagedProperties properties;

    @PostConstruct
    public void initProperties() throws Exception {
      band = properties.getProperty("aCoolBand", "Mothers of invention");
    }

Note by using afterPropertiesSet or @PostConstruct this will override any configuration done in Spring configuration files, and the only way to change the values is by using the property files

Overriding properties

StagedProperties uses an ArrayList internally and, in the case of multiple files are registered, you are allowed to use a key in several files. When the StagedProperties class encounters several keys that match, it will always use the key registered last in the class. You may also register a file that does not yet exists, and it will be picked by the refresh mechanism.

Refreshing of property files

When a StagedProperties class is added to a Spring context, it will start a refresh thread, that runs on the schedule defined in the property refreshIntervalInSecods. The default here is 60 seconds. If you are constructing the class yourself you will need to start the refresh mechanism manually by invoking the startRefreshingCache method.

Configuring Spring beans with placeholders

In addition, those of you familiar with Spring probably know the PropertyPlaceHolderConfigurer that Spring ships with. To be able to use this kind of configuration and use stages this project provide a StagedPropertyPlaceHolderConfigurer class that are able to use the StagedProperties class to resolve the values. This functionality is best shown with an example

<bean id="stagedProperties"
     class="no.arktekk.stagedspring.properties.StagedProperties">
  <property name="propertyFiles">
    <list>
      <value>myProperties.properties</value>
    </list>
  </property>
</bean>

<bean id="placeHolderConfigurer"
     class="no.arktekk.stagedspring.properties.StagedPropertyPlaceholderConfigurer">
  <property name="stagedProperties" ref="stagedProperties" />
</bean>

<bean id="testBean" class="..TestBean">
  <property name="url" value="${aCoolUrl}" />
</bean>

of course the stagedProperties property is marked with the @Autowired annotation so the ref shown above is optional

For more information

Please check out the latest version of the code at staged-spring and run the mvn site:site command for more detailed documentation.

Stage aware spring contexts

del.icio.us TRACK TOP
Posted on April 2nd, 2008 by Kaare Nilsen. Filed in Open Source.
1 comment filed

The Spring framework has in our parts of the world become the kind of de-facto standard for almost all enterprise Java pplications. There are close to zero projects starting up in the Oslo area not using it. In my role as consultant and Spring Instructor I have over the years seen my share of Spring based projects, and one of the discussions that I see in these
projects are how should we configure our Spring applications ?

Well of course there are no one answer to that question, and the options we have when we use Spring are many, and sufficient for most use cases. But there is one use case that too often have been a kind of pain in the….

How do we manage configurations in various stages of development?

Let us say that we are going to use one implementation of a interface when we are developing our application, and another one in production. Let us say for e.g. mocking purposes. How should we configure our application to support that.

There is always the option of having your build system do it for you with ant filters, or Maven resource filtering. But hey. That often require us to build the application one time for each environment.

Then we have PropertyPlaceholderConfigurer. It is a very little know fact, that it also can be used to select bean classes using property files. But again. We would need one property file for each stage, and it can be somewhat difficult to make sure the correct one is used.

Also we have the option of having more bean xml files. one for tests, one for development and then include the right one, but that gives us the hassle of keeping them in sync.

I have also tried using special factory beans to solve this, but that gave me quite large xml files.

And there is another common complaint

There are way to much xml when using Spring!

To the rescue

In Spring 2.5 they introduced autodetection of components in the classpath by scanning for annotated classes. The annotation used for detecting components are called stereotypes, and Spring ships with the follwing out of the box :

  • @Component
  • @Service
  • @Controller
  • @Component

What the component scanner does, is looking for these stereotypes, and registers the classes as beans in the running Spring container. By default it uses the class name as bean id e.g. the class DevelopmentEnvironmentService annotated with the @Service annotation would be registered as a bean with the id developmentEnvironmentService :

@Service
public class DevelopmentEnvironmentService implements EnvironmentService {

    public String getEnvironment() {
        return “development”;
    }
}

Well all good so far. But how to get a hold of this bean, and still keep us free from xml configuration files ?

Let us say we have a service that is supposed to use the EnvironmentService interface to query for the environment we are running in. First we need to create the ConfigurationService and let it be known to the container with the @Service annotation.

@Service
public class ConfigurationService {
}

Then we need to inject it with an instance of the EnvironmentService. To do this, we use the @Autowired annotation. And after we have provided the dependency and implemented the business call the class may now looks like this :

@Service
public class ConfigurationService {
    @Autowired EnvironmentService environmentService;
    public String getEnvironment() {
        return “development”;
    }
}

That’s it. basically all you need to wire up spring applications using annotations instead of xml. ehh. well almost. You may want to add this little snippet to your xml configuration file :

<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-2.5.xsd
    http://www.springframework.org/schema/context
    http://www.springframework.org/schema/context/spring-context-2.5.xsd”>

    <context:component-scan base-package=“no.arktekk.stagedspring”/>
</beans>

With that said, there are other options like JavaConfig, or by creating your application context in Java, setting the correct scanners in code, but hey. the above snippet is kind a good enough for me.

Half way there

Ok now we have taken the xml configuration files out of the equation, but what happens if we have 2 instances of the EnvironmentService interface in the container ?

Well I can tell you… you get this stacktrace :

org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'configurationService': Autowiring of fields failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire field: no.arktekk.stagedspring.service.EnvironmentService no.arktekk.stagedspring.service.ConfigurationService.environmentService; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [no.arktekk.stagedspring.service.EnvironmentService] is defined: expected single matching bean but found 2: [developmentEnvironmentService, productionenvironmentService]
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessAfterInstantiation(AutowiredAnnotationBeanPostProcessor.java:240)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:876)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:437)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory$1.run(AbstractAutowireCapableBeanFactory.java:383)
    at java.security.AccessController.doPrivileged(Native Method)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:353)
    at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:245)
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:169)
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:242)
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:164)
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:400)
    at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:736)
    at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:369)
    at org.springframework.context.support.ClassPathXmlApplicationContext.(ClassPathXmlApplicationContext.java:123)
    at org.springframework.context.support.ClassPathXmlApplicationContext.(ClassPathXmlApplicationContext.java:66)
    at no.arktekk.stagedspring.context.StagedClassPathXmlApplicationContext.(StagedClassPathXmlApplicationContext.java:37)
    at no.arktekk.stagedspring.StageTest.defaultStageResolve(StageTest.java:38)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:585)
    at org.junit.internal.runners.TestMethod.invoke(TestMethod.java:59)
    at org.junit.internal.runners.MethodRoadie.runTestMethod(MethodRoadie.java:98)
    at org.junit.internal.runners.MethodRoadie$2.run(MethodRoadie.java:79)
    at org.junit.internal.runners.MethodRoadie.runBeforesThenTestThenAfters(MethodRoadie.java:87)
    at org.junit.internal.runners.MethodRoadie.runTest(MethodRoadie.java:77)
    at org.junit.internal.runners.MethodRoadie.run(MethodRoadie.java:42)
    at org.junit.internal.runners.JUnit4ClassRunner.invokeTestMethod(JUnit4ClassRunner.java:88)
    at org.junit.internal.runners.JUnit4ClassRunner.runMethods(JUnit4ClassRunner.java:51)
    at org.junit.internal.runners.JUnit4ClassRunner$1.run(JUnit4ClassRunner.java:44)
    at org.junit.internal.runners.ClassRoadie.runUnprotected(ClassRoadie.java:27)
    at org.junit.internal.runners.ClassRoadie.runProtected(ClassRoadie.java:37)
    at org.junit.internal.runners.JUnit4ClassRunner.run(JUnit4ClassRunner.java:42)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:38)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:460)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:673)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:386)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:196)
Caused by: org.springframework.beans.factory.BeanCreationException: Could not autowire field: no.arktekk.stagedspring.service.EnvironmentService no.arktekk.stagedspring.service.ConfigurationService.environmentService; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [no.arktekk.stagedspring.service.EnvironmentService] is defined: expected single matching bean but found 2: [developmentEnvironmentService, productionenvironmentService]
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:433)
    at org.springframework.beans.factory.annotation.InjectionMetadata.injectFields(InjectionMetadata.java:79)
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessAfterInstantiation(AutowiredAnnotationBeanPostProcessor.java:237)
    … 38 more
Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [no.arktekk.stagedspring.service.EnvironmentService] is defined: expected single matching bean but found 2: [developmentEnvironmentService, productionenvironmentService]
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:583)
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:409)
    … 40 more

What have I done to end up here ?

What I did is that I added this class below to my project :

@Service
public class ProductionEnvironmentService implements EnvironmentService {

    public String getEnvironment() {
        return “production”;
    }
}

And then, suddenly I am back to square one. I know this is somewhat a strange and constructed example, but is has been quite common in projects I have been in, that we need different implementations of an interface. Most often for mocking purposes. So
what I think Spring need to have support for is to have a discriminator between stages. And in true Open Source style, I thought.. well if they do not add it. then I have to do it :)

Stage Enabled Spring Contexts

So what I did was to create a little addon to the Spring framework providing the neccecary hooks to make this happen. it consists of just a few classes, and one annotation.

@Stage annotation

First, the @Stage annotation. This annotation serves as the discriminator, and can be registered on types. It has a String value, and defines 3 default stages :

  • Stage.DEVELOPMENT
  • Stage.TEST
  • Stage.PRODUCTION

When this annotation is present on a Java class, it tells the new stage enabled bean factory which stage this particular class should apply to.

StagedListableBeanFactory

This is a spring bean factory that when autowiring is happening, finds all the candidate classes, checks if they have a @Stage annotation and if there are more than one candidate, select the one that have the correct stage set and gives the reference back to the running application context.

Application Context

There are 2 application contexts supplied in the 1.0 version of Staged Enabled Spring Contexts StagedClassPathXmlContext and StagedXmlWebApplicationContext. To enable stage detection in spring you will have to use one of these contexts

StagedClassPathXmlContext

Used when a set of xml based configuration file is used to assemble a context in Java code. e.g. for embedding Spring in a server application, or test cases :

@Test
public void defaultStageResolve() {
  ApplicationContext ctx = new StagedClassPathXmlApplicationContext(“classpath:applicationContext.xml”);
  ConfigurationService configurationService = (ConfigurationService) ctx.getBean(“configurationService”);
  assertEquals(Stage.PRODUCTION, configurationService.getRunningEnvironment());
}
StagedXmlWebApplicationContext

Used when you are creating a web application. To enable this context instead of the default spring context, you will need to set a context param in you web application web.xml file :

  <context-param>
    <param-name>contextClass</param-name>
    <param-value>no.arktekk.stagedspring.context.StagedXmlWebApplicationContext</param-value>
  </context-param>

Finally, we need to know what environment we are actually running in, and that is done with a configurable StageResolver strategy.

StageResolver

This is an interface that you could use to tell the stage enabled what environment we are running in. A default strategy is supplied, and it uses simply a system property to resolve the environment, defaulting to Stage.PRODUCTION. Of course there is nothing keeping you to supply your own environment check, by simply implementing that interface and register it as a bean in the context. The bean factory will automatically choose the one supplied by you if found.

Putting it all together

Then I have shown how to use the Stage Enabled Spring Contexts project, and it is time to summarize a little :

  1. Enable the Spring component scanner in your bean xml configuration file
  2. Annotate you classes with Spring stereotypes to make them discoverable
  3. Instanciate the application context using the StagedClassPathXmlApplicationContext or StagedXmlWebApplicationContext
  4. Annotate the classes you want to be stage aware with the @Stage annotation as in the example below
  5. (optionally) supply your own StageResolver strategy
@Service
@Stage(Stage.PRODUCTION)
public class ProductionEnvironmentService implements EnvironmentService {

    public String getEnvironment() {
        return “production”;
    }
}
@Service
@Stage(Stage.DEVELOPMENT)
public class DevelopmentEnvironmentService implements EnvironmentService {

    public String getEnvironment() {
        return “development”;
    }
}

Where to get it

Stage Enabled Spring Contexts is currently only available from my own public Subversion repository at :
http://kaare-nilsen.com/subversion/public/labs/staged-spring

Is it completly finished

The short answer. Nope. But for a 1.0 release I think it is sufficient. What I would like to point out is that it currently does not work well with the @Qualifier annotation, so if you are using it, the stage may not be correctly resolved.
I aim to fix that in a 1.1 release in a short while.

So as the last ting I would say, is that I hope you find it interesting and please drop me questions and suggestions to make it even better.

Comparing groupware

del.icio.us TRACK TOP
Posted on July 19th, 2007 by Kaare Nilsen. Filed in Uncategorized.
2 comments filed

I now have gotten some time available to play with technology again, and I have set out to find the groupware to use in Arktekk.
Since none of us are using windows operating system, exchange is not really an option, so I have created myself a little short list of requirements that I think a good candidate should have (in no particular order).

  • Shared calendars
  • Shared imap folders
  • Mailing lists
  • Good user management preferably LDAP (so that I can also use it with e.g. Subversion)
  • Nice looking web-mail, with good ajaxy touch to it
  • iCal/iSync support (we are all using Mac’s in our company)
  • Able to be deployed on a Linux platform
  • Open Source
  • As cheap as possible :)

Here are the ones I am currently looking into :

  • Open Xchange
  • Scalix
  • Kerio
  • Zimbra
  • eGroupWare
  • OpenGroupware

I will write a small post on each and one of them with the pro’s and con’s, and then at the end say which one of them I found to be best. If there are some other candidates out there I have not mentioned, please drop me a comment so I can test it out

Time to move on

del.icio.us TRACK TOP
Posted on July 16th, 2007 by Kaare Nilsen. Filed in Uncategorized.
No comments yet. Be the first to comment!

After some time in Objectware I have now left this company to co-found Arktekk. We are an Oslo based consulting company with a strong focus on open source based solutions and agile practices. In addition to delivering traditional consulting services, we also perform public and private training sesions.

We started our company the first of june, and thus I should have blogged about this earlier, but we have been so busy writing a 5 days course on agile techniques based on Maven, Continuum, Subversion and Scrum. This training is in held in cooperation with Programutvikling

We are currently four employees and our staff is :

Kaare Nilsen
Kristian Nordal
Krisoffer Moum
Trygve Laugstøl (CEO)

Late night discoveries

del.icio.us TRACK TOP
Posted on March 13th, 2007 by Kaare Nilsen. Filed in fun.
1 comment filed

Who siad taht stitnig up at nghit looikng at Niatnoal Gogarpeihc on the TV is a wtsae of tmie ?

During a commercial brake I stubled across a reference to this : study
The human mind never stops amazing me :)

Faith Based Programming

del.icio.us TRACK TOP
Posted on February 25th, 2007 by Kaare Nilsen. Filed in java.
No comments yet. Be the first to comment!

This coming tuesday I am going to have a talk at a software seminar at Tandberg Telecom here in Oslo. I am very much looking forward to this, since I am going to talk about all my favourite topics.

  • Open Source
  • Lightweight architecture
  • Continous Integration
  • Maven2
  • Testing

And if I am lucky I will throw in some few things about AOP as well :)

Well enough about that. During the research and planning of this talk, I remembered a quote I have been using for a while for describing what in my personal experience as programmer in several projects over the years seems to be the most used programming style. Forget TDD, everyone says they are using it, but few actually are. Enter the realm of….

Faith Based Programming
“I Really do believe it works”
The art of writing software without the need for tests.

Do your project use this principle ?
If you are not sure what your teams are doing, and would like to find out if they are practicing the faith. Look for theese other statements that may indicate followers

  • Well.. It did work on my machine.
  • Funny.. I fixed that bug ages ago
  • Regression….. what ?
  • Clover.. no I am not superstitious
  • c:\.. not a valid unix path ?… strange…

Not far from the truth ?

del.icio.us TRACK TOP
Posted on January 25th, 2007 by Kaare Nilsen. Filed in mac.
1 comment filed

Being a relatively new convert to the mac cult, I (as almost everybody having a mac) truly love my mac, but cannot really shake the feeling of belonging to a religious sect of true believers waiting to be rewarded, not only in the afterlife, but every time there is a Apple special event.
So a when a someone posted this video on mac1.no, I found it to be both very funny, and very to the point on (at the current time actually the only thing) what I do not like with my mac.

Joining bloggers against commons logging

del.icio.us TRACK TOP
Posted on January 24th, 2007 by Kaare Nilsen. Filed in java.
No comments yet. Be the first to comment!

Johannes Brodwall in his blog, commented about commons-logging and his pain with it.

I have had my share of struggles with the damned API, and spent quite a few hours to get it to run well together with a maven-jetty-spring combination (classloading issues basicly). So I cannot do anything else but concur, and join his crusade :)

Did also find some other people out there with similar thoughts

Jonas Boners blog
Ceki Gülcüs blog

and obviously hani have a blog entry complaining on Ceki ;)
but also some complaining on commons-logging

All in all the fun continues.