JRebel ?

I use JRebel to speed up my development. It is a really impressive tool allowing to develop full blended Java EE application as you would develop in PHP. No redeploy, at the cost of a little slow-down in development mode. The tool does what it says, and it's worth the price ! The JRebel plugin for maven does the job very well by generating the rebel.xml file that does the magic.

What's the deal ?

Although JRebel is an awesome tool, there is some magic within, and, in special corner cases it might not work as expected. In my case I have a quite typical web application split in multiple parts:

  • a web application (war)
  • an ejb module (jar)
  • other modules not involved in my problem
The web application includes, in its WEB-INF/lib folder, the ejb-client artifact of my ejb module. To make it clear, ejb-client artifact is typically the jar containing the interfaces to be used by the client module(s).

The problem I had was that JRebel magic was reloading too much things : in fact, it reloaded classes even if they were not in the ejb-client. My application container (Glassfish 3.x) was not very keen on this thing. I opened a thread on ZeroTurnAround's forum and the answer I got is that I have to find a way to ignore files in my ejb-client module. By digging in maven-ejb-plugin, I didn't find anything to rename a file in the ejb-client module, and I didn't find a parameter to pass to JRebel to specify which filenames can contain its configuration.

The solution

I patched the maven-ejb-plugin to fulfill my needs. It is done in a very simple and probably not optimal way. The trick is to create a file named client.rebel.xml containing the JRebel configuration to be used by the ejb-client module. At compile time, when building the ejb-client artifact, Maven will automatically replace the auto-generated rebel.xml by the client.rebel.xml.

The piece of code corresponding to the patch is the following:

File file = new File(outputDirectory, "client.rebel.xml");
if (file.exists()){
   getLog().info("Found a client.rebel.xml, renaming it to rebel.xml and put it into destination ejb-client archive");
   clientArchiver.getArchiver().addFile(file, "rebel.xml");
   List list = new ArrayList(Arrays.asList(excludes));
   list.add("**/client.rebel.xml");
   list.add("**/rebel.xml");
   excludes = (String[]) list.toArray(EMPTY_STRING_ARRAY);
}

This is the only modification done to the original maven-ejb-plugin (aside the modified version number in pom.xml to clearly identify my fork) so it will surely be easy to port to the another version.

How to use ?

I imported my little fork of maven-ejb-plugin on my github account. You can freely use it, fork it, improve it if you need to. If I find the time I could make it better by providing a much more flexible system (client.rebel.xml to rebel.xml hard coded hurts me while reading this code...).

To use this, if you need to, you simply need to clone the sources, build this project and set the maven-ejb-plugin version to your pom like the following :

<build>
 <plugins>
   <plugin>
     <groupId>org.apache.maven.plugins</groupId>
     <artifactId>maven-ejb-plugin</artifactId>
     <version>2.3-jrebel</version>
  </plugin>
 </plugins>
</build>

If it works, you will see in your build log a line telling "Found a client.rebel.xml, renaming it to rebel.xml and put it into destination ejb-client archive". If everything goes well, the problem disappears and the next step is to deploy the artifact to your company hosted maven repository to let your entire team use this.

Hope it'll help...

comments powered by Disqus