Leveraging a little bit of the OSGi power

These days I have been pushing all the OSGi stuff through the review process so we have already got some of the work in the master branch. Ray has written a really good blog post about using the Apache Felix Gogo console inside Liferay and he has already explained some of the benefits of our current work so I am not going to explain it here again.

We are still going through the peer review process so, at the time of this writing, some of the features could not be in the master branch yet. Anyway, we can still get many benefits and write powerfull applications which can exploit some of the benefits wich OSGi brings to us. In order to illustrate the previous statement, let's write a small, and extensible, metrics application.

Our goal is to build a small and pluggable monitoring system which allow us to track different aspects of the Liferay's internals like, for example, JVM statistics or whatever you can imagine.
 
The example is using the OSGI Declarative Services specification. It is a declarative and very easy way of declaring and consuming OSGi services. It is not included by default right now because, once all the stuff is already in master, we will try to push something very close to the approach shown in this example, but using the Eclipse Gemini Blueprint project, in order to keep all the Spring benefits we already own.
 

The metrics core system

The core of our metrics system is extremely simple, we just create a domain model to represent our system metrics
 
 
Another important piece of our metrics core component is the MetricsProviderManager. It is just a simple backgrupund task which, periodically, collects all the metrics extensions registered in the system.
 
 
As you can see, right now we don't have any source code which can provide us any kind of metric. At the beggining of the post we have said that our metrics system should be pluggable/extensible. In order to do that let's create an SPI (Service Provider Interface) which the extensions of our metrics system should fulfill.
 
 
Once we have the core of our system let's go and register it as a service inside the OSGi container (which is running inside liferay). We have different ways to do that: in this example we are going to show how we can achieve that using the Declarative Service specs:
 
 
What are we doing within the previous definition?
  • Declaring our Metrics manager as a component (OSGi service)
  • Get/UnGet a reference to every MetricsProvider service which is registered/unregistered in the OSGi container (note how easily we can extend our metrics system)

Our first metrics extension

At this point we have the core of our system, which, by its own, it does not measure anything :). Let´s build our first metric component, a JVM metrics provider (a stupid one :) ). How can we do that? Just two easy steps

Implement the SPI wich the core system is exposing

 

 

 

Register the previous implementation as an OSGi service (we are using the Declarative Service approach too):

 

And that´s everything we need to do. Simple, isn´t it?. Just package both components and deploy it to your LIFERAY_HOME/data/osgi/deploy folder and just see the logs. Now, you can connect to the console (as Ray has already shown) and stop your metrics-jvm component so JVM metrics will not be longer collected, or you can create a new metric extension, deploy it and start seing it metrics on the log.

I am, intentionally, hiding all the OSGi details since I want you to put the focus in the general idea, and not in the details of building a MANIFEST.MF. In the near future we will see more complex things like using Liferay services as OSGi services, creating OSGi based webapps, ...

You can find all the source code in the following Github repo under the folder liferay-module-framework/examples/declarative-services.

I would love to hear your feedback and if you would prefer having a wiki page with all the new module framework related stuff instead of having long blog posts like this one (sorry about that)

Blogs
Looking forward to the examples of using Liferay services and webapps as OSGI components.