21 December 2011

Spring Integration Tests with Real Transactions

Spring's Test Context has a @Transactional annotation for wrapping tests in a transaction started and rolled back by the test container, to keep the tests from modifying the database. This is just what you need for deterministic, repeatable database tests.

On the other hand, due to this approach, the transaction boundaries in your test system differ from the ones in your production system, which can lead to errors in production which were never noticed in your tests suites.

I wouldn't go as far as saying that transactional tests should be considered harmful, but at least you should be aware of the side effects which may or may not be harmless in your specific use case.

For tests with real transactions, you need to take care of cleaning up the database yourself.

JUnit rules are a neat way of doing this. Here is an example:

02 December 2011

XVisitor: Visitor Pattern for JAXB

XVisitor is a plugin for the xjc code generator to enrich the JAXB model generated from an XML schema so that users can work with the Visitor pattern on this model.

16 November 2011

Eclipse Performance on KDE and Ubuntu 11.10

If you suffer from poor graphics performance when using Eclipse under KDE, especially when scrolling large trees, check your GTK+ Style.

After changing the style from oxygen-gtk to QtCurve, my Eclipse is now running on steroids.

I'm using Eclipse Indigo 3.7.1 on Kubuntu 11.10 amd64 with Oracle JDK 1.6.0_26 and an NVIDIA GeForce 8400 GS graphics adapter. I never used to have any issues on Kubuntu 10.04 LTS which is still running smoothly on another partition of my disk.

I had suspected the NVIDIA drivers, tried different JREs (including 32 bit versions) and Eclipse releases, none of which made a difference.

Finally, changing various configuration options by trial and error, I found out that oxygen-gtk seemed to be the cause.

To optimize your installation, install the qtcurve package, and select it in K Menu | System Settings | Appearance | GTK+ Appearance | Widget Style. Then restart Eclipse and enjoy.

23 October 2011

JBoss AS 7: Catching up with Java EE 6

In my Java EE 6 server comparison of June 2011, JBoss AS 6.0.0 was not exactly the shining star, both in terms of performance and usability.

The next major release JBoss AS 7, claiming to be lightning fast, was published in July 2011, followed by two maintenance updates in August and September.

Time to take another look at JBoss and check if it now compares more favourably to other servers.

29 August 2011

Eclipse Maven Integration Extensions

For me, the most important new feature in Eclipse 3.7.0 (Indigo) is the improved Maven Integration, formerly developed by Sonatype under the name of m2eclipse, now an official Eclipse subproject under the name of m2e.

m2eclipse and Eclipse sometimes used to have different opinions on what was going on in the workspace, and so we had to go through series of refresh/update dependencies/update configuration/rebuild voodoo (or "m2eclipse dance" as some called it) to get projects in a good state. (Quote from the m2e Wiki).

m2e has a different approach. First of all, it complains when detecting a Maven plugin in one of your POMs that it cannot handle out of the box. m2e flags your POM with an error marker that will not go away until you tell m2e what do to about the unknown plugin. The easy way out is a Quick Fix to ignore the plugin, which means you'll have to run the corresponding Maven goal manually when you need it.

However, when the Maven plugin in question generates source code or post-processes byte code, this is usually not sufficient - ideally, Eclipse and m2e should pick up the required build steps from your POM automatically.

This issue is addressed by m2e extensions, which provide the missing link between Eclipse project builders and Maven plugins. An m2e extension for a given Maven plugin not only invokes the required mojos but also informs Eclipse about new source or binary folders created by the mojos, so that Eclipse and Maven can stay in sync.

My projects use a number of Maven plugins that are not supported by m2e out of the box, e.g. for JAXB and OpenJPA, so I started creating some custom extensions for these plugins, based on a GitHub fork of the official m2e extensions from Sonatype.

See the wiki page at GitHub for more details. The GitHub project also contains an Eclipse update site (aka p2 repository) for installing the plugins. Time permitting, I'll try to make these extensions available via the Eclipse marketplace.

For any fixes, additions or new extensions, feel free to send my pull requests.

25 June 2011

Wicket and OSGi

After playing around with the OSGi JPA and JTA components of Apache Aries for a while, it was only natural to try and add a web layer to my sample projects. The Aries samples all use plain old servlets and JSPs, so I wondered if Wicket would work in this context.

So far, I had only ever used Wicket in standard Java EE web applications, but I had noticed the Wicket JARs come with an OSGi manifest, so someone must have tried to use Wicket in OSGi before.

