Tata AIG General Insurance Company - Insurer Innovation Award 2024
Maven 2 in the real world
1. Object Oriented and beyond
Maven 2 in the real world
Carlo Bonamico
carlo.bonamico@gmail.com
JUG Genova
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
2. Maven2: love it or hate it?
Widespread build platform
●
used by many open source and commercial projects
–
PROs
●
automatic dependency management
–
good tool/IDE support
–
automate the entire build life cycle
–
highly configurable also...
–
lots of tutorials
CONs on simple cases,
●
less documentation
on complex builds
highly configurable :-)
–
too much XML...
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
3. Presentation goals
Maven can be your friend (and save lots of time!)
●
if you
–
learn it and understand it
●
use it in the right way
●
My talk is about how to maximize usefulness and
●
efficiency
while minimizing complexity & overhead
–
Sharing real world experience
●
in designing and managing the build process for
–
several large projects (>20 modules, >100 kLoc)
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
4. Part 1
Maven2 in 5 minutes
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
5. Maven2 in 5 minutes
Maven is a modular automation system built
●
around 4 main elements
repository
POM
Maven
Plugins
src
input: project src/resources + POM
–
output: tested and packaged artifact
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
6. Maven in 5': the POM
The Project Object Model describes
●
project coordinates
–
groupId: net.juggenova
artifactId: sample
project type
–
version: 1.0
packaging (JAR, WAR, EAR, POM)
●
source structure
–
build phases
–
standard + custom
●
dependencies
–
plugins
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
7. Maven in 5': build lifecycle
Default life cycle Every goal implies all
● ●
the previous ones
validate
–
generate-sources
–
mvn compile
–
process-resources
–
actually executes
–
compile
–
validate
–
test-compile
–
generate-sources
–
test
–
process-resource
–
package
–
compile
–
integration-test
–
verify
–
Stand-alone goals
●
install
–
deploy
–
mvn scm:update
–
(some skipped for clarity)
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
8. Maven in 5':
Dependency Management
Dependencies
●
include all external libraries and files needed to
–
completely assemble the output
JARs, WARs, ZIPs, POMs
●
are versioned
–
can be transitive
–
e.g. include just spring, get commons-logging
●
automatically
Conflict resolution mechanism
●
determines the version to be used when a jar is
–
included multiple times
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
9. Maven in 5': repositories
Maven repository
●
a structured store containing artifacts (JAR, WAR, ZIP...)
–
Maven uses at leas two
●
local repository – on your PC
–
central repository – http://repo1.maven.org/maven2/
–
Three types of repositories
●
local repository
plain filesystem folder
–
${user.home}/
folder served by HTTP daemon
–
.m2/repository
populated via SCP/FTP/WEBDAV
●
full “intelligent” repository (with indexing, search, cache, ...)
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
10. From code to repo (and back)
deploy
install remote
repository
local
repository
package central
resolve repository
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
11. Part 2
Effective maven2
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
12. Getting the most out of Maven
Good old sw engineering principles still apply!
●
Don't repeat yourself
●
things
the DRY principle
– always change
in a project
reduce time, effort, maintenance
●
minimize the impact of changes
●
Separate concerns
●
Automate as much as possible
●
Use the right tools (plugins & repositories)
●
Keep the build fast
●
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
13. How to minimize XML
Exploit the three main POM relationships
●
inheritance, aggregation, dependency
–
This is a valid (and working) maven POM
●
<project xmlns=quot;...quot; xmlns:xsi=quot;...quot;
–
xsi:schemaLocation=quot;...quot;>
● <modelVersion>4.0.0</modelVersion>
● <groupId>net.juggenova.sample</groupId>
● <artifactId>minimal</artifactId>
● <version>1.0</version>
</project>
–
How can this work?
●
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
14. The Super POM
Implicitely, all POMs inherit from the Super POM
●
see http://maven.apache.org/pom.html
–
Defines Super
●
POM
standard directory structure
–
default plugins & repo
–
your
where it is? inside mvn jars POM
–
how to check it?
–
mvn help:effective-pom
–
Convention over Configuration
●
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
15. The Super-POM
<repos itories >
<repos itory>
<id>central</id>
<name>Maven R epos itory S witchboard</name>
<url>http://repo1.maven.org /maven2</url>
</repos itory>
</repos itories >
<build>
<s ourceDirectory>s rc/main/java</s ourceDirectory>
<tes tS ourceDirectory>s rc/tes t/java</tes tS ourceDirectory>
<outputDirectory>targ et/clas s es </outputDirectory>
...
<res ources >
<res ource>
<directory>s rc/main/res ources </directory>
</res ource>
</res ources >
<tes tR es ources >...</tes tR es ources >
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
16. The Super-POM
<plug inManag ement>
<plug ins >
<plug in>
<artifactId>maven-as s embly-plug in</artifactId>
<vers ion>2.2-beta-1</vers ion>
</plug in>
<plug in>
<artifactId>maven-compiler-plug in</artifactId>
<vers ion>2.0.2</vers ion>
</plug in>
...
</plug ins >
</plug inManag ement>
</build>
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
17. Parent POM: make you own
Create a POM defining your project conventions
●
and tools
additional resource directories
–
default plugin configuration
–
e.g. custom configuration for maven-compiler-plugin
●
standard libraries
–
e.g. default spring version with
●
<dependencyManagement>
–
repositories and deployment config
–
e.g. your company repository with
●
<distributionManagement>
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
18. net.juggenova.sample:parent
<build>
<s ourceDirectory>java/s rc</s ourceDirectory>
...
<plug inManag ement>
<plug ins >
<plug in>
<g roupId>org .apache.maven.plug ins </g roupId>
<artifactId>maven-compiler-plug in</artifactId>
<config uration>
<s ource>1.6</s ource>
<targ et>1.6</targ et>
</config uration>
</plug in>
<plug in>
<artifactId>maven-s urefire-plug in</artifactId>
<config uration>...</config uration>
</plug in>
</plug ins >
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
19. Parent POM: use it
Reference the parent at the beginning of a POM
●
<parent>
–
● <artifactId>parent</artifactId>
● <groupId>net.juggenova.sample</groupId>
● <version>1.1</version>
● <relativePath>../parent</relativePath>
</parent>
–
Useful
●
if you have many similar projects/components
–
to separate responsibilities between senior and
–
junior developers
to encapsulate company-wide settings
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
20. Issues and suggestions
Main issue: children must reference parent
●
version explicitely
strong dependency! (as usual with inheritance)
–
there is no <version>LATEST</version> or
–
<version>[1.0,)</version> for the parent
if you change the parent, must update ALL children
–
So, avoid putting in the parent things that change
●
your project modules versions
–
developer/machine-specific settings
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
21. Suggestion
Separate things that change
from things that stay the same
Bruce Eckel
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
22. Dependency POMs
Maven2 supports compile (default)
● ●
transitive your libs
–
dependencies
test
●
controlled by a
–
junit, spring-test
–
consistent use of the
provided
<scope> tag ●
servlet-api
–
runtime
●
library minimize them!
log4j
your POM –
POM
system
●
tools.jar
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
23. Issues and suggestions
Good old encapsulation / minimize coupling
●
minimize dependencies
–
minimize visibility
–
Can also define codeless POMs, which only
●
contain a group of other dependencies
declare with
–
<packaging>pom</packaging>
used with
–
<dependency>...
–
● <type>pom</type>
</dependency>
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
24. Dependency Management
Several libraries are often used in many modules
●
commons-logging, spring, servlet-api,...
●
avoid repeating their version everywhere in POMs
–
Apply DRY & separation of concerns
●
which version to use in the parent/main POM
–
<dependencyManagement> (artifact, group, version)
●
whether to use it
–
<dependency> (artifact, group only) </dependency>
●
Tip: <dependencyManagement> is also effective in
●
overriding versions coming from transitive dependencies
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
25. Aggregation
Multimodule projects
●
every goal is repeated on
–
all modules by the reactor plugin
mvn clean
–
mvn compile
–
<modules >
modules can be
–
<module>client</module>
children of master <module>s erver</module>
<module>tes t</module>
but not necessarily </modules >
●
module
main POM
POM
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
26. Issues and suggestions
Issue: modules are referenced by folder name
●
beware when checking out or renaming
–
Issue: IDE plugin support is not perfect
●
m2eclipse requires manual refresh of dependencies
–
after configuration changes
also, different classpaths in eclipse and maven when
●
opening a multimodule project as a single project
netbeans only supports separate modules
–
Risk: pom proliferation (think of maintenance)
●
mvn modules vs SVN modules
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
27. Suggestion
Common Reuse Principle
Package together what is used/reused togehter
Robert C. Martin
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
28. Tip: create a “Master” POM
A “component list” POM
●
does not have its own code or settings
–
just an index of all modules to be built
–
it is NOT the parent of the modules
–
Example: the main spring pom which triggers the
●
build of
spring-core
–
spring-mvc
–
spring-test
–
...
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
29. Make it easy to create
new projects
Define an archetype
●
a customizable template for creating a kind of
–
projects (e.g. a web application)
defines POMs, project structure
●
Simple setup with
●
mvn archetype:create-from-project
–
customize with resource filtering
–
${property} references in the archetype
●
Use http://appfuse.org
●
library of pre-assembled archetypes
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
30. Part 3
Automate the entire build
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
31. Automate the entire build
Build means much more than compile!
●
Avoid manual steps!
●
copy, rename, deploy to a test server...
–
pass configuration information
–
Automatically process resources
●
copy and filter configuration files, CSS, HTML, properties
–
Share resources across projects
●
package them as jar/zip
–
reuse them in a war project with jar/zip/war overlays
–
http://maven.apache.org/plugins/maven-war-plugin/overlays.html
●
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
32. Assembly plugin
Creates zips/jars containing any kind of resource
●
project sources
–
common files
–
XSDs
●
● html/CSS
● templates
http://maven.apache.org/plugins/maven-assembly-plugin
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
33. Preview and test webapps
with the Jetty plugin
Run a webapp directly from source folders
●
mvn jetty:run
–
Advantages
●
very fast
–
resource changes are visible without restart
–
automatic redeploy after code changes
–
http://docs.codehaus.org/display/JETTY/Maven+Jetty+Plugin
–
Now a mvn glassfish:run goal is also available
●
full JEE 5.0 support
–
https://maven-glassfish-plugin.dev.java.net/
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
34. Automate deployment
Deploy to an application server with cargo
●
can even download, install and run a full Jboss
–
instance for testing purposes
http://cargo.codehaus.org/
–
Write custom ssh-based scripts using the ssh/scp
●
ant tasks within the maven-antrun-plugin
transfer files to test servers
–
launch administration scripts
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
35. Integrate with the IDE
E.g. Eclipse plugin (m2eclipse)
●
http://m2eclipse.sonatype.com
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
36. Use a group repository
Why your own?
●
Within a Team
●
deploy and share your project artifacts
–
so that other developers do not have to rebuild them
●
“mavenize” external jars which miss a POM
–
centrally configure and control which repositories
–
and artifacts are used
cache dependencies
–
available when internet connection breaks
●
faster download times
●
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
37. Sonatype Nexus repository
Powerful web-based console
●
and REST API
–
Lightweight
●
Easily upload artifacts via HTTP
●
Quickly search for jars
●
with the included index
–
Download from http://nexus.sonatype.org/
●
unzip and run!
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
38. settings.xml: Mirror definition
Team repository in addition to central
●
<repository>
–
● <id> set </id>
● <url> http://server:8080/repository </url>
</repository>
–
Team repository as a mirror of central (or others)
●
<mirror>
–
● <id> central </id>
● <url> http://server:8080/repository</url>
● <mirrorOf> central </mirrorOf>
</mirror>
–
Team repository as the only one
●
<mirror>
–
● <id> ... </id> <url> ... </url>
● <mirrorOf> * </mirrorOf>
</mirror>
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
39. Part 4
Troubleshooting
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
40. Build troubleshooting
Verify POM structure
●
mvn validate
–
Verify actually used dependencies
●
mvn dependency:tree
–
● -Dinclude=spring
Verify the full POM
●
mvn help:effective-pom
–
m2eclipse plugin
–
Moreover,
●
keep a consistent naming scheme to prevent typos
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
41. Debug/Log
Run mvn with
●
-e (print Exception stacktraces)
–
-X (print debug info)
–
POM information can be accessed at runtime!
●
META-INF/<group>/<artifact>/pom.properties
–
groupId
●
artifactId R es ource[] res ources = applicationC ontext
●
.g etR es ources (quot; clas s path*:M ETA-INF/mavenquot;+
version quot; /**/pom.properties quot; );
●
META-INF/../pom.xml for (R es ource r : res ources ) {
–
Properties p = new Properties ();
p.load(r.g etInputS tream());
full POM info
●
artifact = p.g etProperty(quot; artifactIdquot; );
vers ion = p.g etProperty(quot; vers ionquot; );
}
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
42. Add a timestamp to your builds
Automatically define a timestamp property
●
use it in resources or test properties
–
<plugin>
–
● <groupId>org.codehaus.mojo</groupId>
● <artifactId>buildnumber-maven-
plugin</artifactId>
● <executions> ... </executions>
● <configuration>
<format>{0,date,yyyy-MM-dd HH:mm:ss}</format>
●
<items>
●
<item>timestamp</item>
●
</items>
●
● </configuration>
</plugin>
http://mojo.codehaus.org/buildnumber-maven-plugin
●
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
43. Part 5
Keep the build fast
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
44. Keep the build fast
Ideally, zero-time build
●
http://blog.carbonfive.com/2008/09/java/make-the-
–
things-you-do-often-fast-and-easy
The more often a task is performed, the more its
●
optimization improves developer productivity
save time for actual project work
–
Run maven on the latest JDK
●
benefit from JDK 1.6 fast startup times/optimizations
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
45. Eclipse compiler
Faster than JDK's javac
●
also provides more warnings (unused variables, generics
–
misuse...)
<plugin>
–
<artifactId>maven-compiler-plugin</artifactId>
–
<configuration>
–
<compilerId>eclipse</compilerId>
–
</configuration>
–
<dependencies>
–
<dependency>
–
<groupId>org.codehaus.plexus</groupId>
●
<artifactId>plexus-compiler-eclipse</artifactId>
–
<version>1.5.2</version>
–
</dependency>
–
</dependencies>
–
</plugin>
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
46. Unit test vs integration tests
Run unit tests often
●
must not take half an hour! or else developers will
–
just skip them
-Dmaven.test.skip=true
–
Separate unit tests from integration tests
●
unit tests in every project/module
–
fast
●
run at every build (within mvn install)
●
integration and acceptance tests in dedicated
–
module
run after major changes, and/or on build servers
●
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
47. Remove useless build elements
POM, plugin and dependency list keeps growing
●
Periodically review the POM
●
Remove unused dependencies
–
copying them around means more slow disk accesses
●
mvn dependency:analyze
●
Remove unused plugins
–
move them to optionally-activated profiles
●
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
48. Speed-up day-to-day tasks
Define a default goal
●
<defaultGoal>compile</defaultGoal>
–
then just run
–
mvn
–
Use the right goal
●
avoid a full mvn install if you just need a mvn test
–
Define shell aliases for common tasks
●
Use a CI server that reads and reuses mvn
●
configuration such as hudson
https://hudson.dev.java.net
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
49. Incrementally build large
multimodule projects
Reactor plugin
●
http://maven.apache.org/plugins/maven-reactor-plugin/
–
manages dependencies and build order
–
resume a build from the last failed module
●
mvn reactor:resume
–
build a project and all its dependencies
●
mvn reactor:make
–
build all modules which have an SVN status of changed
●
mvn reactor:make-scm-changes
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
50. References
Maven official site
●
http://maven.apache.org
–
Best online book
●
Maven 2 – The Definitive Guide
–
http://books.sonatype.com/maven-book
–
JavaWorld articles
●
Introduction to maven2
–
http://www.javaworld.com/javaworld/jw-12-2005/jw-1205-maven.html
●
POM
–
http://www.javaworld.com/javaworld/jw-05-2006/jw-0529-maven.html
●
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009
51. Thanks for your attention!
Learn more at
●
http://www.carlobonamico.com/blog
–
http://juggenova.net
–
presentations, demos, code samples
●
Play with the samples
●
http://juggenova.net/code-samples/
–
Contact me at
●
carlo.bonamico@gmail.com
–
Related reading: Continuous Integration with Hudson
●
http://www.slideshare.net/carlo.bonamico/continuous-integration-with-hudson
–
Carlo Bonamico - carlo.bonamico@gmail.com – JUG Genova
Javaday Roma III Edizione – 24 gennaio 2009