How to update release artifacts in Maven? - maven

I have the following case:
- Maven project compiles fine on one machine where artifact A (release one) exists in that machine's local Maven repository,
- artifact A was removed from the remote repository.
How can we be sure that the project builds fine on a new machine where local Maven repository is empty?

Try the install task install-file to put the jar into your local repo from your local hard drive:
mvn install:install-file -Dfile=<path-to-file>
See maven.apache.org for more details.

Few cases :
One, if you own artifact A and use <repository> to keep the versions in sync. You can anytime rebuild your project on the new machine to fetch the artifact.
Second, If artifact A is owned by you and you didn't use repositories until now, you can simply bump up its version and deploy it on the remote server(<repository>) and consume the new version on the machine where you want to. Use <repositories> in your pom.xml to specify the remote path as follows :
<repository>
<id>clojars</id>
<name>Clojars Maven Repository</name>
<url>http://clojars.org/repo/</url>
</repository>
Third, if you don't own the artifact A and it exists in a public maven central repositories, all you need to do is rebuild the correct dependency to fetch it over the net.
Worst case, the artifact A used is owned by you and doesn't exist in a public central repository. You can still copy-paste the jar file using any mode and move it to the machine's /m2/repository where you require it. But do note in such case you shouldn't reach this case ever again.
Also in the last case, you can copy it into your project and use it as suggested by #Adam
mvn install:install-file -Dfile=<path-to-file>

Related

How does Maven use external dependencies in your own project?

I had a quick question on how Maven configures dependencies in the pom.xml file. In my project's pom.xml file, when I add a dependency tag and provide the artifact id and group id, how/where does Maven store those dependencies to use in my project? Since Maven is a central repository, does Maven use the internet to pull the dependencies or does it download the repositories in your local machine and use it from there?
Maven repository is of three types :
Local
Central
Remote
Maven first starts finding in Local Repository created by Maven in %USER_HOME% directory. To override the default location, mention another path in Maven settings.xml file available at %M2_HOME%\conf directory.
When Maven does not find any dependency in a local repository, it starts searching in the Central repository.
Sometimes, Maven does not find a mentioned dependency in the central repository as well. It then stops the build process and output error message to console. To prevent such situation, Maven provides a concept of Remote Repository, which is the developer's own custom repository containing required libraries or other project jars.
For user-defined jars, you also need to specify :
<repositories>
<repository>
<id>in-project</id>
<name>Name_of_your_project</name>
<url>file://${project.basedir}/libs</url>
</repository>
</repositories>
In standard configuration, Maven looks first in your local Maven repository (.m2/repository in your user directory) and if it does not find anything, it tries to download from the remote repositories that you specified. If you did not specify any, it will use MavenCentral.
When Maven finds something, it will be downloaded to the local Maven repository for future use. If you have -SNAPSHOT dependencies, they will be updated regularly.

Jenkins - deploy artifacts to Maven repository