07 June 2011

Java EE 6 Server Comparison: Conclusion

Lessons Learned

Portability is not just a Java EE marketing promise. My application now runs on three different Java EE 6 servers, using the same WAR file, without any compile-time configuration.

An application is not portable until it has been ported. Of course, this is true for any specification with different implementations, not just for Java EE. Each of the three servers helped me discovering incorrect API usage in my application that just happened to work on another server.

Certification is not reliable. My application hit at least one major specification violation in each of the three Java EE 6 certified servers. Thus, the test coverage in the Java EE TCKs must be insufficient.

Java EE 6 Server Comparison: Resin

The first time I read about Caucho Resin 4.x was last summer, when I was looking for alternative CDI implementations, i.e. other than Weld. Resin has its own CDI implementation named CanDI, and I was bold enough to give it a try, knowing that Resin 4.x was not yet Java EE 6 certified and probably not stable enough.

I didn't get very far at that time, CanDI looked ok, but the JPA API was broken and @Singleton @Startup beans did not work, so I left it at that and made a mental note to check back after the first stable release.

Java EE 6 Server Comparison: JBoss

I never did any serious work with JBoss AS 5 or earlier versions. At the peak of my frustration with Glassfish last summer after the 3.0.1 release when CDI continued to be unusable, I knew that JBoss would be no help as it also included Weld, the main source of trouble. Besides, given the number of problems in released and certified Glassfish, I dreaded an even larger number of problems in an unreleased, uncertified and undocumented JBoss.

When JBoss AS 6.0.0 was finally released late in December 2010, with surprisingly little marketing noise and community echo, I briefly had a look at the release and was disappointed to find out that it was still largely undocumented.

Java EE 6 Server Comparison: Glassfish

In April 2010, I started a Java EE 6 project, and Glassfish 3.0 was the obvious server choice, or rather, the only option at that time. For the next couple of months, I spent a considerable amount of time not working on my application, but analyzing, reporting and working around bugs in the server, mainly in the CDI and JPA areas. This appeared to be the price you had pay for being an early adopter of the new Java Enterprise standard.

Java EE 6 Server Comparison: Introduction

A year and a half after the Java EE 6 specification release, there are now three Open Source servers certified for the Java EE 6 Web Profile:
  • Glassfish 3.x
  • JBoss 6.x
  • Resin 4.0.x
Time to take a look at these three servers in direct comparison and do some experiments, not with a toy or benchmark application developed for this purpose, but with a real-life enterprise application.

06 June 2011

Java EE 6 Integration Testing on Resin and Glassfish

jeeunit, my Java EE 6 Integration Testing project, now supports Caucho Resin 4.0.18 in addition to Glassfish 3.1.

Another new feature is a @Transactional annotation which can be used to wrap test methods in an auto-rollback transaction.

The current release jeeunit 0.8.0 is available from Maven Central and from the jeeunit Project Page on Google Code.

01 June 2011

Using CDI from Spring

Spring and Java EE are converging in many areas, mainly due to CDI. In fact, by confining yourself to a suitable subset of annotations and other configuration mechanisms, you can design your persistence and service layers to run either on Java EE 6 or on Spring 3, simply by selecting the appropriate set of libraries.

The web layer is a different story: if your web framework is tightly coupled to either Java EE 6 or Spring, it will be hard or even impossible to simply change the container, but even in the web layer, there are solutions like Apache Wicket which work well both with Spring and Java EE, all you need is some glue code to access the dependency injection container.

I'm currently migrating a web application from Tomcat/Spring to Glassfish, and since this application is based on Spring MVC, I cannot completely replace Spring in this step. The goal of the migration is to drop all Spring dependencies from all components except the web frontend and to somehow make the service beans (stateless session beans and CDI managed beans) visible to the Spring web application context.

25 May 2011

Eclipse Helios with Firefox 4 on Ubuntu Natty

I've just finished installing Kubuntu 11.04 on a spare partition, and I'm rather pleased with it, there were absolutely no problems with the usual suspects like X driver, sound or fake RAID.

The only regression I noted is that Eclipse 3.6.2 no longer supports an internal web browser. Ubuntu 11.04 comes with Firefox 4.x, and this is not currently supported by Eclipse SWT.

