Use Maven snapshots
A Maven snapshot is a special version of a Maven package that refers
to the latest production branch code. It is a development version that precedes the final
release version. You can identify a snapshot version of a Maven package by the suffix
SNAPSHOT
that's appended to the package version. For example, the snapshot
of version 1.1
is 1.1-SNAPSHOT
. For more information, see What is a SNAPSHOT version?
AWS CodeArtifact supports publishing and consuming Maven snapshots. Unique snapshots that use a time-based version number are the only snapshots that are supported. CodeArtifact doesn't support non-unique snapshots that are generated by Maven 2 clients. You can publish a supported Maven snapshot to any CodeArtifact repository.
Topics
Snapshot publishing in CodeArtifact
AWS CodeArtifact supports the request patterns that clients, such as mvn
, use
when publishing snapshots. Because of this, you can follow the documentation for your
build tool or package manager without having a detailed understanding of how Maven
snapshots are published. If you’re doing something more complex, this section describes
in detail how CodeArtifact handles snapshots.
When a Maven snapshot is published to a CodeArtifact repository, its previous version is preserved in a new version called a build. Each time a Maven snapshot is published, a new build version is created. All previous versions of a snapshot are maintained in its build versions. When a Maven snapshot is published, its package version status is set to Published
and the status of the build that contains the previous version is set to Unlisted
. This behavior applies only to Maven package versions where the package version has -SNAPSHOT
as a suffix.
For example, snapshot versions of a maven package called
com.mycompany.myapp:pkg-1
are uploaded to a CodeArtifact repository called
my-maven-repo
. The snapshot version is 1.0-SNAPSHOT
. So
far, no versions of com.mycompany.myapp:pkg-1
have been published. First,
the assets of the initial build are published at these paths:
PUT maven/
my-maven-repo
/com/mycompany/myapp/pkg-1/1.0-SNAPSHOT/pkg-1-1.0-20210728.194552-1.jar PUT maven/my-maven-repo
/com/mycompany/myapp/pkg-1/1.0-SNAPSHOT/pkg-1-1.0-20210728.194552-1.pom
Note that the timestamp 20210728.194552-1
is generated by the client publishing the snapshot builds.
After the .pom and .jar files are uploaded, the only version of
com.mycompany.myapp:pkg-1
that exists in the repository is
1.0-20210728.194552-1
. This happens even though the version specified
in the preceding path is 1.0-SNAPSHOT
. The package version status at this
point is Unfinished
.
aws codeartifact list-package-versions --domain
my-domain
--repository \my-maven-repo
--package pkg-1 --namespace com.mycompany.myapp --format maven { "versions": [ { "version": "1.0-20210728.194552-1", "revision": "GipMW+599JmwTcTLaXo9YvDsVQ2bcrrk/02rWJhoKUU=", "status": "Unfinished" } ], "defaultDisplayVersion": null, "format": "maven", "package": "pkg-1", "namespace": "com.mycompany.myapp" }
Next, the client uploads the maven-metadata.xml
file for the package
version:
PUT
my-maven-repo
/com/mycompany/myapp/pkg-1/1.0-SNAPSHOT/maven-metadata.xml
When the maven-metadata.xml file is uploaded successfully, CodeArtifact creates the
1.0-SNAPSHOT
package version and sets the
1.0-20210728.194552-1
version to Unlisted
.
aws codeartifact list-package-versions --domain
my-domain
--repository \my-maven-repo
--package pkg-1 --namespace com.mycompany.myapp --format maven { "versions": [ { "version": "1.0-20210728.194552-1", "revision": "GipMW+599JmwTcTLaXo9YvDsVQ2bcrrk/02rWJhoKUU=", "status": "Unlisted" }, { "version": "1.0-SNAPSHOT", "revision": "tWu8n3IX5HR82vzVZQAxlwcvvA4U/+S80edWNAkil24=", "status": "Published" } ], "defaultDisplayVersion": "1.0-SNAPSHOT", "format": "maven", "package": "pkg-1", "namespace": "com.mycompany.myapp" }
At this point, the snapshot version 1.0-SNAPSHOT
can be consumed in a build. While there are two versions of com.mycompany.myapp:pkg-1
in the repository my-maven-repo
, they both contain the same assets.
aws codeartifact list-package-version-assets --domain
my-domain
--repository \my-maven-repo
--format maven --namespace com.mycompany.myapp \ --package pkg-1 --package-version 1.0-SNAPSHOT--query 'assets[*].name' [ "pkg-1-1.0-20210728.194552-1.jar", "pkg-1-1.0-20210728.194552-1.pom" ]
Running the same list-package-version-assets
command as shown previously
with the --package-version
parameter changed to
1.0-20210728.194552-1
results in an identical output.
As additional builds of 1.0-SNAPSHOT
are added to the repository, a new
Unlisted
package version is created for each new build. The assets of
the version 1.0-SNAPSHOT
are updated each time so that the version always
refers to the latest build for that version. Updating the 1.0-SNAPSHOT
with
the latest assets is initiated by uploading the maven-metadata.xml
file for
the new build.
Consuming snapshot versions
If you request a snapshot, the version with the status Published
is
returned. This is always the most recent version of the Maven snapshot. You can also
request a particular build of a snapshot using the build version number (for example,
1.0-20210728.194552-1
) instead of the snapshot version (for example,
1.0-SNAPSHOT
) in the URL path. To see the build versions of a Maven
snapshot, use the ListPackageVersions API in the CodeArtifact API Guide and
set the status parameter to Unlisted
.
Deleting snapshot versions
To delete all build versions of a Maven snapshot, use the DeletePackageVersions API, specifying the versions that you want to delete.
Snapshot publishing with curl
If you have existing snapshot versions stored in Amazon Simple Storage Service (Amazon S3) or another artifact
repository product, you may want to republish them to AWS CodeArtifact. Because of how CodeArtifact
supports Maven snapshots (see Snapshot publishing in CodeArtifact), publishing snapshots with a generic
HTTP client such as curl
is more complex than publishing Maven release
versions as described in Publishing with curl. Note
that this section isn’t relevant if you’re building and deploying snapshot versions with
a Maven client such as mvn
or gradle
. You need to follow the
documentation for that client.
Publishing a snapshot version involves publishing one or more builds of a snapshot
version. In CodeArtifact, if there are n builds of a snapshot version,
there will be n + 1 CodeArtifact versions: n build
versions all with a status of Unlisted
, and one snapshot version (the
latest published build) with a status of Published
. The snapshot version
(that is, the version with a version string that contains “-SNAPSHOT”) contains an
identical set of assets to the latest published build. The simplest way to create this
structure using curl
is as follows:
-
Publish all assets of all builds using
curl
. -
Publish the
maven-metadata.xml
file of the last build (that is, the build with the most-recent date-time stamp) withcurl
. This will create a version with “-SNAPSHOT
” in the version string and with the correct set of assets. -
Use the UpdatePackageVersionsStatus API to set the status of all the non-latest build versions to
Unlisted
.
Use the following curl
commands to publish snapshot assets (such as .jar
and .pom files) for the snapshot version 1.0-SNAPSHOT
of a package
com.mycompany.app:pkg-1
:
curl --user "aws:$CODEARTIFACT_AUTH_TOKEN" -H "Content-Type: application/octet-stream" \ -X PUT https://
my_domain-111122223333
.d.codeartifact.us-west-2
.amazonaws.com/maven/my_maven_repo/com/mycompany/app/pkg-1/1.0-SNAPSHOT/pkg-1-1.0-20210729.171330-2.jar
\ --data-binary@pkg-1-1.0-20210728.194552-1.jar
curl --user "aws:$CODEARTIFACT_AUTH_TOKEN" -H "Content-Type: application/octet-stream" \ -X PUT https://
my_domain-111122223333
.d.codeartifact.us-west-2
.amazonaws.com/maven/my_maven_repo/com/mycompany/app/pkg-1/1.0-SNAPSHOT/pkg-1-1.0-20210729.171330-2.pom
\ --data-binary@pkg-1-1.0-20210728.194552-1.pom
When using these examples:
-
Replace
my_domain
with your CodeArtifact domain name. -
Replace
111122223333
with the AWS account ID of the owner of your CodeArtifact domain. -
Replace
us-west-2
with the AWS Region in which your CodeArtifact domain is located. -
Replace
my_maven_repo
with your CodeArtifact repository name.
Important
You must prefix the value of the --data-binary
parameter with the
@
character. When putting the value in quotation marks, the
@
must be included inside the quotation marks.
You may have more than two assets to upload for each build. For example, there might
be Javadoc and source JAR files in addition to the main JAR and pom.xml
. It
is not necessary to publish checksum files for the package version assets because CodeArtifact
automatically generates checksums for each uploaded asset. To verify the assets were
uploaded correctly, fetch the generated checksums using the
list-package-version-assets
command and compare those to the original
checksums. For more information about how CodeArtifact handles Maven checksums, see Use Maven checksums.
Use the following curl command to publish the maven-metadata.xml
file for the latest build version:
curl --user "aws:$CODEARTIFACT_AUTH_TOKEN" -H "Content-Type: application/octet-stream" \ -X PUT https://
my_domain-111122223333
.d.codeartifact.us-west-2
.amazonaws.com/maven/my_maven_repo/com/mycompany/app/pkg-1/1.0-SNAPSHOT/
maven-metadata.xml \ --data-binary @maven-metadata.xml
The maven-metadata.xml
file must reference at least one of the assets in
the latest build version in the <snapshotVersions>
element. In
addition, the <timestamp>
value must be present and must match the
timestamp in the asset file names. For example, for the 20210729.171330-2
build published previously, the contents of maven-metadata.xml
would be:
<?xml version="1.0" encoding="UTF-8"?> <metadata> <groupId>com.mycompany.app</groupId> <artifactId>pkg-1</artifactId> <version>1.0-SNAPSHOT</version> <versioning> <snapshot> <timestamp>20210729.171330</timestamp> <buildNumber>2</buildNumber> </snapshot> <lastUpdated>20210729171330</lastUpdated> <snapshotVersions> <snapshotVersion> <extension>jar</extension> <value>1.0-20210729.171330-2</value> <updated>20210729171330</updated> </snapshotVersion> <snapshotVersion> <extension>pom</extension> <value>1.0-20210729.171330-2</value> <updated>20210729171330</updated> </snapshotVersion> </snapshotVersions> </versioning> </metadata>
After maven-metadata.xml
has been published, the last step is to set all
the other build versions (that is, all the build versions apart from the latest build)
to have a package version status of Unlisted
. For example, if the
1.0-SNAPSHOT
version has two builds, with the first build being
20210728.194552-1
, the command to set that build to
Unlisted
is:
aws codeartifact update-package-versions-status --domain
my-domain
--domain-owner 111122223333 \ --repositorymy-maven-repo
--format maven --namespace com.mycompany.app --package pkg-1 \ --versions 1.0-20210728.194552-1 --target-status Unlisted
Snapshots and external connections
Maven snapshots cannot be fetched from a Maven public repository through an external connection. AWS CodeArtifact only supports importing Maven release versions.
Snapshots and upstream repositories
In general, Maven snapshots work in the same way as Maven release versions when used
with upstream repositories, but there is a limitation if you plan on publishing snapshots
of the same package version to two repositories which have an upstream relationship. For example,
say that there are two repositories in an AWS CodeArtifact domain, R
and U
,
where U
is an upstream of R
. If you publish a new build in R
,
when a Maven client requests the latest build of that snapshot version, CodeArtifact returns the latest version
from U
. This can be unexpected since the latest version is now in R
, not
U
. There are two ways to avoid this:
-
Don't publish builds of a snapshot version such as
1.0-SNAPSHOT
inR
, if1.0-SNAPSHOT
exists inU
. -
Use CodeArtifact package origin controls to disable upstreams on that package in
R
. The latter will allow you to publish builds of1.0-SNAPSHOT
inR
, but it will also preventR
from getting any other versions of that package fromU
that aren't already retained.