Deploying to OSSRH with Apache Maven - Introduction⚓︎
Apache Maven started the Central Repository by publishing all its components and required dependencies into the Central Repository - back then known as Maven Central. Maven is pre-configured to connect to the Central Repository and download everything it needs including your project dependencies from the Central Repository.
We recommend to use stable versions of Maven 3 since other versions of Apache Maven including all versions of Maven 2 and Maven 1 have reached their end of life and are no longer supported by the project maintainers. There are known issues regarding signing components and other aspects with a number of older Maven releases.
A Maven build configuration can be set up to fulfill all the requirements in various ways and we will discuss all applicable details below.
Note that while these instructions are considered best practice by Sonatype, opinions differ and you can find links to other documentation in the Additional Information section below.
Besides an Apache Maven installation, you have to have a GPG client installed and on your command line path as required by the Maven GPG plugin. For more information, please refer to http://www.gnupg.org/ as well as the plugin documentation and below.
- Requirements and Signing Tips
- First Deployments
- Project Object Model POM?!
- Javadoc, Sources and Signing
Distribution Management and Authentication⚓︎
In order to configure Maven to deploy to the OSSRH Nexus Repository Manager with the Nexus Staging Maven plugin you have to configure it like this
Note: As of February 2021, all new projects began being provisioned on https://s01.oss.sonatype.org/. If your project is not provisioned on https://s01.oss.sonatype.org/, you will want to login to the legacy host https://oss.sonatype.org/.
<distributionManagement> <snapshotRepository> <id>ossrh</id> <url>https://s01.oss.sonatype.org/content/repositories/snapshots</url> </snapshotRepository> </distributionManagement> <build> <plugins> <plugin> <groupId>org.sonatype.plugins</groupId> <artifactId>nexus-staging-maven-plugin</artifactId> <version>1.6.7</version> <extensions>true</extensions> <configuration> <serverId>ossrh</serverId> <nexusUrl>https://s01.oss.sonatype.org/</nexusUrl> <autoReleaseAfterClose>true</autoReleaseAfterClose> </configuration> </plugin> ... </plugins> </build>
Since OSSRH is always running the latest available version of Sonatype Nexus Repository Manager, it is best to use the latest version of the Nexus Staging Maven plugin.
Alternatively if you are using the Maven deploy plugin, which is the default
behavior, you need to add a full
<distributionManagement> <snapshotRepository> <id>ossrh</id> <url>https://s01.oss.sonatype.org/content/repositories/snapshots</url> </snapshotRepository> <repository> <id>ossrh</id> <url>https://s01.oss.sonatype.org/service/local/staging/deploy/maven2/</url> </repository> </distributionManagement>
The above configurations will get the user account details to deploy to OSSRH
from your Maven
settings.xml file, usually placed in
~/.m2. A minimal
settings with the authentication is:
<settings> <servers> <server> <id>ossrh</id> <username>your-jira-id</username> <password>your-jira-pwd</password> </server> </servers> </settings>
Note how the
id element in the server element in
settings.xml is identical to
id elements in the
repository element as well as
serverId configuration of the Nexus Staging Maven plugin
Javadoc and Sources Attachments⚓︎
To get Javadoc and Source jar files generated, you have to configure the javadoc and source Maven plugins.
<build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-source-plugin</artifactId> <version>2.2.1</version> <executions> <execution> <id>attach-sources</id> <goals> <goal>jar-no-fork</goal> </goals> </execution> </executions> </plugin> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-javadoc-plugin</artifactId> <version>2.9.1</version> <executions> <execution> <id>attach-javadocs</id> <goals> <goal>jar</goal> </goals> </execution> </executions> </plugin> </plugins> </build>
GPG Signed Components⚓︎
The Maven GPG plugin is used to sign the components with the following configuration.
<build> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-gpg-plugin</artifactId> <version>1.5</version> <executions> <execution> <id>sign-artifacts</id> <phase>verify</phase> <goals> <goal>sign</goal> </goals> </execution> </executions> </plugin> </plugins> </build>
It relies on the gpg command being installed and the GPG credentials being available e.g. from settings.xml. In addition you can configure the gpg command in case it is different from gpg. This is a common scenario on some operating systems.
<settings> <profiles> <profile> <id>ossrh</id> <activation> <activeByDefault>true</activeByDefault> </activation> <properties> <gpg.executable>gpg2</gpg.executable> <gpg.passphrase>the_pass_phrase</gpg.passphrase> </properties> </profile> </profiles> </settings>
If you need more help setting up and configuring GPG, please read our detailed instructions.
Nexus Staging Maven Plugin for Deployment and Release⚓︎
The Nexus Staging Maven Plugin is the recommended way to deploy your components to OSSRH and release them to the Central Repository. To configure it simply add the plugin to your Maven pom.xml.
<build> <plugins> ... <plugin> <groupId>org.sonatype.plugins</groupId> <artifactId>nexus-staging-maven-plugin</artifactId> <version>1.6.7</version> <extensions>true</extensions> <configuration> <serverId>ossrh</serverId> <nexusUrl>https://s01.oss.sonatype.org/</nexusUrl> <autoReleaseAfterClose>true</autoReleaseAfterClose> </configuration> </plugin>
If your version is a release version (does not end in -SNAPSHOT) and with this setup in place, you can run a deployment to OSSRH and an automated release to the Central Repository with the usual:
mvn clean deploy
With the property autoReleaseAfterClose set to false you can manually inspect the staging repository in the Nexus Repository Manager and trigger a release of the staging repository later with
If you find something went wrong you can drop the staging repository with
Please read Staging Releases in the Repository Manager 2 documentation for more information about the Nexus Staging Maven Plugin.
In the past all the plugin configuration and other setup was managed by a Maven parent POM with the latest
org.sonatype.oss:oss-parent:9. This project leaked SCM, URL and other details and its usage is
discouraged. Maintenance of the project has stopped and it no longer works with latest tooling such as Maven versions
or Java versions. If desired, please manage your own organization-level POM in a similar manner.
Using a Profile⚓︎
Since the generation of the javadoc and source jars as well as signing components with GPG is a fairly time consuming process, these executions are typically isolated from the normal build configuration and moved into a profile. This profile is then in turn used when a deployment is performed by activating the profile.
<profiles> <profile> <id>release</id> <build> ... javadoc, source and gpg plugin from above ... </build> </profile> </profiles>
Performing a Snapshot Deployment⚓︎
Snapshot deployment are performed when your version ends in
-SNAPSHOT . You do
not need to fulfill the requirements when performing snapshot deployments and can simply run
mvn clean deploy
on your project.
SNAPSHOT versions are not synchronized to the Central Repository. If you wish your users to consume your SNAPSHOT versions, they would need to add the snapshot repository to their Nexus Repository Manager, settings.xml, or pom.xml. Successfully deployed SNAPSHOT versions will be found in https://s01.oss.sonatype.org/content/repositories/snapshots/
Performing a Release Deployment⚓︎
In order to perform a release deployment you have to edit your
version in all
your POM files to use release versions. This means that they can not end in
In addition plugin and dependency declarations can also not use snapshot
versions. This ensures that you only depend on other released components.
Ideally they are all available in the Central Repository. This ensures that your
users can retrieve your components as well as your transitive dependencies from
the Central Repository.
The change of the versions for your project, and the parent references in a multi module setup, can be performed manually or with the help of the Maven versions plugin.
mvn versions:set -DnewVersion=1.2.3
Once you have updated all the versions and ensured that your build passes
without deployment you can perform the deployment with the usage of the
mvn clean deploy -P release
This process is completely independent from your workflow with your SCM system. If you want to ensure that a specific version in the Central Repository corresponds to a specific revisions in your SCM system, which is a good practice, you can either perform the commits manually in a flow similar to
- Develop, develop, develop
- Commit any outstanding changes
- Verify build passes
- Update versions to release version
- Commit release version
- Run deployment
- Update versions to next snapshot version
- Commit new snapshot version
- Develop, develop, develop and rinse and repeat
or you can automate it with a script of your choice including a configuration running on a CI server or you can use the Maven release plugin, documented in the following.
Performing a Release Deployment with the Maven Release Plugin⚓︎
The Maven Release Plugin can be used to automate the changes to the Maven POM files, sanity checks, the SCM operations required and the actual deployment execution.
The configuration for the Maven release plugin should include disabling the
release profile that is part of the Maven Super POM, since we are using our own
profile, and specify the deploy goal together with the activation of our
<plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-release-plugin</artifactId> <version>2.5.3</version> <configuration> <autoVersionSubmodules>true</autoVersionSubmodules> <useReleaseProfile>false</useReleaseProfile> <releaseProfiles>release</releaseProfiles> <goals>deploy</goals> </configuration> </plugin>
With the SCM connection configured correctly you can perform a release deployment to OSSRH with
mvn release:clean release:prepare
by answering the prompts for versions and tags, followed by
This execution will deploy to OSSRH and release to the Central Repository in one go, thanks to the usage of the Nexus Staging Maven Plugin with autoReleaseAfterClose set to true.
Manually Releasing the Deployment to the Central Repository⚓︎
If you are using autoReleaseAfterClose set to false you or you are using the default Maven deploy plugin, you can inspect and potentially release the deployed artifacts manually
Alternatively if you have deployed with the Nexus Staging Maven Plugin, and the deployment succeeded, you can release the repository directly on the command line. Immediately after the deployment a properties file in the target directory contains all the information required and you can simply release the staging repository with
If you have been running the deployment as part of a release done with the Maven release plugin, the deployment was done from the tag in your version control system checked out into target/checkout so you have to run the Nexus Staging plugin from there:
mvn release:perform ... cd target/checkout mvn nexus-staging:release
You can configure this goal to be run automatically as part of your release deployment with the release plugin by adding it as a goal execution after deploy.
<plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-release-plugin</artifactId> <configuration> <goals>deploy nexus-staging:release</goals> ...
- Using a local repo manager and OSSRH. An approach to using OSSRH for the occasional deployment of a component.
- Example project and video showing full project creation and deployment, part of the video series Empowering Releases with the Nexus Staging Suite
- Blog post with example project with documentation and video showcasing deployment with Bitbucket Pipelines