Monday 10 June 2013

Implementing Maven into an existing project

My current project requires using Apache Ant to build our Java applications into WAR (Web Application Archives) files for Tomcat which in turn we use to run our service on a virtual machine. I've had a number of problems with this as we have two developers, one (me) primarily developing on Windows 8 the other on iOS.

Our Tomcat service runs on the same Linux server (Ubuntu Precise) however as we commit back and forth via GitHub we are overriding each others environmental variables (despite trying to get the other developer to use .gitignore more). To restore some sense of consistency and not to have to constantly worry about different environments I've decided to try out Maven.

Maven is a project management and comprehension tool (Maven) and by structuring our project files and libraries I hope it helps fix a lot of our dependency and co-development problems as we continue to add developers to our software project.

I'm using Eclipse with the Android Development Kit plugin (https://developer.android.com/sdk/index.html). You can install new software to Eclipse by going to the top menu, clicking Help then Install New Software.


From there you can select "All Available Sites" to "Work With" and search for maven. Install the Maven plugins and restart Eclipse when asked to.


Because I want to import an existing project into the Maven format, I'm going to go ahead and create a new Maven Project via New -> Other -> Maven -> Maven Project

Using the default Workspace location and a simple project. (FYI there is a Tomcat archetype, but I found it unwieldy to use as a beginner to Maven). My GroupId is the namespace we are using for all our packages previously (com.businessname), the ArtifactId is the Project name and change the Packaging to 'war' and fill in the other fields as you see fit.

I placed my previous projects code under src/main/java/com/businessname/subfolders. Change this as you need to, I wanted to keep my previous package namespacing "com.businessname.*" intact. There will usually now be a hundred or so errors where dependencies are now failing.

Right click in the Package Explorer to reveal the Maven contextual menu and go to Maven -> Add Dependencies. It gives you the ability to search for your missing dependency, I find it easy to copy in the import missing.library.name.* and search for that directly, adding only what I really need.

You can see the dependencies being updated in pom.xml in the projects root directory. The POM file is a Project Object Model written using XML. It contains the brains of the projects paths and dependencies. It allows you to set rules based on your resources so only specific revisions are included or excluded.

Example: Snippet of a pom.xml requiring Tomcat7







In some cases there are no Maven supplied dependencies for Java libraries you need. You can still manually place them into the pom.xml so they are treated as a core-dependency of your code.

Example: Adding in net.sf.json.lib dependency to Maven







Update: Thanks to Petar Tehchiev for his answer to this dependency problem, you need to also include the classifier tag to specify which JDK to use. [stackoverflow]

When we are ready to build this war file, we need to ensure that our web.xml from our previous Ant-based project has been brought across and added into our pom.xml.

The easiest way to add the requirement into your section of your pom.xml file.
Ensure that you have copied your WebContents folder (or equvilent) to the path specified in the below tags PATH.
Example: Adding in the web.xml file to our list of Maven plugins








Run-As and make a new Maven Build configuration. Goals should be war:war and with that you can Run and build your WAR file. If it goes well you will get a lot of output including:

[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------

I deployed to my Tomcat service only to have a few errors popup. Not all dependencies are immediately obvious, especially when you inherit random projects like I frequently do. The error in my /var/log/tomcat7/servername.date.log was:

java.lang.ClassNotFoundException: com.sun.jersey.spi.container.servlet.ServletContainer

Which isn't a completely new problem if you spend a second googling it. Mkyong.com shows how to resolve this quickly and also reveals how powerful Maven is at it's core. By adding a new dependency (this time groupid: com.sun.jersey and artifactid: jersey-server) and building the WAR again we have fixed this dependency issue and can continue to do so.

More to come on Maven in later articles.


No comments:

Post a Comment