I have a basic Springboot Maven project and I want to be able to deploy it and make API call as it works in local.
I have a remote linux machine with Jenkins on it, and I am able to make a build of my application correctly. Now I want to deploy this build in the same linux machine, in a certain folder /deploy.
Right now I have added a Post Build Action on Jenkins to Deploy artifacts to Maven repository having the following parameters:
and right now I did not make any changes to my pom.xml or my maven settings.xml.
The error that I get is the following:
[INFO] Deployment in http://localhost:8080/deploy (id=test2,uniqueVersion=true)
Deploying the main artifact reag.login-0.0.1-SNAPSHOT.jar
Downloading: http://localhost:8080/deploy/reag/login/reag.login/0.0.1-SNAPSHOT/maven-metadata.xml
ERROR: Failed to retrieve remote metadata reag.login:reag.login:0.0.1-SNAPSHOT/maven-metadata.xml: Could not transfer metadata reag.login:reag.login:0.0.1-SNAPSHOT/maven-metadata.xml from/to deploymentRepo (http://localhost:8080/deploy): Access denied to: http://localhost:8080/deploy/reag/login/reag.login/0.0.1-SNAPSHOT/maven-metadata.xml , ReasonPhrase:Forbidden.
org.apache.maven.artifact.deployer.ArtifactDeploymentException: Failed to retrieve remote metadata reag.login:reag.login:0.0.1-SNAPSHOT/maven-metadata.xml: Could not transfer metadata reag.login:reag.login:0.0.1-SNAPSHOT/maven-metadata.xml from/to deploymentRepo (http://localhost:8080/deploy): Access denied to: http://localhost:8080/deploy/reag/login/reag.login/0.0.1-SNAPSHOT/maven-metadata.xml , ReasonPhrase:Forbidden.
The machine where I'm working is protected by username and password, I tried to put them in the settings.xml file but nothing changes. Does anyone know which are the steps to make this process work?
Thanks in advance.
Local artifact deployment is done by mvn clean install.
The install goal copies your artifact into your local maven repository (Default [USER_HOME]/.m2/repository).
If you want to deploy your artifact to another service, like a Nexus Maven Repository, then you need to deploy and also provide the credentials for that machine in your settings.xml, or even better setup a private/public key authentication for the machines.
I think Jenkins is trying to do the remote deploy, which is only working if you run a Maven Repository on your machine (like the Nexus)
"deploy" in Maven parlance means "upload the built artifacts and their metadata (such as pom files) to a repository manager.
It does not mean "copy the artifact to any location that you want".
Therefore as #funfried mentioned, you need to actually have a repository manager running.
If that is the case then the following is how you set up the maven configuration.
Maven links credentials to servers via the id element.
Your settings.xml file would have your credentials setup something like:
<servers>
<server>
<id>newhope-nexus</id>
<username>steve</username>
<password>{1T7Jmp/PBoQH4cvFjZDTaDe/F/Z+D9rJ925rf+3H1LY=}</password>
</server>
</servers>
And then your project model (project pom or parent pom) should define it's distributionManagement:
<distributionManagement>
<repository>
<id>newhope-nexus</id>
<url>http://newhope:8081/nexus/content/repositories/releases/</url>
</repository>
<snapshotRepository>
<id>newhope-nexus</id>
<url>http://newhope:8081/nexus/content/repositories/snapshots/</url>
</snapshotRepository>
</distributionManagement>
Note that the ids all match.
The mvn deploy from Jenkins should then work correctly.

How to configure maven to copy dependencies from central repo to local repository mirror (not local repo)

All
Need to get maven to copy central dependencies to local filesystem repository mirror. Can't work out how to do this in maven (3.3.1).
We have:
[1] maven central, which for the UK is: "http://uk.maven.org/maven2"
[2] local remote filesystem repository mirror: "c:/mylocalRepository"
[3] local repo "c:/users/myuser/.m2/repository"
Version of maven is 3.3.1 (doing a migration from 2.0.10).
We need to run our system without connecting to central (behind firewalls) and also without using a repository manager (Nexus, Archiva or the like) - it's something we would like to change but cannot change our infrastructure immediately. Please don't reply just saying do this.
Therefore we need our dependencies in a local file system that maven will then be use as a mirror of central.
I can't find a way to configure maven to build this - I'm getting dependencies - jar + pom and then using
To install jars:
mvn org.apache.maven.plugins:maven-deploy-plugin:2.8.2:deploy-file
-Durl="file:///{repositoryPath}"
-DrepositoryId="InternalRepo"
-Dfile="{jarFile}"
-DpomFile="{pomFile}"
-DrepositoryLayout=default
-DgroupId={groupId}
-DartifactId={artifactId}
-Dversion={version}
-Dpackaging=jar
-s "C:/apache-maven-3.3.1/conf/settings_centralRepo.xml"
To install Poms:
mvn org.apache.maven.plugins:maven-deploy-plugin:2.8.2:deploy-file
-Durl="file:///{repositoryPath}"
-DrepositoryId="InternalRepo"
-Dfile="{pomFile}"
-DpomFile="{pomFile}"
-DrepositoryLayout=default
-DgroupId={groupId}
-DartifactId={artifactId}
-Dversion={version}
-Dpackaging=pom
-s "C:/apache-maven-3.3.1/conf/settings_centralRepo.xml"
Ideally would like a configuration that we could put in the parent pom that would trigger all dependencies to be copied over. However the documentation implies this is for build artifacts rather than dependencies. There's usually a way in maven, but it can be hard to find.
Any help much appreciated - I've currently jury-rigged a script to do this and it tedious and labour intensive.

Convert android library project to maven artifact for use in intellij idea

I am using Maven for dependency management in my android projects and its great.
I want to use a 3rd party android library project (https://github.com/emilsjolander/StickyListHeaders) and rather than download the directory and add the dependency manually I want to change the StickyListHeaders project into a maven project (an apklib?).
How do I create the maven artefact.
Is there anything I can commit back to github in order to allow the author to publish there project on maven central?
After creating the artefact, should I set up a local maven repo such as nexus in order to share the artefact with the team.
This project already has a pom.xml, so to create the artifact you only have to do a mvn package.
Here there is a detailed explanation of how to publish in Maven Central Respository.
When I have to use a non-maven library in my Maven projects I use a "folder repository". By "folder respository" I mean that I use one folder of my project (lib or repo sometimes) as a local repository.
For this you have to config a repository like that:
<repository>
<id>project</id>
<name>Project Maven Repository</name>
<layout>default</layout>
<url>file://${project.basedir}/lib</url>
</repository>
And then you can deploy the artifact into your local repository as this:
mvn install:install-file -Dfile=path-to-your-artifact-jar \
-DgroupId=your.groupId \
-DartifactId=your-artifactId \
-Dversion=version \
-Dpackaging=jar \
-DlocalRepositoryPath=path-to-specific-local-repo
Tip: When my project has multiple maven modules, then I use file://${project.basedir}/../lib as a repository url.

How do I add an artifact to a local maven repository so that it will properly reference its own set of dependencies?

I am developing an application that depends on a number of legacy JAR files and I want the project to build straight out of version control without other users having to install these JARs in their local repository. I cannot add them to the corporate repository so I have created a repository that is local to this project and I have added these JARs to that repository using maven-install-plugin:install-file and setup the repository entry in the POM file so it knows to search the local repository.
This works exactly the way I want...up to a point. The problem is that most of these legacy JAR files have their own set of dependencies. I would like for them to work just like other artifacts that have their own set of dependencies so that maven can resolve everything and include all the necessary files but I can't find a way to do this with any maven-install-plugin:install-file options (or any other maven commands/plugins). I am pretty new at maven so I am probably just ignorant on this point.
As a work around, I attempted to go into the local repository directory and manually edit the POM file for the artifact to include the dependencies. This didn't cause any errors but it is also not pulling in those dependencies.
Can someone out there give me a clue?
The maven-install-plugin:install-file goal has a pomFile attribute. You can use this to specify a POM file for your legacy jar. You would create a POM file that points to all of the dependencies by artifactId in the <dependencies> section. If you have a remote nexus repository you can use the admin screen for the repository to deploy a jar.
Once you edit POM files in your project specific repository, host it as maven repo using Maven Repository Managers (like sonatype nexus). Add your project nexus repo as one of the maven repo in project pom.xml as below
<repositories>
<repository>
<id>my-project-mvn-repo</id>
<name>my-project-mvn-repo</name>
<url>http://<your project maven repo URL here></url>
</repository>
<repositories>
Now all developers should be able to make build. The legacy jar files POM contains dependency. Maven should take care of automatically pulling dependent jars on developer's workspace.

Resources