This thread gave me the hint how to fix it:
  • Install package libwebkitgtk-1.0-0 (do not use the newer version libwebkitgtk-3.0-0)
  • Add the following to eclipse.ini: -Dorg.eclipse.swt.browser.UseWebKitGTK=true
  • Create a symlink in /usr/lib to satisfy the SWT dependencies:
    ln -sf libwebkitgtk-1.0.so.0.6.0 libwebkit-1.0.so.2
Restart Eclipse and check Window | Preferences | General | Web Browser. The radio button Use internal web browser should now be enabled.

Update 2 Jul 2001: After upgrading to Eclipse Indigo 3.7.0, the internal browser works out of the box. I did not have to modify eclipse.ini. But it seems Eclipse now uses WebKit by default, so you still need to install the WebKit library and create the symlink if you haven't done so before.

03 April 2011

reFit Plugin for Jenkins

After working with Hudson (now Jenkins) as a user for almost three years, I've now created my first plugin for publishing Fit test reports for Jenkins projects.

The plugin works with reFit 1.7.0 or higher. It is published on the Jenkins Community infrastructure, separate from the reFit project on Google Code. You can install the plugin from the Jenkins update centre.

For more details, see the reFit Plugin page in the Jenkins Wiki.

20 March 2011

JAXB Marshalling with Custom Namespace Prefixes

The Problem

  • You have an XML schema with multiple XML namespaces.
  • You generate a JAXB model with xjc.
  • You build a JAXB document model and use the JAXB Marshaller to create XML from the model.
  • You want to override the default namespace prefixes ns1, ns2, ... created by the Marshaller.

13 March 2011

Transparent Asynchronous Remoting via JMS

The Scenario

A client needs to invoke a service interface with the following restrictions:
  • The service implementation is running on a remote machine.
  • This fact is transparent to the client, i.e. any service method invocation is just like a local method invocation.
  • The service methods are executed asychronously on the server, method invocations on the client return immediately (fire-and-forget).
  • All service methods have void return types.
  • The service invocations shall be transported via JMS.

20 February 2011

Hamburg Elections Powered by MySQL

Following a link on Google to the intermediate results of today's elections in Hamburg on the official website of Statistikamt Nord (Hamburg and Schleswig-Holstein Statistics Office), I found this:

Ok, the good news is that our taxes don't get wasted on expensive Oracle licenses...

Building a Web Application with Wicket, Spring and JPA

This is a tutorial on setting up a web application stack with Wicket, Spring and JPA, with a special focus on avoiding Spring XML configuration in favour of Java configuration, and on using the JSR-330 @Inject annotation both in the web and service layers.

Martijn Dashorst's blog on Wicket/Spring/Hibernate configurationwas the starting point for my setup, and as I hate "oodles of XML"  as much as he does, I replaced all the XML bean declarations by a @Configuration class, a new feature in Spring 3.0.x.

07 February 2011

Maven Snapshot Repositories with Nexus

When you have a Maven build which depends on more than one external repository, it is usually a good idea to work with a repository manager. A repository manager also enables you to share your artifacts with other team members.

Nexus Open Source is probably the most popular Maven repository manager. Once it's set up correctly, it requires little or no maintenance, at least that's my experience after using it in different projects over the last three years.

I've just finished setting up Nexus for my current project, but this time, I spent almost a day chasing a problem related to snapshot repositories.

I had set up the Public Repositories group of Nexus as a mirror for Maven central and configured the Nexus Snapshots repository as an additional snapshot-enabled repository for the snapshots from my own project:

22 January 2011

Transparent Asynchronous Remoting

The Scenario

A client needs to invoke a service interface with the following restrictions:
  • The service implementation is running on a remote machine.
  • This fact is transparent to the client, i.e. any service method invocation is just like a local method invocation.
  • The service methods are executed asychronously on the server, method invocations on the client return immediately (fire-and-forget).
  • All service methods have void return types.

The Solution with Java EE 6

With Java EE 6, the solution is quite simple, thanks to the @Asynchronous annotation introduced in EJB 3.1. You simply create a remote session bean and add this annotation to any business method or to the entire class. The container will then execute the given methods asynchronously.

Patrick Champion has a complete example in his blog, so there's no need for me to provide any sample code.

When your client is also a Java EE 6 application, you can simply @Inject the service interface and use a @Produces annotation on an @EJB reference somewhere else to direct the client to the appropriate implementation.

In addition, to avoid hardcoding the service URL in your client, you should define a local JNDI alias in your Java EE 6 container for the address of the remote service implementation, so you can move the remote implementation to another host without recompiling your client.

The Solution with Spring 3.0

