23 July 2009

SpringFramework/BeanFactory My notebook.

This post is my notebook for programming with the Spring Framework.

(wikipedia)The Spring Framework is an open source application framework for the Java platform. Central to the Spring Framework is its Inversion of Control container, which provides a consistent means of configuring and managing Java objects using callbacks. The container is responsible for managing object lifecycles: creating objects, calling initialization methods, and configuring objects by wiring them together. Objects created by the container are also called Managed Objects or Beans. Typically, the container is configured by loading XML files containing Bean definitions which provide the information required to create the beans.

OK, say you have been asked to write a Java program translating a DNA sequence with a default genetic code. This program will also list all the available genetic codes. As, in this software, the translated sequences should not contain any Proline, we also want to test this fact in our development version. First we need an Interface named spring.Translator :

package spring;
public interface Translator {
/** answers the name of this translator */
public String getName();
/** answers the translation of this DNA sequence */
public String translate(CharSequence sequence);
}
A basic implementation of this interface use an ordered String of amino acids to translate the DNA.
package spring;

public class Translate
implements Translator
{
private String geneticCode;
private String name;

public void setCode(String geneticCode) {
this.geneticCode = geneticCode;
}

public void setName(String name) {
this.name = name;
}

public String getName()
{
return this.name;
}

private int base2index(char c)
{
switch(Character.toLowerCase(c))
{
case 't': return 0;
case 'c': return 1;
case 'a': return 2;
case 'g': return 3;
default: return -1;
}
}

@Override
public String translate(CharSequence sequence) {
StringBuilder b= new StringBuilder(1+sequence.length()/3);
for(int i=0;i+2< sequence.length();i+=3)
{
int base1= base2index(sequence.charAt(i));
int base2= base2index(sequence.charAt(i+1));
int base3= base2index(sequence.charAt(i+2));
if(base1==-1 || base2==-1 || base3==-1)
{
b.append('?');
}
else
{
b.append(this.geneticCode.charAt(base1*16+base2*4+base3));
}
}
return b.toString();
}
}
We also create a class called spring.NoProlineTranslate for our test:
package spring;

public class NoProlineTranslate extends Translate{
@Override
public String translate(CharSequence sequence)
{
String s=super.translate(sequence);
if(s.contains("P")) throw new IllegalArgumentException("Sequence should not contain any Proline");
return s;
}
}
And in a file called beans.xml we define our java beans. Here we define four beans:
  • A Translate object for the standard genetic code
  • A Translate object for the Mitochondrial code
  • An instance of spring.NoProlineTranslate
  • And a java.util.List of two Genetic Codes
  • We also define an alias "defaultcode" for the default genetic code
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:util="http://www.springframework.org/schema/util"
xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-2.5.xsd
http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-2.5.xsd
http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-2.5.xsd" >


<bean id="gencode1" class="spring.Translate">
<property name="name" value="Standard Code"/>
<property name="code" value="FFLLSSSSYY**CC*WLLLLPPPPHHQQRRRRIIIMTTTTNNKKSSRRVVVVAAAADDEEGGGG"/>
</bean>
<bean id="gencode2" class="spring.Translate">
<property name="name" value="Vertebrate Mitochondrial Code"/>
<property name="code" value="FFLLSSSSYY**CCWWLLLLPPPPHHQQRRRRIIMMTTTTNNKKSS**VVVVAAAADDEEGGGG"/>
</bean>
<bean id="gencode3" class="spring.NoProlineTranslate">
<property name="name" value="Vertebrate Mitochondrial Code"/>
<property name="code" value="FFLLSSSSYY**CC*WLLLLPPPPHHQQRRRRIIIMTTTTNNKKSSRRVVVVAAAADDEEGGGG"/>
</bean>

<alias name="gencode1" alias="defaultcode"/>

<util:list id="listOfGenCodes" list-class="java.util.ArrayList">
<ref bean="gencode1"/>
<ref bean="gencode2"/>
</util:list>
</beans>
And here is the program creating each instance
package spring;
import java.util.List;

import org.springframework.beans.factory.BeanFactory;
import org.springframework.context.ApplicationContext;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class SprintTest01
{
public static void main(String[] args)
{
try
{
ApplicationContext context =
new ClassPathXmlApplicationContext("beans.xml");
BeanFactory factory = (BeanFactory) context;

/* list the genetic codes in the list "listOfGenCodes" */
for(Translate translator:(List<Translate>) factory.getBean("listOfGenCodes"))
{
System.out.println("Genetic code available: "+translator.getName());
}
/* translate with the default genetic code defined in beans.xml */
Translate geneticCode=(Translate) factory.getBean("defaultcode");
System.out.println("Default code is \""+ geneticCode.getName()+"\" : "+geneticCode.getClass());
System.out.println(geneticCode.translate(
"ATGGAGAGGCAGAAACGGAAGGCGGACATCGAGAAG"+
"GGGCTGCAGTTCATTCAGTCGACACTACCCCTAAAGCAAGAAGAGTATGAGGCCTTTCTGCTCAAGCTGG"+
"TGCAGAATCTGTTTGCTGAGGGCAATGATCTGTTCCGGGAGAAGGACTATAAGCAGGCTCTGGTGCAGTA"+
"CATGGAAGGGCTGAACGTGGCCGACTACGCTGCCTCTGACCAGGTGGCCCTGCCCCGGGAGCTGCTGTGC"
));
}
catch(Throwable err)
{
err.printStackTrace();
}
}
}

