Artifact Repositories (Nexus/Artifactory) Cheat Sheet
Configuring and using binary repository managers like Nexus and Artifactory to store, version, and proxy build artifacts.
Repository Types
Common repository classifications in Nexus/Artifactory.
- Hosted repository- Stores artifacts you publish yourself, e.g. internal releases
- Proxy repository- Caches artifacts fetched from a remote source like Maven Central or npm registry
- Group/virtual repository- Aggregates multiple hosted/proxy repos behind a single URL
- Snapshot vs release repo- Separates mutable pre-release builds from immutable versioned releases
Maven settings.xml for Nexus
Point Maven at a Nexus-hosted repository with authentication.
<settings> <servers> <server> <id>nexus-releases</id> <username>${env.NEXUS_USER}</username> <password>${env.NEXUS_PASS}</password> </server> </servers> <mirrors> <mirror> <id>nexus</id> <mirrorOf>*</mirrorOf> <url>https://nexus.example.com/repository/maven-public/</url> </mirror> </mirrors></settings>
Publish to Artifactory (npm)
Configure npm to publish packages to a private Artifactory registry.
# Set registry for the scopenpm config set @myorg:registry https://artifactory.example.com/api/npm/npm-local/# Authenticate (writes token to .npmrc)npm login --registry=https://artifactory.example.com/api/npm/npm-local/# Publishnpm publish --registry=https://artifactory.example.com/api/npm/npm-local/
Docker Push to Artifactory Registry
Tag and push a Docker image to an Artifactory Docker repository.
docker login artifactory.example.comdocker tag myapp:1.2.0 artifactory.example.com/docker-local/myapp:1.2.0docker push artifactory.example.com/docker-local/myapp:1.2.0
Best Practices
Common conventions for keeping artifact repos maintainable.
- Immutable releases- Never overwrite a published release version; bump the version instead
- Retention policies- Auto-purge old snapshots and unused proxy cache entries to save storage
- Vulnerability scanning- Integrate Xray/Nexus IQ to block artifacts with known CVEs
- Access control by repo- Scope read/write permissions per team or environment
Artifactory REST API for Automation
Query, promote, and delete artifacts programmatically without the UI.
# Search for artifacts by property (e.g. build.name)curl -s -H "Authorization: Bearer $ARTIFACTORY_TOKEN" \ "https://artifactory.example.com/artifactory/api/search/prop?build.name=myapp&build.number=42"# Promote a build's artifacts from staging to release repocurl -X POST -H "Authorization: Bearer $ARTIFACTORY_TOKEN" \ -H "Content-Type: application/json" \ -d '{"targetRepo":"libs-release-local","status":"released","copy":true}' \ "https://artifactory.example.com/artifactory/api/build/promote/myapp/42"# Delete artifacts older than 90 days matching a pattern (AQL)curl -X POST -H "Authorization: Bearer $ARTIFACTORY_TOKEN" -H "Content-Type: text/plain" \ -d 'items.find({"repo":"libs-snapshot-local","created":{"$before":"90d"}})' \ "https://artifactory.example.com/artifactory/api/search/aql"
Nexus Cleanup Policy via Groovy Script API
Automate repository cleanup with a scheduled task defined through the scripting API.
import org.sonatype.nexus.repository.storage.StorageFacetimport org.sonatype.nexus.repository.storage.Querydef repository = repository.repositoryManager.get('maven-snapshots')def tx = repository.facet(StorageFacet).txSupplier().get()tx.begin()try { def cutoff = new Date() - 90 def query = Query.builder() .where('last_updated').lt(cutoff.time) .build() tx.browseComponents(tx.findBucket(repository), query).each { component -> tx.deleteComponent(component) } tx.commit()} finally { tx.close()}
Advanced Query & Deduplication Concepts
Mechanisms Artifactory/Nexus use to keep large binary stores efficient and queryable.
- AQL (Artifactory Query Language)- SQL-like DSL for finding artifacts by property, checksum, or usage stats across repos in one query
- Checksum-based storage- Binaries are stored once by SHA-256; identical files across repos share the same underlying blob
- Deploy-time checksum deploy- Uploading just a checksum header lets the server link to an existing binary without re-uploading bytes
- Bill of Materials export- Build-info integration links every deployed artifact back to the CI build and its dependency graph
- Replication- Push/pull mirroring between Artifactory instances for multi-region or DR setups
- Federated repositories- Multi-site repos that stay in sync in near-real-time, unlike one-way replication
Provision a Repository with Terraform
Manage Nexus repository configuration as code instead of clicking through the UI.
resource "nexus_repository_docker_hosted" "internal" { name = "docker-internal" online = true docker { force_basic_auth = true http_port = 8082 v1_enabled = false } storage { blob_store_name = "default" strict_content_type_validation = true write_policy = "allow_once" }}resource "nexus_repository_maven_proxy" "central" { name = "maven-central-proxy" online = true proxy { remote_url = "https://repo1.maven.org/maven2/" content_max_age = 1440 metadata_max_age = 1440 } maven { version_policy = "RELEASE" layout_policy = "STRICT" } storage { blob_store_name = "default" strict_content_type_validation = true write_policy = "ALLOW" }}
CI Gate: Reject Overwritten Release Artifacts
Fail a pipeline that tries to push over an existing immutable release version.
VERSION=1.4.0REPO_URL="https://artifactory.example.com/artifactory/libs-release-local/com/myorg/myapp/${VERSION}"if curl -s -o /dev/null -w "%{http_code}" "$REPO_URL/myapp-${VERSION}.jar" | grep -q '^200$'; then echo "ERROR: version ${VERSION} already published — bump the version before releasing" >&2 exit 1fimvn deploy -DaltDeploymentRepository=nexus-releases::default::https://nexus.example.com/repository/maven-releases/
Route all external dependency downloads through a proxy repository, not directly to the public internet — it gives you a build cache, an outage buffer if the upstream registry goes down, and a single point to enforce vulnerability policy.