Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Maven building only changed files

Lets say i have module structure like below

     Modules
       ->utils
       ->domain
       ->client
       ->services
       ->deploy (this is at the module level)

Now to lauch the client i need to make a build of all the modules, i.e utils, domain, client, services, because i am loading the jars of all the above modules to fianlly lanch the client

And all the jars gets assembled in the module deploy.

My question is if i change anything in services for example, then is there a way when running a build from deploy maven could recognise it has to build only services and hence build it and deploy it in deploy folder?

like image 445
user1224036 Avatar asked Mar 14 '13 09:03

user1224036


4 Answers

If you only call "mvn install" without "clean", the compiler plugin will compile only modified classes.

like image 87
Puce Avatar answered Nov 17 '22 00:11

Puce


For GIT

mvn install -amd -pl $(git status | grep -E "modified:|deleted:|added:" | awk '{print $2}' | cut -f1 -d"/")

OR

In your .bashrc file (.bashrc can be found in home directory ~/.bashrc , or create it if doesn't exists) add the following function.

mvn_changed_modules(){
    [ -z "$1" ] && echo "Expected command : mvn_changed_modules (install/build/clean or any maven command)" && exit 0

        modules=$(git status | grep -E "modified:|deleted:|added:" | awk '{print $2}' | cut -f1 -d"/")

                if [  -z "$modules" ];
                then
                        echo "No changes (modified / deleted / added)  found"
                else
                        echo -e "Changed modules are : `echo $modules`\n\n"
                        mvn $1 -amd -pl $modules
                fi
}

**Then after re-starting your bash** (command prompt), you **can just use the following command** from the ROOT directory itself.

smilyface@machine>ProjectRootDir]$ mvn_changed_module install

How it works
As per the question mvn install -amd -pl services is the command when "some changes done in services module". So, first get module name from the changed file(s) and put it as input for mvn-install command

Say for example, below is a list of modified files (output of git status) -
services/pom.xml
services/ReadMe.txt
web/src/java/com/some/Name.java
Then services and web are the modules name which need to be build / compile / install

like image 21
smilyface Avatar answered Nov 17 '22 00:11

smilyface


Within a multi-module build you can use:

mvn -pl ChangedModule compile

from the root module will compile only the given ChangedModule. The compiler plugin will only compile the files which have been changed. But it can happen that the module you have changed would cause a recompile of other module which are depending on the ChangedModule. This can be achieved by using the following:

mvn -amd -pl ChangedModule compile

where the -amd means also make dependents. This will work without installing the whole modules into the local repository by a mvn install.

like image 15
khmarbaise Avatar answered Nov 17 '22 02:11

khmarbaise


After trying and using aforementioned advises, I've met following problems:

  1. Maven install (without clean) still takes a lot of time, which for several projects can be 10-20s extra time.
  2. Sebasjm's solution is fast and useful (I was using it for a couple of months), but if you have several changed projects, rebuilding them all the time (if you even hadn't change anything) is a huge waste of time

What really worked for me is comparing source modification dates against .jar modification in local repository. And if you check only for VCS changed files (see sebasjm's answer), then date comparison won't take noticeable time (for me it was less than 1s for 100 changed files). Main benefit of such approach is very accurate rebuild of only really changed projects. Main problem is doing modification date comparison is a bit more than one-liner script.

For those, who want to try it, but too lazy to write such script themself sharing my version of it: https://github.com/bugy/rebuilder (linux/windows). It can do some additional useful things, but the main idea and central algorithm is as explained above.

like image 4
buggy Avatar answered Nov 17 '22 01:11

buggy