Adding Maven artifacts to your target platform

Don’t get me wrong I really like Maven. It’s a great and technically mature build system. Nevertheless I try to avoid it in all my RCP and OSGi projects because all that POM declarations are redundant and unnecessary in some way. Inter bundle dependencies are expressed by means of OSGi manifests and the build process provided by the Eclipse environment respectively the headless PDE build is more than adequate. Obviously this is just a matter of taste and if you use Tycho or other IDEs with the better Maven support, maybe you will not agree.

Anyway there are many existing OSGi bundles (e.g. Jetty, Vaadin, log4j, Knopflerfish) available in Maven Central and manually downloading them together with all their dependencies is a cumbersome task. Also Maven dependencies without proper OSGi metadata information can be transformed via the maven-bundle-plugin if required.

So during my experiments with the embedded XULRunner, I tried to find a mechanism that automatically adds bundles from Maven repositories to my active target platform. If you are not familiar with the concept of Eclipse target platforms read this tutorial first.

This is my best solution so far. If you have better ideas please let me know!

Create a simple project named target_platform in your workspace. In the new project create a sub folder named maven_libs. Later this sub folder is the location of all jar files fetched by Maven. Select New->Other->Target Definition and add the maven_libs folder to the list of required locations.

The path ${project_loc:/target_platform}/maven_libs works fine even if the target_platform project is outside the current workspace. Of course you can still add further locations like environment variables, folders or p2 repositories.

Create the following pom.xml definition that lists all required dependencies in your target platform project and configure the outputDirectory accordingly.


<project>
    <modelVersion>4.0.0</modelVersion>
    <name>Target Platform Project</name>
  
    <groupId>com.javahacks.sample</groupId>
    <artifactId>target_platform</artifactId>
    <version>1.0</version>  
    <packaging>pom</packaging>
	
	<properties>
		<outputDirectory>maven_libs</outputDirectory>
	</properties>

	
    <dependencies>
        
		<!--Configure dependencies here -->
        <dependency>
            <groupId>log4j</groupId>
            <artifactId>log4j</artifactId>
            <version>1.2.17</version>       
        </dependency>
               
    </dependencies>
  
    <build>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-dependency-plugin</artifactId>
                <version>2.8</version>
                <executions>
                    <execution>
                        <id>copy-dependencies</id>
                        <phase>initialize</phase>
                        <goals>
                            <goal>copy-dependencies</goal>
                        </goals>
                        <configuration>                            
                            <overWriteReleases>false</overWriteReleases>
                            <overWriteSnapshots>false</overWriteSnapshots>
                            <overWriteIfNewer>true</overWriteIfNewer>
                        </configuration>
                    </execution>
                </executions>
            </plugin>
  
           
        </plugins>
  
    </build>
    
</project>

Now run mvn install from within Eclipse or on the command line inside the ‘target_platform’ location to fetch all libraries configured in the POM configuration.

Reopen the target definition and select Set as Target Platform. If you run Maven outside your IDE refresh the target platform project first.

This approach is also useful for the POM dependency resolution explained here. Now you have the same bundle resolution at the build and development time and running the Maven installation to setup the target platform on your build server (without Tycho) is no problem.


2 Comments on “Adding Maven artifacts to your target platform”

  1. An interesting approach. I actually used this approach in the past to build my Eclipse RCP application. To get continuous integration (“headless build”) working I decided that
    Buckminster was way too complicated and I didn’t even want to start with PDE build with ANT. I wonder what you are using? As I was already using Maven for the server part of my application, I decided to use Maven Tycho. I have never regret this decision. For most plugins a very simple default pom suffices.

    Because my build requires Eclipse RCP, it is much more natural to use a p2 repository on the target platform through an Eclipse .target configuration file. I do have many pom-first dependencies.
    I solved the issue of creating the full target platform by using the pde-target-maven-plugin (groupId lt.velykis.maven) instead of the maven-dependency-plugin. It does a very neat trick to get your Maven artifacts on the target platform for the PDE build (when you are developing in Eclipse). Instead of copying the dependencies, it creates a new target definition file based
    on your handmade one with directories that point directly to the directories in your local Maven repository.

    • javahacks says:

      Thanks for your reply. I used to build RCP applications with PDE, but now we are using Tycho too. I didn’t know the pde-target-maven-plugin but will give it a try in the future!


Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s