I am trying to use external library inside my maven project. Since I want the project to build out of the box on any machine, I don\'t want to use mvn install
solut
Maven will never read the jar present inside any library folder. You must first understand how maven works. The only place where maven looks for jar is the localRepository (.m2)
, if absent it searches the other repository, mentioned in your POM.xml
The previous answerer (and one commenter) pointed out, that maven looks within the local project-repository only once, and on subsequent builds it gets the cached jar from the .m2-repository.
I just found a workaround for the need to increment the version number (e.g. on small changes of a dev-library):
First reinstall the jar into your local project-repository:
mvn install:install-file -DlocalRepositoryPath=repo -DcreateChecksum=true -Dpackaging=jar -DgroupId=com.johndoe.dev -DartifactId=Helpers -Dversion=0.1 -Dfile=C:/path/to/helpers.jar
(Where -Dfile could point to an external Project which produces the helpers.jar)
Then purge just this specific artifact in the .m2-repository:
mvn dependency:purge-local-repository -DmanualInclude=com.johndoe.dev:Helpers:0.1
(With com.johndoe.dev as the GroupId, Helpers as the ArtifactId and the same version installed in the previous step)
Executing the latter step, maven rebuilds the artifact inside .m2 using your local project-repository jar-file.
Alternative and maybe dirty variant: Just copy helpers.jar to C:\Users\johndoe\.m2\repository\com\johndoe\dev\Helpers\0.1\Helpers-0.1.jar (don't know about linux as I haven't used mave there).
If you use a repository for this, then Maven will copy the JAR once into it's local repository (usually in $HOME/.m2/repository/
). Unless the version number changes, Maven won't consider this file to have changed and it won't copy it. Note that the version number is the only thing that Maven looks at; it doesn't care about checksums or file sizes or dates.
Incidentally, snapshots are assigned a version number internally for just this purpose: So that Maven can internally notice that a snapshot has been updated.
I suggest to use a system dependency instead. That way, the actual JAR is going to be added to the classpath (without any copying or stuff). You also don't need to replicate a repo structure for this approach and it will clearly communicate your intent.
[EDIT] I understand that Maven handles dependencies with scope system
differently. I'm not sure whether this makes sense or not (if it uses the dependency to compile, it surely can use it to run?)
As I see it, you have these options:
Install the dependency into your libRepo
using deploy:deploy-file instead of copying it yourself. That should update the meta data in such a way that Maven will copy it again when you run mvn install
again on the real project.
Note that file:install
doesn't work. The file plugin is used to access the local repository but you need to use the deploy plugin which knows how to update a shared / server repository.
Install the dependency into your local repo; I suggest to use a script for this that you can include in your project. That way, you avoid all the problems and it will be easy to set this up on a new machine.
Change the version number of the dependency but that's tedious and you might get into trouble when the real version number of the dependency changes.
Set up a local repo server for your company and deploy the dependency to it. That will take a few hours but a) you will get a local cache of all your dependencies, making your initial builds faster and b) it will make setup for additional developers much faster.