{ by david linsin }
Showing posts with label spring. Show all posts
Showing posts with label spring. Show all posts
March 01, 2011
303
This is my last blog post here on blogger.com! You'll find my new thoughts, projects and development ramblings at http://dlinsin.github.com.
I migrated to blogger.com in late 2005 and was always quite happy with it. More than 5 years and exactly 502 posts later it's time to move on to something new.
Subscribe to my new blog feed, check my stuff on github or follow me on Twitter.
January 08, 2010
Spring's ResourceBundleMessageSource
Last week my colleague Marc spent hours trying to figure out why a ResourceBundle wasn't loaded in a Spring based web app we are developing here at Synyx. It turned out to be a broken Unicode representation, which wasn't properly reported by Spring's ResourceBundleMessageSource.
In case you don't know ResourceBundleMessageSource, here's an excerpt of its javadoc:
We are leveraging the basename functionality of ResourceBundleMessageSource in our application, the way it's suggested in the javadoc. It's pretty neat and you should definitely check it out, if you've never used it.
The problem we encountered indicated that the bundle could not be found. This is what we saw in our log statements:
Of course, we tried to fiddle with the classpath, changed the names of the properties files and moved them to different directories in our WAR file - it would only print the above log statement. After hours of trying and failing, Marc discovered an invalid Unicode character representation (something like d\u00Fvid instead of d\u00FCvid) in the ResourceBundle, which wouldn't let ResourceBundle load the damn thing.
So where's the problem with ResourceBundleMessageSource? The problem is that it swallowed the cause of its own MissingResourceException. Here's what Java's good old ResourceBundle class tells you in case of a broken \uxxxx representation:
You can clearly figure out what the problem is and how to solve it. Whereas, with the message of MissingResourceException the least you would expect, is to look for the problem in the properties file itself.
I created a small test case to reproduce the problem and filed a request for improvement. I hope there'll be a fix, so that other people don't have to suffer the same way we did.
In case you don't know ResourceBundleMessageSource, here's an excerpt of its javadoc:
MessageSource implementation that accesses resource bundles using specified basenames. This class relies on the underlying JDK's ResourceBundle implementation, in combination with the JDK's standard message parsing provided by MessageFormat.
We are leveraging the basename functionality of ResourceBundleMessageSource in our application, the way it's suggested in the javadoc. It's pretty neat and you should definitely check it out, if you've never used it.
The problem we encountered indicated that the bundle could not be found. This is what we saw in our log statements:
WARNING: ResourceBundle [broken_messages] not found for MessageSource: Can't find bundle for base name broken_messages, locale en_US
Of course, we tried to fiddle with the classpath, changed the names of the properties files and moved them to different directories in our WAR file - it would only print the above log statement. After hours of trying and failing, Marc discovered an invalid Unicode character representation (something like d\u00Fvid instead of d\u00FCvid) in the ResourceBundle, which wouldn't let ResourceBundle load the damn thing.
So where's the problem with ResourceBundleMessageSource? The problem is that it swallowed the cause of its own MissingResourceException. Here's what Java's good old ResourceBundle class tells you in case of a broken \uxxxx representation:
java.util.MissingResourceException: Can't find bundle for base name broken_messages, locale en_US
...
Caused by: java.lang.IllegalArgumentException: Malformed \uxxxx encoding.
You can clearly figure out what the problem is and how to solve it. Whereas, with the message of MissingResourceException the least you would expect, is to look for the problem in the properties file itself.
I created a small test case to reproduce the problem and filed a request for improvement. I hope there'll be a fix, so that other people don't have to suffer the same way we did.
November 30, 2009
Playing with Spring's RestTemplate
A couple of week ago, I saw a talk on Spring 3.0's MVC REST support. It's quite impressive how simple SpringSource made REST development by applying the proven concepts of the core Spring Framework.
One of those great core concepts is Templates. Spring's Data Access Framework is an example, where templates are used extensively. One of the templates is the JDBCTemplate. It provides a set of predefined methods to access a database, without worrying about Connection management or Exception handling. Templates are a nice way to help you the the job done, without constraining flexibility. The book "Building Spring 2 Enterprise Applications", which I reviewed last year, there's a whole chapter on Data Access and the corresponding Templates.
The RestTemplate is the latest child in the family. Arjen Poutsma from SpringSource wrote a blog entry about it and describes it as follows:
In the before mentioned blog post, Arjen shows how to pull pictures from Flickr, using their REST API, and display them in a JFrame. He uses an XML based approach, whereas I'll show you some code, which handles JSON:
You can see it's quite easy to work with a RestTemplate. You simply create an instance, tell that instance what your expected content is going to be and you are good to go. In this case we expect the request and response to be JSON. Spring is using the Jackson JSON Processor, to automagically map POJOs to JSON and all the way back.
The concept of a MessageConverter is really neat. You can set multiple converters and specify to use a certain converter for certain POJOs. You can also handle multiple content types by setting multiple instances of MessageConverter.
In order to make a REST call with the predefined MessageConverter, you simply use the getForObject method. You pass the url to call, the type the response is supposed to be mapped to and the values to be replaced in the url. The type of the response is actually a wrapper class:
It is necessary since the following JSON response, which is represented in the POJO Issue, needs some kind of holder object:
As you can see, it's really easy to work with Spring's new RestTemplate. These couple of lines are enough to retrieve a JSON or XML response from a REST call. With the Template approach, you have the full flexibility to hook almost every method and tweak it to your needs.
One of those great core concepts is Templates. Spring's Data Access Framework is an example, where templates are used extensively. One of the templates is the JDBCTemplate. It provides a set of predefined methods to access a database, without worrying about Connection management or Exception handling. Templates are a nice way to help you the the job done, without constraining flexibility. The book "Building Spring 2 Enterprise Applications", which I reviewed last year, there's a whole chapter on Data Access and the corresponding Templates.
The RestTemplate is the latest child in the family. Arjen Poutsma from SpringSource wrote a blog entry about it and describes it as follows:
The RestTemplate is the central Spring class for client-side HTTP access. Conceptually, it is very similar to the JdbcTemplate, JmsTemplate, and the various other templates found in the Spring Framework and other portfolio projects. This means, for instance, that the RestTemplate is thread-safe once constructed, and that you can use callbacks to customize its operations.
In the before mentioned blog post, Arjen shows how to pull pictures from Flickr, using their REST API, and display them in a JFrame. He uses an XML based approach, whereas I'll show you some code, which handles JSON:
You can see it's quite easy to work with a RestTemplate. You simply create an instance, tell that instance what your expected content is going to be and you are good to go. In this case we expect the request and response to be JSON. Spring is using the Jackson JSON Processor, to automagically map POJOs to JSON and all the way back.
The concept of a MessageConverter is really neat. You can set multiple converters and specify to use a certain converter for certain POJOs. You can also handle multiple content types by setting multiple instances of MessageConverter.
In order to make a REST call with the predefined MessageConverter, you simply use the getForObject method. You pass the url to call, the type the response is supposed to be mapped to and the values to be replaced in the url. The type of the response is actually a wrapper class:
It is necessary since the following JSON response, which is represented in the POJO Issue, needs some kind of holder object:
As you can see, it's really easy to work with Spring's new RestTemplate. These couple of lines are enough to retrieve a JSON or XML response from a REST call. With the Template approach, you have the full flexibility to hook almost every method and tweak it to your needs.
October 19, 2009
Spring DM with Annotations
A couple of days ago, I implemented a sample application, based on Spring Dynamic Modules (DM) 1.2.0, with its annotation extension. Unfortunately the documentation doesn't contain any sample code, which might cause some unnecessary work, if you are not too familiar with Spring DM.
Spring DM's annotation extension allows you to pull in an OSGi service reference by annotating a setter of a property:
Unfortunately, you don't get rid of the XML configuration completely, but that's not so bad after all, because you still want to let Spring to all your wiring:
In addition to the instantion part, you need to configure a BeanPostProcessor. It tells Spring to handle your methods annotated with @ServiceReference. If you want all your bundles to use annotations, this might get a little tedious. That's why you can configure annotation processing for all bundles, by defining a fragment bundle, which overrides the default configuration of Spring DM's extender:
Unfortunately, the configuration of the fragement bundle is not in the offical documentation.
Now, that you've got a glimpse of how to use annotations with Spring DM and the ways of configuring it, you might ask whether you want to use it or not? For me this boils down to the question, whether you want to have your dependencies in your xml file or in your code?
It's a tricky question and I think annotations only bring real value, if they make your life easier. Let's take a look at Spring's Web MVC for example: before annotations were introduced, you had to implement an interface in order to code a controller and thus you had dependencies on javax.servlet in your controller code. Spring Web MVC's annotation approach still leaves you with the dependency on Spring, but eliminates the javax.servlet dependency.
In addition to that, it improves testability of controller classes significantly, which I think is worth living with the dependency on Spring.
I think, that the features of Spring DM annotations, at least at the moment, are not compelling enough to have dependencies on it in your code. With the right tooling, Spring's XML configuration should be as easy to handle as annotations.
Spring DM's annotation extension allows you to pull in an OSGi service reference by annotating a setter of a property:
Unfortunately, you don't get rid of the XML configuration completely, but that's not so bad after all, because you still want to let Spring to all your wiring:
In addition to the instantion part, you need to configure a BeanPostProcessor. It tells Spring to handle your methods annotated with @ServiceReference. If you want all your bundles to use annotations, this might get a little tedious. That's why you can configure annotation processing for all bundles, by defining a fragment bundle, which overrides the default configuration of Spring DM's extender:
Unfortunately, the configuration of the fragement bundle is not in the offical documentation.
Now, that you've got a glimpse of how to use annotations with Spring DM and the ways of configuring it, you might ask whether you want to use it or not? For me this boils down to the question, whether you want to have your dependencies in your xml file or in your code?
It's a tricky question and I think annotations only bring real value, if they make your life easier. Let's take a look at Spring's Web MVC for example: before annotations were introduced, you had to implement an interface in order to code a controller and thus you had dependencies on javax.servlet in your controller code. Spring Web MVC's annotation approach still leaves you with the dependency on Spring, but eliminates the javax.servlet dependency.
In addition to that, it improves testability of controller classes significantly, which I think is worth living with the dependency on Spring.
I think, that the features of Spring DM annotations, at least at the moment, are not compelling enough to have dependencies on it in your code. With the right tooling, Spring's XML configuration should be as easy to handle as annotations.
October 12, 2009
Book Review Dynamic Modules for OSGi
Apress was kind enough to pass me a copy of this book, which I agreed to review in return.
I have been sitting on Pro Spring Dynamic Modules for Osgi(tm) Service Platforms for a while, although I got a fresh copy right after if was released earlier this year.
One reason for this might be, that after reading the first chapter, it felt like I was reading a manual rather than a book. Personally, I like a little bit more subjectiveness, because it improves the reading experience significantly. The author should spice up the dry material, so you won't get bored that easily. Unfortunately, that's what happened to me - I got bored. However, let's turn the spotlight to the content of the book.
The introduction chapter on OSGi is sufficient to get you up to speed. There are about 60 pages of Spring introduction. However, I think you should at least have some practical experiences with Spring, before digging into Spring Dynamic Modules or even Spring DM Server. It's simply not enough to explain the technicalities, to get someone an understanding of what Spring an its concepts is all about.
There's lot's of code in the book, which you can download and play with. If you like to read code, printed in a book, you are probably gonna like "Pro Spring Dynamic Modules for Osgi". For me, a book is not the preffered media to consume code. I have nothing against small code samples, but having pages over pages full of code, is really confusing and hurts readability.
The manual kind of feeling of the book continues the further you keep reading. Let me give you a concrete example: In chapter 4, called "Spring Dynamic Modules for OSGi", the author explains how the scope attribute of a bean declaration works:
Unfortunately, the how is all there is to the explanation. I expected a real life example of when to use the scope attribute and where it might not be suitable. I do understand, that the book can't go into details all the time, but especially those powerful Spring DM features like scoping, deserve more spotlight. Most of the time, the book stops when it gets interesting and you are left with your own imagination of how to apply that particular feature.
Despite the criticism, I got some neat tips from the book. The author suggests to split the OSGi dependent and traditional Spring configuration to make life easier for testing and mocking. I also gained a lot of knowledge from chapter 6, called "Versioning with OSGi and Spring". The author explains the concepts and implementation of versioning most of the time in a very understandable manner.
Overall, I think Pro Spring Dynamic Modules for Osgi(tm) Service Platforms is a reasonable reference book, with a nice sample application. If you are new to Spring and OSGi, you might have a hard time understanding the use case for those technologies, so I'd suggest to get this book as an addition to some basic reading material.
One reason for this might be, that after reading the first chapter, it felt like I was reading a manual rather than a book. Personally, I like a little bit more subjectiveness, because it improves the reading experience significantly. The author should spice up the dry material, so you won't get bored that easily. Unfortunately, that's what happened to me - I got bored. However, let's turn the spotlight to the content of the book.
The introduction chapter on OSGi is sufficient to get you up to speed. There are about 60 pages of Spring introduction. However, I think you should at least have some practical experiences with Spring, before digging into Spring Dynamic Modules or even Spring DM Server. It's simply not enough to explain the technicalities, to get someone an understanding of what Spring an its concepts is all about.
There's lot's of code in the book, which you can download and play with. If you like to read code, printed in a book, you are probably gonna like "Pro Spring Dynamic Modules for Osgi". For me, a book is not the preffered media to consume code. I have nothing against small code samples, but having pages over pages full of code, is really confusing and hurts readability.
The manual kind of feeling of the book continues the further you keep reading. Let me give you a concrete example: In chapter 4, called "Spring Dynamic Modules for OSGi", the author explains how the scope attribute of a bean declaration works:
Unfortunately, the how is all there is to the explanation. I expected a real life example of when to use the scope attribute and where it might not be suitable. I do understand, that the book can't go into details all the time, but especially those powerful Spring DM features like scoping, deserve more spotlight. Most of the time, the book stops when it gets interesting and you are left with your own imagination of how to apply that particular feature.
Despite the criticism, I got some neat tips from the book. The author suggests to split the OSGi dependent and traditional Spring configuration to make life easier for testing and mocking. I also gained a lot of knowledge from chapter 6, called "Versioning with OSGi and Spring". The author explains the concepts and implementation of versioning most of the time in a very understandable manner.
Overall, I think Pro Spring Dynamic Modules for Osgi(tm) Service Platforms is a reasonable reference book, with a nice sample application. If you are new to Spring and OSGi, you might have a hard time understanding the use case for those technologies, so I'd suggest to get this book as an addition to some basic reading material.
September 22, 2009
Spring DM Web Extender Problems
In my current project, I'm evaluating moving a large and very old code base to OSGi. Part of that is getting the the development team on board. I'm trying to point out, how much you can benefit from designing your application with OSGi in mind and the advantages you can have, running your application in an OSGi container.
I created some sample code with the help of the book "Pro Spring Dynamic Modules for Osgi(tm) Service Platforms" to highlight some of my OSGi presentation bulletpoints. One of the samples is running Tomcat inside of Equinox together with Spring Dynamic Modules. Although the sample is really simple and I sticked to the steps in the book precisely, Equinox spit out the following Exception:
After various failed attempts to google for a solution, I decided to consult the book again. Although, I thought I sticked to the steps closely, I missed an important point: start levels.
I missed the fact that there is a start order in my Equinox run configuration. The bundles, which are in charge of bootstrapping Tomcat, need to be activated in special order, otherwise the previously mentioned Exception is raised. In particular the following bundles need to start in order:
In "Pro Spring Dynamic Modules for Osgi" the config only orders the bundles and doesn't add any explicit start levels. However, I still ran into the same Exception from time to time, depending on other bundles I loaded. I put explicit start levels in my run configuration to solve those problems.
I created some sample code with the help of the book "Pro Spring Dynamic Modules for Osgi(tm) Service Platforms" to highlight some of my OSGi presentation bulletpoints. One of the samples is running Tomcat inside of Equinox together with Spring Dynamic Modules. Although the sample is really simple and I sticked to the steps in the book precisely, Equinox spit out the following Exception:
After various failed attempts to google for a solution, I decided to consult the book again. Although, I thought I sticked to the steps closely, I missed an important point: start levels.
A start level is simply a non-negative integer value. The Framework has an ‘active start level’ that is used to decide which bundles can be started. Bundles themselves have an associated ‘bundle start level’ which is used to determine when a bundle is started. The bundles at a given start level will all have their start method completely executed before any bundles at a higher level are started. When booted, the Framework monotonically goes through each start level and starts relevant bundles (all the way until the active start level is met).
...
In the end, start levels are there to simply determine the start order of bundles.
I missed the fact that there is a start order in my Equinox run configuration. The bundles, which are in charge of bootstrapping Tomcat, need to be activated in special order, otherwise the previously mentioned Exception is raised. In particular the following bundles need to start in order:
... org.springframework.osgi.catalina.osgi@3:start, \ org.springframework.osgi.catalina.start.osgi@3:start, \ org.springframework.bundle.osgi.web.extender@4:start, \ ...
In "Pro Spring Dynamic Modules for Osgi" the config only orders the bundles and doesn't add any explicit start levels. However, I still ran into the same Exception from time to time, depending on other bundles I loaded. I put explicit start levels in my run configuration to solve those problems.
June 29, 2009
Wrapping-up Jazoon09
I was attending Jazoon09 in Zurich, Switzerland last week. As with springOne 2009, I wasn't really satisfied with this content of the conference. The problem was, that there were only a few really good speakers and thus only a couple of great talks. The keynotes were average, only Adrian Colyer's presentation on the last day was standing out. Even James Gosling's presentation or Danny Cowards talk were both not that exciting.
However, instead of telling you what sucked, I rather want to highlight, that the organization of the conference was great! The food was really good! There was an vegetarian alternative every day and the coffee was delicious. Jazoon took place in a movie theater, just like Devoxx, thus it was easy to get there by train and the seats were nice and comfy. Kudos to the organizers.
There were a couple of great talks I want to highlight: Neal Ford's "Smithying in the 21st Century" as well as Ed Burns' "Secrets of the Rockstar Programmers" were really awesome and I can only commend listening to them, in case they come up on the schedule of another conference.
I'm not too sure if I'll come back to Jazoon next year, although I think it could be a really cool conference and a great alternative to Devoxx, which takes place in Antwerp.
May 04, 2009
springOne 2009 recap
The most outstanding announcement for me was something called "Spring Roo". According to Ben Alex, it's
...a sophisticated round-tripping code generator that makes it quicker and easier than you've ever imagined to create and evolve Spring applications
You can leverage it to create applications with technologies like Spring, JPA and Spring MVC, using a shell-based approach with tab completion, hints and great default behavior. A big part of the opening keynote was dedicated to Spring Roo, where Ben live coded a simple web-based voting application. You can already download an alpha release and check it out.
Overall the keynotes were the most valuable sessions for me. Most of the others had a rather introductory character and were quite basic, which I think should not be the focus of such a conference. I'm a little disappointed, but nevertheless, I hope next year will be better.
April 21, 2009
SpringOne 2009
Unlike the last 2 years, the conference is not going to be held in Antwerp, Belgium - instead it'll take place in Amsterdam, Netherlands. I think it's a nice change. I've never been to Amsterdam before and I even added a couple of days to my trip to explore the city with my wife.
Looking at the first day, there's a bunch of really interesting sessions like "Performance Tuning for Apache Tomcat", "New Features in Spring 3.0" or "Extreme Productivity in Application Development".
I'm really excited to feel some Spring spirit again...
March 19, 2009
Final or Not Final?
I recently implemented an extension to Spring's HsqlSequenceMaxValueIncrementer. When I digged into the Spring source code of HsqlSequenceMaxValueIncrementer and its ancestors, I noticed something astonishing: almost all methods are public or at least protected and there is not one final class or field. Everything is extensible and somewhat accessible.
Let's take a look at AbstractSequenceMaxValueIncrementer, one of the parent classes of HsqlSequenceMaxValueIncrementer:
Since I was extending the framework, the degree of flexibility was great for me. All I had to do was override a few methods to plug in my code and that's it.
If everything is accessible, the way it is in case of AbstractDataFieldMaxValueIncrementer, users can do almost everything they want with the classes you published. They can override all the methods and subclass each and every class. As shown above, that was obviously intended. The class wouldn't be abstract and have public/protected methods if it wasn't intended to be subclassed.
After reading the book Practical API Design, which preaches backward compatibility, I wonder how you would be able to evolve such a class? Let's say you wanted to extend the meaning of the field incrementerName. It should convey more information than simply the name of the sequence. Therefore you'd create a class IncrementerName, which replaced the String field. With this simple change, you'd break all the clients relying on the field incrementerName. I know this example might seem far-fetched, but I think you get the idea.
Another thing that caught my eye, when looking at AbstractDataFieldMaxValueIncrementer, is the field dataSource. It is basically a public field and I'm not quite sure why. Is it really necessary to replace the DataSource after you initialized the bean? Do you really want everyone to screw with the DataSource?
If it was for me, I would have answered those questions with a plain "No!". Why not implement AbstractDataFieldMaxValueIncrementer as follows:
I think this would not restrict the use of the class, except that you have to use constructor injection, but that's a different story. It would, however, restrict the use of the fields dataSource and incrementerName. I think those fields should be immutable anyways, since I cannot think of a reason why you would want to change them during the life-cycle of the object. I know dataSource isn't truly immutable, but the access is limited to subclasses, which should confine the wrong usage.
That leaves me with the question, why the authors of AbstractDataFieldMaxValueIncrementer didn't go that route? I think it's simply a design decision of Spring authors, to be as open and extensible as possible. They have InitializingBean and @Required to enforce necessary dependencies, which work quite well. I guess they push the responsibility of handling immutables with care to the developer, which is reasonable, but in my opinion rather risky. I think using final in such cases is an easy way to remove unnecessary sources of errors.
I'm not quite sure which approach is the best here. Does it all boil down to "it depends"? Or is all a matter of taste? I don't think so. In my day to day coding, I tend to consciously follow the advices of Effective Java, which favors immutability and limiting accessibility. However, looking at Spring's source code is a truly inspiring. They are doing a phenomenal job of keeping it stable, considering how open and extensible their classes are.
Let's take a look at AbstractSequenceMaxValueIncrementer, one of the parent classes of HsqlSequenceMaxValueIncrementer:
public abstract class AbstractDataFieldMaxValueIncrementer implements DataFieldMaxValueIncrementer, InitializingBean {
private DataSource dataSource;
private String incrementerName;
public AbstractDataFieldMaxValueIncrementer() {
}
public AbstractDataFieldMaxValueIncrementer(DataSource dataSource, String incrementerName) {
Assert.notNull(dataSource, "DataSource must not be null");
Assert.notNull(incrementerName, "Incrementer name must not be null");
this.dataSource = dataSource;
this.incrementerName = incrementerName;
}
public void setDataSource(DataSource dataSource) {
this.dataSource = dataSource;
}
public DataSource getDataSource() {
return this.dataSource;
}
public void setIncrementerName(String incrementerName) {
this.incrementerName = incrementerName;
}
public String getIncrementerName() {
return this.incrementerName;
}
public void afterPropertiesSet() {
if (this.dataSource == null) {
throw new IllegalArgumentException("Property 'dataSource' is required");
}
if (this.incrementerName == null) {
throw new IllegalArgumentException("Property 'incrementerName' is required");
}
}
public int nextIntValue() throws DataAccessException {
return (int) getNextKey();
}
public long nextLongValue() throws DataAccessException {
return getNextKey();
}
public String nextStringValue() throws DataAccessException {
// removed implementation for brevity
}
protected abstract long getNextKey();
}
Since I was extending the framework, the degree of flexibility was great for me. All I had to do was override a few methods to plug in my code and that's it.
If everything is accessible, the way it is in case of AbstractDataFieldMaxValueIncrementer, users can do almost everything they want with the classes you published. They can override all the methods and subclass each and every class. As shown above, that was obviously intended. The class wouldn't be abstract and have public/protected methods if it wasn't intended to be subclassed.
After reading the book Practical API Design, which preaches backward compatibility, I wonder how you would be able to evolve such a class? Let's say you wanted to extend the meaning of the field incrementerName. It should convey more information than simply the name of the sequence. Therefore you'd create a class IncrementerName, which replaced the String field. With this simple change, you'd break all the clients relying on the field incrementerName. I know this example might seem far-fetched, but I think you get the idea.
Another thing that caught my eye, when looking at AbstractDataFieldMaxValueIncrementer, is the field dataSource. It is basically a public field and I'm not quite sure why. Is it really necessary to replace the DataSource after you initialized the bean? Do you really want everyone to screw with the DataSource?
If it was for me, I would have answered those questions with a plain "No!". Why not implement AbstractDataFieldMaxValueIncrementer as follows:
public abstract class AbstractDataFieldMaxValueIncrementer implements DataFieldMaxValueIncrementer {
private final DataSource dataSource;
private final String incrementerName;
public AbstractDataFieldMaxValueIncrementer(DataSource dataSource, String incrementerName) {
Assert.notNull(dataSource, "DataSource must not be null");
Assert.notNull(incrementerName, "Incrementer name must not be null");
this.dataSource = dataSource;
this.incrementerName = incrementerName;
}
protected DataSource getDataSource() {
return this.dataSource;
}
public String getIncrementerName() {
return this.incrementerName;
}
public int nextIntValue() throws DataAccessException {
return (int) getNextKey();
}
public long nextLongValue() throws DataAccessException {
return getNextKey();
}
public String nextStringValue() throws DataAccessException {
// removed implementation for brevity
}
protected abstract long getNextKey();
}
I think this would not restrict the use of the class, except that you have to use constructor injection, but that's a different story. It would, however, restrict the use of the fields dataSource and incrementerName. I think those fields should be immutable anyways, since I cannot think of a reason why you would want to change them during the life-cycle of the object. I know dataSource isn't truly immutable, but the access is limited to subclasses, which should confine the wrong usage.
That leaves me with the question, why the authors of AbstractDataFieldMaxValueIncrementer didn't go that route? I think it's simply a design decision of Spring authors, to be as open and extensible as possible. They have InitializingBean and @Required to enforce necessary dependencies, which work quite well. I guess they push the responsibility of handling immutables with care to the developer, which is reasonable, but in my opinion rather risky. I think using final in such cases is an easy way to remove unnecessary sources of errors.
I'm not quite sure which approach is the best here. Does it all boil down to "it depends"? Or is all a matter of taste? I don't think so. In my day to day coding, I tend to consciously follow the advices of Effective Java, which favors immutability and limiting accessibility. However, looking at Spring's source code is a truly inspiring. They are doing a phenomenal job of keeping it stable, considering how open and extensible their classes are.
February 16, 2009
Spring Integration in 10 minutes
SpringSource's Mark Fisher posted a tutorial on Spring Integration a couple of days ago. I followed the tutorial step-by-step and thought I'd share my IDEA project with you. I also added a maven POM file so you can also import it into Eclipse or use the command line.
NOTE: Over the next few weeks, I'm moving my feed from feedburner back to blogspot so please subscribe to http://dlinsin.blogspot.com/feeds/posts/default/ instead!
NOTE: Over the next few weeks, I'm moving my feed from feedburner back to blogspot so please subscribe to http://dlinsin.blogspot.com/feeds/posts/default/ instead!
November 10, 2008
Eclipse RCP and Inversion of Control
I guess you all heard of Dependency Injection (DI) and Inversion of Control (IoC). To refresh our memories, Wikipedia defines the two terms as follows:
For me those two terms have always described the way a framework is wiring your components at startup, no matter if that framework is called PicoContainer, Spring or Guice. It is in control of creating and passing the dependencies to your application, in order for it to run.
The wiring is usually done in the main method of your application or a ContextListener, in case of a webapp. If you are using Spring, for example, you would create an ApplicationContext, which bootstraps the dependencies of your entry point class:
One of the reasons I like Spring and this particular DI / IoC notion, is that there is no need for creating instance with the new operator. After the initial setup your application is good to go and your dependencies are fully initialized. In webapps this usually works like a charm. In desktop applications, especially if you are using an application framework, it's a little different.
I'm working on a Eclipse RCP desktop app at the moment and combining it with my notion of DI / IoC turns out to be virtually impossible. One of the reasons is OSGi, the underlying technology of the Eclipse RCP. The nature of OSGi is highly dynamic. Bundles and thus dependencies can come and go at runtime. That means the traditional wiring approach isn't suitable. In my project, we are using Spring Dynamic Modules, which somewhat combines the static nature of wiring with OSGi's dynamic capabilities.
The probably most important reason why my understanding of DI /IoC isn't working in our application, is the fact that we are trying to mix Spring's life-cycle and IoC capabilities with that of Eclipse. The Rich Application Platform has its own notion of wiring and if you base your application on it, you must comply with that. The way Eclipse wires its dependencies is similar to that of Spring, but not compatible after all.
Instead of having dependencies injected by Spring in a inversion of control way, we are basically left with the good old Service Locator.
Although there are solutions, bridging the gap between Eclipse and Spring, there's nothing supported "officially". That was the reason for us to go the Service Locator route, although to me it doesn't feel right. There are pros and cons when it comes to the Service Locator pattern. One of the most compelling arguments against it, is the hard reference to the locator instance in your code. It is a necessary evil in order to get a hold of your dependencies. This pain point was kind of mitigated for me, when I read that Netbeans is using it in their code base to lookup dependencies as well.
The solution we came up with, is a static ApplicationContext instance in the Activator class of each OSGi bundle. It serves as a location to grab the dependencies needed in the contained environment of a bundle. The ApplicationContext is configured using the usual Spring XML-configuration, together with Spring Dynamic Modules. An alternative approach, that we considered as well, is to use the OSGi API to locate your services. It limits the dependencies to Spring, since you don't need a reference to the ApplicationContext. If you are planning to replace Spring with anything else, you might consider taking that approach.
Although this works very well, it doesn't fit my understanding of DI and IoC. I want my dependencies to be injected, wherever I need them. I don't want to ask for them myself. Martin Fowler mentions in his article, that using the black magic of IoC, in contrast to the ServiceLocator pattern, makes your code harder to understand and debug. I can think of situation where it's harder to debug your code, but I cannot imagine how your code would be harder to grasp. I think, if you clearly state the dependencies of your class, it is easier to comprehend and to test. The fact that Spring does some magic and injects the dependencies for you, doesn't harm understandability at all.
Trying to get the best of both worlds - Eclipse RCP and Spring - probably means to compromise about doing DI using a Service Locator instead of doing DI with IoC. But isn't everything we do in software development a compromise?
Dependency Injection refers to the process of supplying an external dependency to a software component. It is a specific form of inversion of control where the concern being inverted is the process of obtaining the needed dependency.
Inversion of control, is an abstract principle describing an aspect of some software architecture designs in which the flow of control of a system is inverted in comparison to the traditional architecture of software libraries.
For me those two terms have always described the way a framework is wiring your components at startup, no matter if that framework is called PicoContainer, Spring or Guice. It is in control of creating and passing the dependencies to your application, in order for it to run.
The wiring is usually done in the main method of your application or a ContextListener, in case of a webapp. If you are using Spring, for example, you would create an ApplicationContext, which bootstraps the dependencies of your entry point class:
ApplicationContext ctx = new ClassPathXmlApplicationContext("conf/appContext.xml");
Service s = ctx.getBean("calculationService"); // wires all dependencies
s.start(); // everything is setup already
One of the reasons I like Spring and this particular DI / IoC notion, is that there is no need for creating instance with the new operator. After the initial setup your application is good to go and your dependencies are fully initialized. In webapps this usually works like a charm. In desktop applications, especially if you are using an application framework, it's a little different.
I'm working on a Eclipse RCP desktop app at the moment and combining it with my notion of DI / IoC turns out to be virtually impossible. One of the reasons is OSGi, the underlying technology of the Eclipse RCP. The nature of OSGi is highly dynamic. Bundles and thus dependencies can come and go at runtime. That means the traditional wiring approach isn't suitable. In my project, we are using Spring Dynamic Modules, which somewhat combines the static nature of wiring with OSGi's dynamic capabilities.
The probably most important reason why my understanding of DI /IoC isn't working in our application, is the fact that we are trying to mix Spring's life-cycle and IoC capabilities with that of Eclipse. The Rich Application Platform has its own notion of wiring and if you base your application on it, you must comply with that. The way Eclipse wires its dependencies is similar to that of Spring, but not compatible after all.
Instead of having dependencies injected by Spring in a inversion of control way, we are basically left with the good old Service Locator.
The fundamental choice is between Service Locator and Dependency Injection...is about how that implementation is provided to the application class. With service locator the application class asks for it explicitly by a message to the locator. With injection there is no explicit request, the service appears in the application class - hence the inversion of control.
Although there are solutions, bridging the gap between Eclipse and Spring, there's nothing supported "officially". That was the reason for us to go the Service Locator route, although to me it doesn't feel right. There are pros and cons when it comes to the Service Locator pattern. One of the most compelling arguments against it, is the hard reference to the locator instance in your code. It is a necessary evil in order to get a hold of your dependencies. This pain point was kind of mitigated for me, when I read that Netbeans is using it in their code base to lookup dependencies as well.
The solution we came up with, is a static ApplicationContext instance in the Activator class of each OSGi bundle. It serves as a location to grab the dependencies needed in the contained environment of a bundle. The ApplicationContext is configured using the usual Spring XML-configuration, together with Spring Dynamic Modules. An alternative approach, that we considered as well, is to use the OSGi API to locate your services. It limits the dependencies to Spring, since you don't need a reference to the ApplicationContext. If you are planning to replace Spring with anything else, you might consider taking that approach.
Although this works very well, it doesn't fit my understanding of DI and IoC. I want my dependencies to be injected, wherever I need them. I don't want to ask for them myself. Martin Fowler mentions in his article, that using the black magic of IoC, in contrast to the ServiceLocator pattern, makes your code harder to understand and debug. I can think of situation where it's harder to debug your code, but I cannot imagine how your code would be harder to grasp. I think, if you clearly state the dependencies of your class, it is easier to comprehend and to test. The fact that Spring does some magic and injects the dependencies for you, doesn't harm understandability at all.
Trying to get the best of both worlds - Eclipse RCP and Spring - probably means to compromise about doing DI using a Service Locator instead of doing DI with IoC. But isn't everything we do in software development a compromise?
July 21, 2008
Configuration Notations
I've been using XML as a configuration notation since I've started doing web development. It's a basic building block when it comes to Java EE. Unfortunately I think it's also one of the most common source of errors, especially because there's no compiler which tells you what's wrong. How many times have you deployed your web app in a Java EE container, only to find out, that you have a typo in your web.xml. One advantage of XML, in my opinion, is readability. If you have a configuration file, XML does a decent job in suggesting what you are actually trying to configure and how it relates to your code. I do admit that it can become very verbose very quickly, but using XML namespaces, like the Springframework, you can keep it under control - at least to a certain extend.
I'm currently working on a project which leverages the Springframework. We are using the container to manage dependencies, Dynamic Modules to leverage OSGi and a lot of other stuff which sometimes makes life easier. Spring's default configuration option is XML. So if you want the Spring container to know about your class you'd write something like the following:
Of course that's not the whole story, there's lot's of namespace configuration and all the other XML stuff in your configuration file. Basically every class you want Spring to know about, needs a complement in your configuration. It quickly gets more and more, e.g. if you add transaction management or logging. In short: your XML configuration virtually outgrows!
I said this before, but here it is again: I like Spring's XML configuration and I believe it's all a question of proper tooling. If you have a tool like IntelliJ IDEA, it's a lot easier to handle your Spring configuration.
There's another configuration notation, which has been around for a while: properties files. They contain simple key value pairs:
In my last project, we used properties files excessively to configure global variables, which are set at startup of the Java EE container for the lifetime of the JVM. Properties files are also the standard way of internationalizing your application. For each language you can provide a file which contains keys that are used throughout your application and values, containing the translated messages. The keys are being substituted at runtime with the appropriate values, depending on the currently chosen language. As with XML, there is no compiler warning or static check, which could tell you that you haven't configured your properties file correctly. It's generally a good idea to add a null check before accessing a property, since it can lead to nasty NPEs if it's undefined. In my opinion readability of properties files can't keep up with XML. Usually your files are sprinkled with comments, which indicate where and how the properties are used. That doesn't really scale and comments are not always the best way of enforcing a contract.
Another problem with properties files is encoding. As soon as they contain none Latin-1 characters, you need to do extra work more work to avoid problems. Usually you shouldn't have those encoding problems with XML. Proper tooling is a real problem when it comes to management of properties files. I haven't found a really good tool, which conducts some kind of check if my code and properties files are in-sync. I have to plug IntelliJ again here. They are doing a somewhat reasonable job of managing your properties.
One of the most exotic configuration notation, at least in my opinion, is JSON. Yes, I know! You are probably raising your eyebrows right now, like I did the first time I read about it. JSON is used as the configuration notation of SpringSource's Application Platform - S2AP. You can among other stuff configure logging using JSON:
As probably most of you, I've used JSON only for web development. I think its most common application is calling server-side code from JavaScript. Using it for configuration is an interesting idea, though. When looking at the example above, I think the readability is quite reasonable. The hierarchical structure, similar to XML, makes it easy to figure out what you are trying to configure. There are frameworks out there, which are converting JSON to Java and vice versa, so there's no need to write a parser yourself. Like with the perviously mentioned notations, catching mistakes before deployment is rather limited, since there is no compilation step involved. As for tooling, every decent IDE supports JavaScript nowadays and most of the time that includes JSON. It shouldn't be a problem, getting some tool support when editing JSON snippets.
Comparing these different configuration notations rather subjectively, there is no clear winner for me. The only real difference is proliferation. Despite its somewhat bad reputation, XML is clearly the most widely used configuration notation, directly followed by properties files. JSON is kind of the "new kid on the block", because I've never seen it being used for configuration, before S2AP.
Besides its wide usage and ubiquity, XML has DTD and namespaces, which I believe can eliminate the two major downsides: verboseness and misconfiguration. The strong tool support, which came with the proliferation, can help to handle spelling errors and management of large numbers of XML files. I think working with XML can be quite painless today, if you have the right tools.
I'm currently working on a project which leverages the Springframework. We are using the container to manage dependencies, Dynamic Modules to leverage OSGi and a lot of other stuff which sometimes makes life easier. Spring's default configuration option is XML. So if you want the Spring container to know about your class you'd write something like the following:
<bean id="person" class="de.linsin.sample.spring.contracts.PersonImpl"/>Of course that's not the whole story, there's lot's of namespace configuration and all the other XML stuff in your configuration file. Basically every class you want Spring to know about, needs a complement in your configuration. It quickly gets more and more, e.g. if you add transaction management or logging. In short: your XML configuration virtually outgrows!
I said this before, but here it is again: I like Spring's XML configuration and I believe it's all a question of proper tooling. If you have a tool like IntelliJ IDEA, it's a lot easier to handle your Spring configuration.
There's another configuration notation, which has been around for a while: properties files. They contain simple key value pairs:
authentication.factory=de.linsin.sample.factory.LDAPAuthFactory
admin.email=dlinsin@gmail.comIn my last project, we used properties files excessively to configure global variables, which are set at startup of the Java EE container for the lifetime of the JVM. Properties files are also the standard way of internationalizing your application. For each language you can provide a file which contains keys that are used throughout your application and values, containing the translated messages. The keys are being substituted at runtime with the appropriate values, depending on the currently chosen language. As with XML, there is no compiler warning or static check, which could tell you that you haven't configured your properties file correctly. It's generally a good idea to add a null check before accessing a property, since it can lead to nasty NPEs if it's undefined. In my opinion readability of properties files can't keep up with XML. Usually your files are sprinkled with comments, which indicate where and how the properties are used. That doesn't really scale and comments are not always the best way of enforcing a contract.
Another problem with properties files is encoding. As soon as they contain none Latin-1 characters, you need to do extra work more work to avoid problems. Usually you shouldn't have those encoding problems with XML. Proper tooling is a real problem when it comes to management of properties files. I haven't found a really good tool, which conducts some kind of check if my code and properties files are in-sync. I have to plug IntelliJ again here. They are doing a somewhat reasonable job of managing your properties.
One of the most exotic configuration notation, at least in my opinion, is JSON. Yes, I know! You are probably raising your eyebrows right now, like I did the first time I read about it. JSON is used as the configuration notation of SpringSource's Application Platform - S2AP. You can among other stuff configure logging using JSON:
"trace": {
"directory": "serviceability/trace",
"defaultLevel": "info",
"specificLevels": {
"com.foo.*" : "verbose",
"com.foo.UnimportantClass" : "info",
"com.bar.ImportantClass" : "verbose"
}
}As probably most of you, I've used JSON only for web development. I think its most common application is calling server-side code from JavaScript. Using it for configuration is an interesting idea, though. When looking at the example above, I think the readability is quite reasonable. The hierarchical structure, similar to XML, makes it easy to figure out what you are trying to configure. There are frameworks out there, which are converting JSON to Java and vice versa, so there's no need to write a parser yourself. Like with the perviously mentioned notations, catching mistakes before deployment is rather limited, since there is no compilation step involved. As for tooling, every decent IDE supports JavaScript nowadays and most of the time that includes JSON. It shouldn't be a problem, getting some tool support when editing JSON snippets.
Comparing these different configuration notations rather subjectively, there is no clear winner for me. The only real difference is proliferation. Despite its somewhat bad reputation, XML is clearly the most widely used configuration notation, directly followed by properties files. JSON is kind of the "new kid on the block", because I've never seen it being used for configuration, before S2AP.
Besides its wide usage and ubiquity, XML has DTD and namespaces, which I believe can eliminate the two major downsides: verboseness and misconfiguration. The strong tool support, which came with the proliferation, can help to handle spelling errors and management of large numbers of XML files. I think working with XML can be quite painless today, if you have the right tools.
June 13, 2008
SpringOne08.exit();
The last 2 days I attended SpringOne08. It was even better than last year, although it was only 2 instead of 3 days. I met a couple of nice fellow developers and learned quite a bit about the Spring Framework.
I'm not gonna summarize any sessions here since you can already find blogs out there already covering a lot of sessions. I just like to point out, that there was one ubiquitos topic: OSGi. SpringSource is heavily backing OSGi, with Spring Dynamic Modules as well as their new product SpringSource Application Platform (S2AP). It's a topic you won't get passed if you are developing enterprise applications.
From a technical point of view I find this very interesting. I wonder how that will affect the application server market. I guess it's still early for predications, but you should definitely keep a close eye on S2AP.
I'm not gonna summarize any sessions here since you can already find blogs out there already covering a lot of sessions. I just like to point out, that there was one ubiquitos topic: OSGi. SpringSource is heavily backing OSGi, with Spring Dynamic Modules as well as their new product SpringSource Application Platform (S2AP). It's a topic you won't get passed if you are developing enterprise applications.
From a technical point of view I find this very interesting. I wonder how that will affect the application server market. I guess it's still early for predications, but you should definitely keep a close eye on S2AP.
June 07, 2008
SpringOne 2008 coming
SpringOne 2008 is coming next week and taking place in Antwerp, Belgium again. I was there last year and I can only recommend conferences held by the BeJug. They are usually well organized and you get the chance to talk to a lot of fellow developers.
I checked out the conference schedule and unlike last year, there is a lot more Spring stuff covered. All the sessions are packed with topics on the different parts of the Spring Portfolio. A lot of talks are covering OSGi and the recently announced Spring Application Platform. Those are exactly the topics I'm interested in, because we use some of them on my current project. Last year there were a lot of general sessions, e.g. Eric Evans was speaking on Domain Driven Design.
There is one thing, that never seems to change though: the sessions I'm interested in are always taking place at the exact same time.
I checked out the conference schedule and unlike last year, there is a lot more Spring stuff covered. All the sessions are packed with topics on the different parts of the Spring Portfolio. A lot of talks are covering OSGi and the recently announced Spring Application Platform. Those are exactly the topics I'm interested in, because we use some of them on my current project. Last year there were a lot of general sessions, e.g. Eric Evans was speaking on Domain Driven Design.
There is one thing, that never seems to change though: the sessions I'm interested in are always taking place at the exact same time.
May 16, 2008
Book Review: Building Spring 2 Enterprise Applications
Apress was kind enough to pass me a copy of this book, which I agreed to review in return.
Building Spring 2 Enterprise Applications is the second book of an Apress series about the Springframework. It cover topics like Aspect Oriented Programming (AOP), persistence and transaction management, as well as different view technologies all related to Spring.
Each book of the series addresses a different user level. Although this one is meant for an intermediate audience, I think a beginner would have no problems. The book describes each concept depicted, in a brief, but adequate introduction. Almost 30 pages, for instance, are devoted to the concept of AOP, followed by it's Spring specific implementation - Spring AOP.
The book contains a lot of code, probably more than I've ever seen in any other book. Well, most of it is not really code, but XML, used to configure the Spring container. I still call it code though, cause the amount of XML configuration in a Spring application can be extensive. The fact that the book is full of it, is actually positive, because it shows you on the spot how to implement the concepts depicted. The Springframework is all about applying concepts declaratively through XML and the book make a good job pointing that out.
Building Spring 2 Enterprise Applications is written in a very readable manner. I actually enjoyed reading it, which is not very common, when it comes to programming books. The code is also easy to read, which I think is important. I know how draggy it can be to rifle through extensive amount of other people's code.
After all the praises, I do have a couple of pain points. First of all the book suffers from the syndrome most framework related books do: they are out of date as soon as they hit the shelves. The book doesn't cover the latest release of the Springframework, which is currently 2.5.x. But I think that's not really a problem. All the concepts should be the same. However, there might be some differences in Springs implementations. What really bothers me is that fact that only JDBC is covered as a persistence strategy. I do realize that including JPA or iBatis probably would have raised the user level quite a bit. However, I think those frameworks and particularly their integration with Spring are important and shouldn't have been omitted. Last but not least, I think the level of the book is not quite intermediate - it's basic at most. One could argue that that's a good thing, but if you bought the book, expecting an intermediate level, you might be disappointed. I just think the book doesn't present enough best practices and coding idioms to be an intermediate level.
Overall I like the book, it's easy to read and a good reference to quickly recap on various topics or concept related to the Springframework.
Building Spring 2 Enterprise Applications is the second book of an Apress series about the Springframework. It cover topics like Aspect Oriented Programming (AOP), persistence and transaction management, as well as different view technologies all related to Spring.Each book of the series addresses a different user level. Although this one is meant for an intermediate audience, I think a beginner would have no problems. The book describes each concept depicted, in a brief, but adequate introduction. Almost 30 pages, for instance, are devoted to the concept of AOP, followed by it's Spring specific implementation - Spring AOP.
The book contains a lot of code, probably more than I've ever seen in any other book. Well, most of it is not really code, but XML, used to configure the Spring container. I still call it code though, cause the amount of XML configuration in a Spring application can be extensive. The fact that the book is full of it, is actually positive, because it shows you on the spot how to implement the concepts depicted. The Springframework is all about applying concepts declaratively through XML and the book make a good job pointing that out.
Building Spring 2 Enterprise Applications is written in a very readable manner. I actually enjoyed reading it, which is not very common, when it comes to programming books. The code is also easy to read, which I think is important. I know how draggy it can be to rifle through extensive amount of other people's code.
After all the praises, I do have a couple of pain points. First of all the book suffers from the syndrome most framework related books do: they are out of date as soon as they hit the shelves. The book doesn't cover the latest release of the Springframework, which is currently 2.5.x. But I think that's not really a problem. All the concepts should be the same. However, there might be some differences in Springs implementations. What really bothers me is that fact that only JDBC is covered as a persistence strategy. I do realize that including JPA or iBatis probably would have raised the user level quite a bit. However, I think those frameworks and particularly their integration with Spring are important and shouldn't have been omitted. Last but not least, I think the level of the book is not quite intermediate - it's basic at most. One could argue that that's a good thing, but if you bought the book, expecting an intermediate level, you might be disappointed. I just think the book doesn't present enough best practices and coding idioms to be an intermediate level.
Overall I like the book, it's easy to read and a good reference to quickly recap on various topics or concept related to the Springframework.
February 20, 2008
OSGi @ JUG-Ka
The Java Users Group Karlsruhe is going to have an OSGi session tomorrow.
I'll start the event with an introductory to OSGi while my co worker Heiko will give some insights on Spring Dynamic Modules. Michael Grammling will conclude the talk with on overview of the best practices and give some information on the activities of the OSGi Alliance.
If you haven't heard of OSGi yet, you definitely should come. It's a hot topic in the Java world right now and I think it's here to stay. If you already know about OSGi, you are ver welcome to contribute to the (hopefully) lively discussions.
I'll start the event with an introductory to OSGi while my co worker Heiko will give some insights on Spring Dynamic Modules. Michael Grammling will conclude the talk with on overview of the best practices and give some information on the activities of the OSGi Alliance.
If you haven't heard of OSGi yet, you definitely should come. It's a hot topic in the Java world right now and I think it's here to stay. If you already know about OSGi, you are ver welcome to contribute to the (hopefully) lively discussions.
October 21, 2007
Eberhard Wolff @ Jug-Ka
Java User Group Karlsruhe organized another talk about the Springframework on Monday October 29th at 7:15pm. It will be hosted at University of Karlsruhe at the same building, where the previous talks took place. Eberhard Wolff, managing consultant of Interface 21 in Germany will be giving the talk. For more information and an abstract (German) of the talk, check out the google group of jug karlsruhe or go to the website website.
August 15, 2007
Spring and Java GC talk
Today is another meet up of the Java User Group Karlsruhe. Topics this time are the Springframework and Java Garbage Collection. The talk will be hosted at University of Karlsruhe. You can find more details at the jug-ka google group or on java.net.
June 24, 2007
Code Organization
At SpringOne Interface21's Juergen Hoeller gave a talk about "Code Organization". I found the same talk over at InfoQ where Juergen spoke at The Spring Experience conference.
com_channels
- mail(dlinsin@gmail.com)
- jabber(dlinsin@gmail.com)
- skype(dlinsin)
my_links
recent_postings
loading...