Spring does not have an out-of-the box solution for this scenario. Spring Remoting provides transparent proxies for remote services, but these proxies are always synchronous. Since Spring 3.0, there annotation support for asynchronous execution, but this only applies to local beans.

However, it is not hard to combine these two features with some glue code to implement a solution for our scenario.

18 January 2011

reFit: Acceptance Testing for Java EE 6, Spring and OSGi

Even if you don't practice test-driven development, you are certainly familiar with the JUnit family of testing frameworks (including ports to other languages like cppunit, NUnit, or independent but similar approaches like TestNG).

This post is about the Fit framework family, which has a somewhat different focus and is not just another JUnit clone. In a nutshell, Fit represents expected and actual test results in tables, and you do not have to be a programmer to read or write them.

The following table has one column of inputs and two columns of outputs:

Each row of this table can be regarded as an acceptance test case. You can feed this table to a given system and compare the outputs:

It's only a couple of weeks ago I was introduced to Fit in my current project, and I must admit my first thought was "Why don't you just write a @Parameterized JUnit test?"

The answer is, JUnit is for developers, and developers only; Fit is for customers and developers.

You still need a developer to implement the skeleton logic of a test (called fixture in Fit), but anyone can write new test cases by adding rows or columns to a given Fit table.

The Fit method and the original Java implementation were created by Ward Cunningham in or around 2002, the project is hosted on Sourceforge and has been inactive since 2008.

The Fitnesse project integrates Fit with a Wiki, it includes a modified version of the original Fit implementation and is under active development. However, Fit and Fitnesse are incompatible, Fit lets you write your test tables in plain old HTML, whereas Fitnesse supports its own Wiki syntax only.

Our project has a fair amount of plain old HTML Fit tests, and our production code uses Spring, so it was a fairly natural idea to inject Spring beans from the system under test into our Fit test code.

Spring is just one (and not really my favourite) framework for dependency injection (and lots of others things). so I inevitably started thinking about how to use Fit together with Java EE or OSGi.

Thinking was followed by coding (yeah, it can be the other way round sometimes...), and this led to a project called reFit hosted on Google Code.

reFit is based on the latest Fit sources from SourceForge, it provides up-to-date Maven artifacts on Maven Central and integrations with Java EE 6, Spring and OSGi Declarative Services. The Java EE integration reuses parts of my jeeunit project.

In addition, reFit lets you run Fit tests under a JUnit wrapper or from a Maven plugin, both with or without Spring integration. reFit includes ready-to-run example code for Glassfish 3.1, Spring 3, Equinox and Weld SE.

There's more to come, I'm currently experimenting with a Web frontend and a WYSIWYG HTML editor.

For more details, check out the reFit Wiki.

04 January 2011

Eclipse Meta-Error

01 January 2011

Maven Plugin Inheritance

Writing Plugins for Maven is not hard, and Maven: The Complete Reference has an entire chapter on this subject. Of course, nothing is ever complete in real life or in software development, and one of the topics not covered in the book is plugin inheritance.

The scenario:
  • There is a (fictitious) maven-tea-plugin which takes a number of configuration parameters and has a tea goal. It is implemented by a TeaMojo.
  • You are writing a maven-greentea-plugin which has almost but not quite the same behaviour as the maven-tea-plugin. It takes the same parameters and has the same goals.
  • The natural idea is to derive a GreenTeaMojo from the TeaMojo and to override one or two methods of the base class, reusing all the parameters.
Unfortunately, this does not work, at least not out of the box. The problem is:
  • Maven uses poor man's Javadoc annotations to inject configuration parameters into Mojo classes.
  • This is still true in Maven 3.0, even though the traditional Plexus container has now been replaced by Guice.
  • The maven-plugin-plugin (i.e. the plugin responsible for plugin building) needs to scan the Mojo sources for Javadoc annotations, but the maven-tea-plugin sources are not visible during the build of the maven-greentea-plugin.
Now the maven-inherit-plugin from OPS4J fills the gap by looking up the plugin descriptor from the maven-tea-plugin and merging it with any additional parameters defined in the maven-greentea-plugin. To use it, just follow the documentation.

There is just one point to note: You have to add an @extendsPlugin annotation to your GreenTeaMojo to indicate the plugin you want to extend, but the value of this annotation is not quite obvious. It has to be either the plugin artifact id, or the plugin short name, tea in our case, but this requires the artifact id to be maven-tea-plugin or tea-maven-plugin.