Compiling

mkdir -p build
javac -d build -cp ${SPRINGDIR}/dist/spring.jar -sourcepath src src/spring/*.java
java -cp build:${SPRINGDIR}/dist/spring.jar:${SPRINGDIR}/lib/jakarta-commons/commons-logging.jar spring.SprintTest01

Executing

java -cp build:${SPRINGDIR}/dist/spring.jar:${SPRINGDIR}/lib/jakarta-commons/commons-logging.jar spring.SprintTest01
Jul 23, 2009 3:58:13 PM org.springframework.context.support.AbstractApplicationContext prepareRefresh
INFO: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@1dd46f7: display name [org.springframework.conte
xt.support.ClassPathXmlApplicationContext@1dd46f7]; startup date [Thu Jul 23 15:58:13 CEST 2009]; root of context hierarchy
Jul 23, 2009 3:58:14 PM org.springframework.beans.factory.xml.XmlBeanDefinitionReader loadBeanDefinitions
INFO: Loading XML bean definitions from class path resource [beans.xml]
Jul 23, 2009 3:58:14 PM org.springframework.context.support.AbstractApplicationContext obtainFreshBeanFactory
INFO: Bean factory for application context [org.springframework.context.support.ClassPathXmlApplicationContext@1dd46f7]: org.springf
ramework.beans.factory.support.DefaultListableBeanFactory@1d2fc36
Jul 23, 2009 3:58:14 PM org.springframework.beans.factory.support.DefaultListableBeanFactory preInstantiateSingletons
INFO: Pre-instantiating singletons in org.springframework.beans.factory.support.DefaultListableBeanFactory@1d2fc36: defining beans [
gencode1,gencode2,gencode3,listOfGenCodes]; root of factory hierarchy

Genetic code available: Standard Code
Genetic code available: Vertebrate Mitochondrial Code
Default code is "Standard Code" : class spring.Translate
MERQKRKADIEKGLQFIQSTLPLKQEEYEAFLLKLVQNLFAEGNDLFREKDYKQALVQYMEGLNVADYAASDQVALPRELLC


Ok, and now the test can be run without modifying the code by just changing <alias name="gencode1" alias="defaultcode"/> to <alias name="gencode3" alias="defaultcode"/> in "beans.xml".
java -cp build:${SPRINGDIR}/dist/spring.jar:${SPRINGDIR}/lib/jakarta-commons/commons-logging.jar spring.SprintTest01
Jul 23, 2009 3:58:47 PM org.springframework.context.support.AbstractApplicationContext prepareRefresh
INFO: Refreshing org.springframework.context.support.ClassPathXmlApplicationContext@1dd46f7: display name [org.springframework.conte
xt.support.ClassPathXmlApplicationContext@1dd46f7]; startup date [Thu Jul 23 15:58:47 CEST 2009]; root of context hierarchy
Jul 23, 2009 3:58:47 PM org.springframework.beans.factory.xml.XmlBeanDefinitionReader loadBeanDefinitions
INFO: Loading XML bean definitions from class path resource [beans.xml]
Jul 23, 2009 3:58:47 PM org.springframework.context.support.AbstractApplicationContext obtainFreshBeanFactory
INFO: Bean factory for application context [org.springframework.context.support.ClassPathXmlApplicationContext@1dd46f7]: org.springf
ramework.beans.factory.support.DefaultListableBeanFactory@1d2fc36
Jul 23, 2009 3:58:47 PM org.springframework.beans.factory.support.DefaultListableBeanFactory preInstantiateSingletons
INFO: Pre-instantiating singletons in org.springframework.beans.factory.support.DefaultListableBeanFactory@1d2fc36: defining beans [
gencode1,gencode2,gencode3,listOfGenCodes]; root of factory hierarchy

Genetic code available: Standard Code
Genetic code available: Vertebrate Mitochondrial Code
Default code is "Vertebrate Mitochondrial Code" : class spring.NoProlineTranslate

java.lang.IllegalArgumentException: Sequence should not contains any Proline
at spring.NoProlineTranslate.translate(NoProlineTranslate.java:8)
at spring.SprintTest01.main(SprintTest01.java:25)


That's it.
Pierre

No comments: