Minimal <span class="caps">OSGI</span> with Spring

Very lightweight OSGI with Spring

Author: Michael Krauße
Date: 01.04.2012
EMail: ClickToWriteMail

Motivation

The Spring-framework is fantastic if you need dependency injection in your application. Since I love OSGI’s idea that a framework provide extension-points which can be extended by other plugins I wanted something similar for my current project. What I need is a very lightweight approach similar to OSGI, which allows me that each plugin can have all configuration already “on board” and can contribute to a framework. Researching and asking at Stackoverflow gave me a link to Spring Dynamic Modules Unfortunatly this approach was a little bit to heavyweight for me since my application does not live in an application-server which supports OSGI.

This article contains my solution for the given problem. Available source-code is distributed under a BSD-License and unclear acronyms have been explained at the end.

A more detailed problem description

At the moment I am working at a client who develops multiple plugins which were build upon a self-written-framework and share an Oracle database during runtime. Two years ago all plugins and the framework have been stored in the same repository-structure. This allowed us to configure the product in Spring configuration-files which belonged to the framework. During time the number of plugins raised and developers were not able to keep plugins up-to-date to latest framework version. Now we run into the problem that all plugin-registration-configuration is done in the framework but we do not want all plugins to be part of the product we deploy. (Plugins which have not been tested against latest version of framework will be deployed on an other server with a framework version which has been tested)

For solving the problem I looked for an approach which adds some OSGI to a Spring application. All I needed was a solution which simple creates s static configuration which is not changeable during runtime and is flexible enough to allow new plugins to register without touching the framework. The Spring Dynamic Modules looked promising but were a little bit heavyweight and I don’t like aspect-oriented-programming anyway if I can avoid it.

Or to make a long story short the only thing I wanted to change was that each plugin registers on its own to the framework. The framework should not know anything about the plugins which run on top of it.

Solution overview

My solution was inspired by OSGI. Removing dynamic plugin (un)loading, and all other OSGI I never knew it exists stuff helped me finding a solution. In my approach I changed the configuration is done in Spring. Instead of a Spring configuration which contains all plugin-registration in the framework the framework creates a pluginRegistry with scope singleton. Each contributing plugin is now able to contribute to this registry. In only has to create pluginFactory which creates instances of the plugin. The instances of the plugin are created with help of the spring-application-context.

Since all pluging-factories are configured as spring singletons they will created during application-startup-time.

You will find more information in the following class-diagram and the source-code if you download it (see above how to do it).

Class diagram

click to enlarge image

Implementation details

<?xml version="1.0" encoding="UTF-8"?>
<!-- author: Michael Krausse -->
<beans xmlns="http://www.springframework.org/schema/beans"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.0.xsd">
   <!-- Bean coreRegistry becomes available in spring context. Plugins needs to register against this registry. -->
   <bean id="coreRegistry"
      class="de.m_krausse.articles.minimalOsgiWithSpring.PluginRegistry">
   </bean>
   <!-- Application uses coreRegistry. No plugins are configured here this 
      is done in plugin implementation -->
   <bean id="languageApplication"
      class="de.m_krausse.articles.minimalOsgiWithSpring.Application">
      <property name="pluginRegistry" ref="coreRegistry" />
   </bean>
</beans>
<?xml version="1.0" encoding="UTF-8"?>
<!-- author: Michael Krausse -->
<beans xmlns="http://www.springframework.org/schema/beans"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.0.xsd">
   <!-- Configures the plugin which does the work of saying hello in German. -->
   <bean id="pluginGerman" class="de.m_krausse.articles.minimalOsgiPluginOne.PluginOne">
   </bean>
   <!-- The factory creates new instances of pluginGerman if coreRegistry
   needs a plugin which can say hello in GERMAN. -->
   <bean id="pluginGermanFactory"
      class="de.m_krausse.articles.minimalOsgiWithSpring.PluginFactory">
      <constructor-arg ref="coreRegistry" />
      <constructor-arg value="GERMAN" />
      <constructor-arg value="pluginGerman" />
   </bean>
</beans>

Summary

With the approach described above it is possible to give your spring application a more OSGI like feeling. Although the approach allows only static configuration (no dynamic (un)loading of plugins) it might work well for situations when static configuration is sufficient.

I made good experience with this approach in a non-clustered tomcat environment. It is integrated into a batch-processing framework used in the output-management.

I am interested in your point of view. If you want drop me a line ClickToWriteMail

Download sourcecode

Please feel free to download the sources from my example project. You need at least maven 2.X to compile and run the project. Disclaimer You use the source-code on your own risk.

You find the source code under the following URI.
osgiWithSpring.zip

Acronyms

Some descriptions have been borrowed from wikipedia. ;-)

Acronym Meaning
OSGI Open Services Gateway initiative framework – is a module system and service platform for the Java programming language that implements a complete and dynamic component model
Product As used in an OSGI world. Consits of different applications and is shipable on its own (if runtime requirements are met)

Read on

Online