Corporate https maven2 repositories
So you started using maven / maven2 in your organization. Now you need a place to deploy your company specific artifacts. You also don’t want to depend on an external repository to perform your build.
So setting up a corporate repository is a natural step. Unfortunately, I’ve found that the information describing how to do this is scattered around several places. So here’s a single page version that works for us.
The following short guideline explains how to deploy artifacts to a remote server using scp and retrieve them using https.
Note: I am using apache 2.0.55 under Linux on the server and maven 2.0.2 and SDK 1.5 under Linux on the client. In this example, the serve’s named dev.domaine.com. There are some variations for Windows.
Note2: it is possible to setup your system differently. maven2 is flexible. This just describe one way to make it work, which was I believe, the simplest and most flexible way for us to achieve our goal.
Deploying artifacts on your server
Most of this information comes from this page. My preferred setup is to use scp and an ssh agent for handling my keys.
- on your server, create a place where to put your artifacts. E.g.
/home/m2/public_html - use suitable permissions for developers to be able to deploy artifacts there and for your web server to be able to serve the files later on
- 2 cases:
- If you have control over the pom.xml of the project you are trying to deploy, deploying your artifact is easy. Just add the following information to your project’s pom.xml:
<distributionmanagement> <!-- use the following if you're not using a snapshot version. --> <repository> <id>ssh-repo</id> <name>Repository Name</name> <url>scp://host/path/to/repo</url> </repository> <!-- use the following if you ARE using a snapshot version. --> <snapshotrepository> <id>ssh-repo</id> <name>Repository Name</name> <url>scp://host/path/to/repo</url> </snapshotrepository> </distributionmanagement>Then add an entry in your
~/.m2/settings.xml:<settings> ... <servers> ... <server> <id>ssh-repo</id> <username>...</username> ... </server> </servers> ... </settings>And finally, deploy doing
mvn deploy. - When you don’t have control over the pom, you will need to specify the repository related information on the command line. You will use the
deploy:deploy-filegoal.- If you already have a pom for your artifact, it is best to instruct the plugin to pick the information from the pom. You will end up doing something like:
mvn deploy:deploy-file -Durl=scpexe://dev.domaine.com/home/m2/public_html -DrepositoryId=ssh-repo pomFile=pom.xml -Dfile=the.jar - If you don’t have a pom, you will have to specify all the other arguments:
mvn deploy:deploy-file -DgroupId=... -DartifactId=... -Dversion=... .... -Durl=scpexe://dev.domaine.com/home/m2/public_html -DrepositoryId=ssh-repo pomFile=pom.xml -Dfile=the.jar
- If you already have a pom for your artifact, it is best to instruct the plugin to pick the information from the pom. You will end up doing something like:
- In both cases you will need to add a
<server>entry to yoursettings.xmlfile, as specified above.
- If you have control over the pom.xml of the project you are trying to deploy, deploying your artifact is easy. Just add the following information to your project’s pom.xml:
Make these artifacts accessible from your client
- Generate/sign an ssl certificate for your server. On Linux, it will probably be stored somewhere like
/etc/ssl/apache2/server.crt - Make sure your repository directory is available under apache. E.g.
Alias /m2 /home/m2/public_html <directory /home/m2/public_html> AllowOverride None Options Indexes FollowSymLinks Order allow,deny .... </directory>
- Protect this directory using usual Apache access rights management tools
- Test. Point your browser to https://dev.domaine.com/m2. The browser should ask for username/password. You may or not need to prepend a slash to your url depending on your apache configuration.
Let’s make this work with maven2!
- Import your server ssl certificate into your JVM keystorre. As root:
keytool -keystore $JAVA_HOME/jre/lib/security/cacerts -import -file server.crt. You will need the keystore password to modify it. By default this password is ‘changeit‘. Note: If you change SDK, you will need to redo this operation. Note: if you already have a certificate under the “mykey” alias, you may have the following error:
keytool error: java.lang.Exception: Certificate not imported, aliasalready exists
In that case, import the other one under a new alias (-alias newalias) or remove your old certificate (keytool -keystore $JAVA_HOME/jre/lib/security/cacerts -delete -alias mykey). - on your project: add a repository to your pom:
<repository> <id>https-repo</id> <name>My Company Repository</name> <url>https://dev.domaine.com/m2</name> </repository> - if you host plugins on your corporate repository, you may also need to add something like:
<pluginRepositories> ... <pluginRepository> <id>https-repo</id> <url>https://dev.domaine.com/m2</url> </pluginRepository> </pluginRepositories> - Modify your ~/.m2/settings.xml. That’s where you will add your personnal authentication information:
<settings> ... <servers> ... <server> <id>https-repo</id> <username>...</username> <password>...</password> </server> </servers> ... </settings> - clean up your local maven repository to test downloading from the remote one. E.g.
rm ~/.m2/repository/com/domaine/... - Test building your project. e.g.
m2 install.
If you have any issue and you think it might be ssl related, enable debugging using the javax.net.https unsupported option. You might want to try m2 -Djavax.net.https=ssl install. -Djavax.net.https=all for more info and -Djavax.net.https=help for usage information.
Troubleshooting and common mistakes
- Note: trying to use a a full basic auth url (
https://user:password@dev.domaine.com/m2), either in the pom or on the command line won’t work. You have to externalize your login/password into an external file - if you are deploying a multi-project, and one module is not deployed and you get a generic error that says something like:
Failed to configure plugin parameters for: org.apache.maven.plugins:maven-deploy-plugin:2.1 check that the following section of the pom.xml is present and correct: <distributionManagement> <!-- use the following if you're not using a snapshot version. --> <repository> <id>repo</id> <name>Repository Name</name> <url>scp://host/path/to/repo</url> </repository> <!-- use the following if you ARE using a snapshot version. --> <snapshotRepository> <id>repo</id> <name>Repository Name</name> <url>scp://host/path/to/repo</url> </snapshotRepository> </distributionManagement> Cause: Class 'org.apache.maven.artifact.repository.ArtifactRepository' cannot be instantiated [INFO] ---------------------------------------------------------------------------- [...] Caused by: java.lang.InstantiationException: org.apache.maven.artifact.repository.ArtifactRepository at java.lang.Class.newInstance0(Class.java:335) at java.lang.Class.newInstance(Class.java:303) at org.codehaus.plexus.component.configurator.converters.AbstractConfigurationConverter.instantiateObject(AbstractConfigurationConverter.java:111 ) ... 24 morethen be sure to follow the recommendations in the error log. A classical mistake is to have forgotten to inherit the module’s pom from the parent pom where this information was stored.
- when deploying a module, maven searches the repositories referenced in the pom for the dependencies of the module. I think the idea is to identify whether the required dependency versions are already deployed. If you try to deploy a multi project whose modules depend on each other, you will probably have to make sure that the target repository is listed in the
<repositories>section of your pom, otherwise the deploy operation might fail, not finding a suitable version for your module, even though the dependency might just have been uploaded there. Maven has no way to know that fact (especially as you refer to a repository differently when you upload or retrieve information from it, and also because each module deployment is treated independently of the others, even in the case of a multi-project).
Last advice: you might want to have one repository for snapshots and one for releases. That might simplify backing up operations on the server if you only want to backup your releases.
Voila! m2 should now download your artifacts from new your shiny corporate repository. Good luck!
update: added information on how to update the imported certificate.
March 5th, 2006 at 1:18 pm
[…] Corporate https maven2 repositories (tags: maven2 maven) […]
March 7th, 2006 at 11:22 pm
[…] Corporate https maven2 repositories (tags: maven java) […]
June 5th, 2006 at 10:31 pm
[…] In our projects we also have dependencies that are not available from the maven repository, like the sjsxp-1.0.jar. We have an internal repository for these kind of jars. To install jars and generate the pom.xml for these kind of jars you can do the following (thanks to this execellent blog): […]
October 27th, 2006 at 6:57 am
For debugging the HTTPS connection, the command to use is “m2 -Djavax.net.debug=ssl:handshake install”, not “m2 -Djavax.net.https=ssl install”
October 28th, 2006 at 8:18 pm
[…] Pauses Café » Blog Archive » Corporate https maven2 repositories (tags: coffeebreaks pauses cafe repository artifact maven2 deployment blog post) […]
September 3rd, 2008 at 4:35 pm
Thanks for this Article, It solve many issues I had with maven. Please do write such informative articles…
Thanks a lot.