Artifactory Configuration
Artifactory Integration Guide
Complete guide for integrating Socket Registry Firewall with JFrog Artifactory. Supports auto-discovery of repositories and four deployment topologies.
Overview
Socket Registry Firewall integrates with Artifactory to protect package ingestion and distribution. The firewall can automatically discover and sync repository configurations from Artifactory, eliminating manual route configuration.
Supported Artifactory repository types:
| Artifactory Package Type | Firewall Registry | Firewall URL Path | Notes |
|---|---|---|---|
| npm | npm | /artifactory/api/npm/<repo> | |
| pypi | pypi | /artifactory/api/pypi/<repo> | |
| maven | maven | /artifactory/<repo> | Direct path — no /api/ prefix |
| gradle | maven | /artifactory/<repo> | Maven layout; see cooldown for non-Maven-Central hosts |
| cargo | cargo | /artifactory/<repo> | Direct path |
| gems | rubygems | /artifactory/api/gems/<repo> | |
| nuget (v2) | nuget | /artifactory/api/nuget/<repo> | |
| nuget (v3) | nuget | /artifactory/api/nuget/v3/<repo> | Used for repository keys containing v3 |
| go | go | /artifactory/api/go/<repo> | Requires a virtual repository in front |
| conda | conda | /artifactory/<repo> | Direct path; experimental — scanned as PyPI |
| huggingfaceml | huggingface | /artifactory/api/huggingfaceml/<repo> | Requires version 2.0.9 or higher |
Important: Artifactory smart remotes require the per-ecosystem path shown above. Using a different path triggers Artifactory's warning: "Smart repository detected. URL format missing /api/<package_name>/"
📝 HuggingFace repositories are discovered from Artifactory only. Nexus auto-discovery does not route HuggingFace repositories.
📝 OpenVSX is not auto-discovered from Artifactory or Nexus. Define an OpenVSX route manually under
path_routing.routes.
Package types Socket does not scan natively (Docker, Helm, generic, and others) can still be protected with External Registry Cooldown, which blocks recently published packages based on their publish date.
Deployment Topologies
1. Direct Deployment (Baseline — No Firewall)
Standard Artifactory setup with no security scanning. Remote repositories connect straight to the public registries. Use it as the "before" picture when comparing against the topologies below.
Developer / CI ---> Artifactory ---> Public Registry
(caching) (npmjs.org, pypi.org)
| Ecosystem | Artifactory Remote URL | Notes |
|---|---|---|
| npm | https://registry.npmjs.org | |
| PyPI | https://files.pythonhosted.org | PyPI Registry URL: https://pypi.org |
| Maven | https://repo1.maven.org/maven2/ | |
| Gradle | https://plugins.gradle.org/m2/ | |
| Cargo | https://index.crates.io/ | Git Registry URL: https://index.crates.io/ |
| RubyGems | https://rubygems.org/ | |
| NuGet v3 | https://api.nuget.org/v3/index.json | V3 Feed URL: same value |
| NuGet v2 | https://www.nuget.org/ | |
| Go | https://proxy.golang.org/ | Needs a virtual repository in front |
| Conda | https://repo.anaconda.com/pkgs/main/ |
2. Upstream Deployment (Most Common)
Artifactory remote repositories pull packages through the firewall. Developers and CI use Artifactory directly.
Developer / CI ---> Artifactory ---> Socket Firewall ---> Public Registry
(caching) (npmjs.org, pypi.org)
Benefits:
- Single enforcement point
- No developer config changes needed
- Artifactory caches packages (most installs don't hit firewall)
- Centralized security for entire organization
Use when:
- You already have Artifactory deployed
- Developers are already configured to use Artifactory
- You want to protect package ingestion from public registries
See Upstream Deployment Setup →
3. Downstream Deployment
Developers and CI point at the firewall, which proxies to Artifactory (which may or may not have its own upstream).
Developer / CI ---> Socket Firewall ---> Artifactory ---> Public/Internal Registry
Benefits:
- Protect developer workstations directly
- Works with Artifactory virtual repos or local repos
- Can layer on top of existing Artifactory setup
Use when:
- You want to protect specific teams or projects
- You have Artifactory hosting internal packages
- You want an additional security layer beyond Artifactory
See Downstream Deployment Setup →
4. Middle Deployment (Multi-Tier)
Firewall sits between two Artifactory instances (e.g., On-Premise → Production, Regional → Central).
On-Premise Artifactory ---> Socket Firewall ---> Artifactory Production
(Virtual Repo) (Remote Repo)
Benefits:
- Scan packages flowing between internal registries
- Supports Artifactory virtual repos aggregating remote repos
- Protects multi-tier Artifactory topologies
Use when:
- You have multiple Artifactory instances (On-Premise/Prod, Regional/Central)
- Packages flow between Artifactory instances
- You need to scan internal package distribution
Auto-Discovery Configuration
Socket Firewall can automatically discover all Artifactory remote repositories and create firewall routes without manual configuration.
Basic Auto-Discovery
path_routing:
enabled: true
domain: socket-firewall.company.com
private_registry:
api_url: https://artifactory.company.com/artifactory
api_key: your-artifactory-api-key # Or use env var ARTIFACTORY_API_KEY
mode: artifactory
interval: 5m # Auto-sync every 5 minutesRoutes are discovered from Artifactory and updated automatically. No need to manually define each route!
Advanced Auto-Discovery
path_routing:
enabled: true
domain: socket-firewall.company.com
private_registry:
api_url: https://artifactory.company.com/artifactory
api_key: your-artifactory-api-key # Token auth (takes precedence)
mode: artifactory
# OR use basic auth with separate fields:
username: admin # Basic auth username
password: secret # Basic auth password
interval: 5m # Sync interval (30s, 5m, 1h, etc.)
ignore_ssl_errors: true # Disable verification of SSL when connecting to the Private Registry
include_pattern: "^(npm|pypi|maven)-.*" # Only npm/pypi/maven repos
exclude_pattern: "(tmp|test|snapshot)-.*" # Exclude temp/test repos
supported_ecosystems_only: true # Skip unsupported package types (default: true)
include_virtual: false # Include VIRTUAL repos (default: false)Leave include_virtual at false unless clients route through a virtual repository directly — the member repositories behind a virtual aggregator are discovered individually, and each keeps its own host allowlist and cooldown checks. See include_virtual and supported_ecosystems_only in the Configuration Reference.
How Auto-Discovery Works
- Firewall calls Artifactory REST API:
GET /api/repositories - Filters for the repository types it routes:
REMOTE,LOCAL,FEDERATED, andDISTRIBUTION.VIRTUALrepositories are included only wheninclude_virtual: true - Parses repository list and extracts:
- Repository key (name)
- Package type (npm, pypi, maven, etc.)
- Repository type (
REMOTE,LOCAL,FEDERATED,DISTRIBUTION, orVIRTUAL)
- For
REMOTErepositories, checks the remote URL against the known public registry hosts for that ecosystem. A repository proxying any other host gets a cooldown route when External Registry Cooldown is enabled, and no route otherwise - Creates firewall routes for each discovered repository — both the ecosystem API path (
/artifactory/api/{package-type}/{repo-key}) and the direct path (/artifactory/{repo-key}), so Artifactory smart remotes work with either URL form - Generates nginx configuration with discovered routes
- Repeats on interval, adding/removing routes as repositories change
Service Account Permissions for Auto-Discovery
Auto-discovery calls the Artifactory REST API to list repositories. The service account used for authentication needs read-only access to the repository listing endpoint.
API endpoint used: GET /api/repositories
This endpoint returns the key, package type, repository type, and URL of every repository the authenticated user can see. No write operations are performed — the firewall only reads repository metadata to generate routes.
Minimum-Privilege Setup (Recommended)
Create a dedicated service account with the minimum permissions required:
-
Create a group in Artifactory:
- Go to Administration → Identity & Access → Groups → New Group
- Group Name:
socket-firewall-discovery - Auto Join: No
-
Create a permission target:
- Go to Administration → Identity & Access → Permissions → New Permission
- Name:
socket-firewall-read - Resources → Repositories: Select Any Repository (or only the repositories you want the firewall to discover)
- Groups: Add
socket-firewall-discoverywith Read permission only - Do not grant Deploy, Annotate, Delete, or Manage
- Save
-
Create a local user:
- Go to Administration → Identity & Access → Users → New User
- Username:
socket-firewall - Status: Enabled
- Groups: Add to
socket-firewall-discovery - Save
-
Generate an API key (preferred over password):
- Log in as the new user
- Go to Edit Profile → API Key → Generate
- Use this key as
api_keyinsocket.yml
Alternatively, generate an Access Token (Artifactory 7.x+):
- Go to Administration → Identity & Access → Access Tokens → Generate Token
- Token Scope: User
socket-firewall - Use the token as
api_keyinsocket.yml
Artifactory Permission Reference
| Permission | Purpose | Required? |
|---|---|---|
| Read | Read/list repositories and their metadata | Yes |
| Deploy | Upload artifacts | No — not needed |
| Annotate | Add/modify properties on artifacts | No — not needed |
| Delete | Delete artifacts or repositories | No — not needed |
| Manage | Administer permissions and settings | No — not needed |
Note (Artifactory Cloud / SaaS): If you use Artifactory Cloud (JFrog Platform), the same permissions apply. Use a scoped Access Token with read-only permissions. Navigate to Administration → Identity & Access → Access Tokens to generate one.
Verifying Permissions
Test that the service account can list repositories:
# Using API key
curl -H "X-JFrog-Art-Api: your-api-key" \
https://artifactory.company.com/artifactory/api/repositories
# Using basic auth (username:password)
curl -u "socket-firewall:password" \
https://artifactory.company.com/artifactory/api/repositories
# Using Access Token (Artifactory 7.x+)
curl -H "Authorization: Bearer your-access-token" \
https://artifactory.company.com/artifactory/api/repositories
# Expected: JSON array of repository objects
# [{"key": "npm-remote", "type": "REMOTE", "packageType": "npm", "url": "..."}, ...]If the response is 401 Unauthorized, the API key or token is invalid. If it returns 403 Forbidden, the user lacks the Read permission on repositories. If it returns an empty list, the permission target may be scoped too narrowly — ensure it includes the repositories you want to discover.
Upstream Deployment Setup
Protect package ingestion by pointing Artifactory remote repos at the firewall.
Step 1: Deploy Socket Firewall
socket.yml:
socket:
api_url: https://api.socket.dev
ports:
http: 8080
https: 8443
# Upstream topology - Artifactory -> firewall -> public registry
path_routing:
enabled: true
domain: socket-firewall.internal.company.com
config_mode: upstream
private_registry:
api_url: https://artifactory.company.com/artifactory
api_key: ${ARTIFACTORY_API_KEY}
mode: artifactory # Auto-discovery
interval: 5m
exclude_pattern: "(tmp|test)-.*"
nginx:
worker_processes: 4
worker_connections: 8192docker-compose.yml:
services:
socket-firewall:
image: socketdev/socket-registry-firewall:latest
ports:
- "8080:8080"
- "8443:8443"
environment:
- SOCKET_SECURITY_API_TOKEN=${SOCKET_SECURITY_API_TOKEN}
- ARTIFACTORY_API_KEY=${ARTIFACTORY_API_KEY}
volumes:
- ./socket.yml:/app/socket.yml:ro
- ./ssl:/etc/nginx/ssl
restart: unless-stoppedStart:
docker compose up -d
curl -k https://socket-firewall.internal.company.com:8443/healthStep 2: Configure Artifactory Remote Repositories
In Administration → Repositories → Remote, edit each remote repository and replace the public registry URL with the firewall URL for that ecosystem. Substitute your own repository key for the example keys.
Important: Each ecosystem has its own path form. Artifactory reports "Smart repository detected. URL format missing /api/<package_name>/" when the URL uses the wrong form, and several ecosystems fail outright.
| Ecosystem | Firewall URL | Other settings that matter |
|---|---|---|
| npm | https://socket-firewall:8443/artifactory/api/npm/npm-remote | Repository Layout: npm-default |
| PyPI | https://socket-firewall:8443/artifactory/api/pypi/pypi-remote | PyPI Registry URL: the same firewall URL; Repository Suffix: simple; Repository Layout: simple-default |
| Maven | https://socket-firewall:8443/artifactory/maven-central-remote | Repository Layout: maven-2-default; Handle Releases: Yes; Handle Snapshots: Yes; Suppress POM Consistency Checks: Yes |
| Gradle | https://socket-firewall:8443/artifactory/gradle-plugins-remote | Repository Layout: maven-2-default; Handle Releases: Yes; Handle Snapshots: Yes |
| Cargo | https://socket-firewall:8443/artifactory/cargo-remote | Git Registry URL: the same firewall URL; Repository Layout: cargo-default; Anonymous Access: Yes |
| RubyGems | https://socket-firewall:8443/artifactory/api/gems/gems-remote | Repository Layout: simple-default |
| NuGet v3 | https://socket-firewall:8443/artifactory/api/nuget/v3/nuget-v3-remote | V3 Feed URL: the same firewall URL; Feed Context Path: api/v2; Download Context Path: api/v2/package; Repository Layout: nuget-default |
| NuGet v2 | https://socket-firewall:8443/artifactory/api/nuget/nuget-v2-remote | Feed Context Path: api/v2; Download Context Path: api/v2/package; Repository Layout: nuget-default |
| Go | https://socket-firewall:8443/artifactory/api/go/go-remote | VCS Git Provider: GITHUB; Repository Layout: go-default; requires a virtual repository wrapping the remote |
| Conda | https://socket-firewall:8443/artifactory/conda-main-remote | Repository Layout: simple-default |
| HuggingFace | https://socket-firewall:8443/artifactory/api/huggingfaceml/hf-remote | Requires firewall version 2.0.9 or higher |
Note: Maven, Gradle, Cargo, and Conda use the direct path (
/artifactory/<repo>). Every other ecosystem uses the/api/<type>/prefix.
Step 3: Common Settings for All Remotes
Apply these to every remote repository that points at the firewall:
| Setting | Value | Reason |
|---|---|---|
| Allow Any Host Auth | Yes | Required for Artifactory smart remote authentication |
| Store Artifacts Locally | Yes | Caches scanned packages so repeat installs skip the firewall |
| Verify SSL Certificate | Yes (No for testing) | Add the firewall's CA to Artifactory's trust store in production rather than disabling verification |
Step 4: Test
Test npm:
# Developers use Artifactory as normal
npm config set registry https://artifactory.company.com/artifactory/api/npm/npm-remote/
npm install lodash
# Check firewall logs
docker compose logs socket-firewall | grep lodashTest PyPI:
pip config set global.index-url https://artifactory.company.com/artifactory/api/pypi/pypi-remote/simple
pip install requests
docker compose logs socket-firewall | grep requestsStep 5: Verify Auto-Discovery
Check that the firewall discovered your Artifactory repositories:
# View discovered routes
docker compose exec socket-firewall cat /app/discovered-routes.yml
# Check logs for discovery events
docker compose logs socket-firewall | grep "Discovered.*repositories"Downstream Deployment Setup
Developers point at the firewall, which proxies to Artifactory.
Step 1: Define Routes
socket.yml:
socket:
api_url: https://api.socket.dev
ports:
http: 8080
https: 8443
# Downstream topology (default) - client -> firewall -> Artifactory
path_routing:
enabled: true
domain: firewall.company.com
config_mode: downstream
routes:
# Point to Artifactory virtual or remote repos
- path: /npm
upstream: https://artifactory.company.com/artifactory/api/npm/npm-virtual
registry: npm
- path: /pypi
upstream: https://artifactory.company.com/artifactory/api/pypi/pypi-virtual
registry: pypi
- path: /maven
upstream: https://artifactory.company.com/artifactory/maven-central-virtual
registry: maven
- path: /gradle
upstream: https://artifactory.company.com/artifactory/gradle-plugins-virtual
registry: maven
- path: /cargo
upstream: https://artifactory.company.com/artifactory/cargo-virtual
registry: cargo
- path: /rubygems
upstream: https://artifactory.company.com/artifactory/api/gems/gems-virtual
registry: rubygems
- path: /nuget
upstream: https://artifactory.company.com/artifactory/api/nuget/v3/nuget-v3-virtual
registry: nuget
- path: /go
upstream: https://artifactory.company.com/artifactory/api/go/go-virtual
registry: go
- path: /conda
upstream: https://artifactory.company.com/artifactory/conda-virtual
registry: condaStep 2: Upstream URL Patterns
Each route's upstream must use the Artifactory path form for its ecosystem:
| Ecosystem | Route upstream Format | Example |
|---|---|---|
| npm | /artifactory/api/npm/<repo> | /artifactory/api/npm/npm-virtual |
| PyPI | /artifactory/api/pypi/<repo> | /artifactory/api/pypi/pypi-virtual |
| Maven | /artifactory/<repo> | /artifactory/maven-central-virtual |
| Gradle | /artifactory/<repo> | /artifactory/gradle-plugins-virtual |
| Cargo | /artifactory/<repo> | /artifactory/cargo-virtual |
| RubyGems | /artifactory/api/gems/<repo> | /artifactory/api/gems/gems-virtual |
| NuGet v3 | /artifactory/api/nuget/v3/<repo> | /artifactory/api/nuget/v3/nuget-v3-virtual |
| NuGet v2 | /artifactory/api/nuget/<repo> | /artifactory/api/nuget/nuget-v2-virtual |
| Go | /artifactory/api/go/<repo> | /artifactory/api/go/go-virtual |
| Conda | /artifactory/<repo> | /artifactory/conda-virtual |
Note: Maven, Gradle, Cargo, and Conda use direct paths. Every other ecosystem needs the
/api/<type>/prefix.
Step 3: Client Configuration
Developers point at the firewall instead of Artifactory:
# npm
npm config set registry https://firewall.company.com/npm/
# PyPI
pip config set global.index-url https://firewall.company.com/pypi/simple
# Maven (settings.xml)
# <mirror>
# <id>firewall</id>
# <url>https://firewall.company.com/maven/</url>
# <mirrorOf>central</mirrorOf>
# </mirror>
# Cargo (.cargo/config.toml)
# [registries.firewall]
# index = "https://firewall.company.com/cargo/"
# Go
export GOPROXY=https://firewall.company.com/go/,direct
# RubyGems
gem sources --add https://firewall.company.com/rubygems/ --remove https://rubygems.org/
# NuGet
dotnet nuget add source https://firewall.company.com/nuget/ -n firewall
# Conda
conda config --set custom_channels.main https://firewall.company.com/conda/Middle Deployment Setup
Firewall sits between two Artifactory instances: the on-premise instance's remote repositories point through the firewall at the upstream (cloud) instance, which connects to the public registries.
On-Prem Artifactory ---> Socket Firewall ---> Cloud Artifactory ---> Public Registry
Step 1: Configure the Firewall for Middle Topology
Point auto-discovery at the upstream (cloud) Artifactory instance.
socket.yml:
socket:
api_url: https://api.socket.dev
ports:
http: 8080
https: 8443
# Middle topology - Artifactory -> firewall -> Artifactory
path_routing:
enabled: true
domain: socket-firewall.internal.company.com
config_mode: middle
private_registry:
api_url: https://artifactory-prod.company.com/artifactory
api_key: ${ARTIFACTORY_API_KEY}
mode: artifactory # Auto-discovery from the upstream Artifactory
interval: 5m
nginx:
worker_processes: 4
worker_connections: 8192With config_mode: middle, auto-discovery applies mode: proxy to the ecosystems that rewrite URLs inside package metadata — pypi, conda, npm, and nuget. Every other discovered ecosystem uses mode: rewrite. To define routes by hand instead, set mode: proxy per route:
path_routing:
routes:
- path: /pypi
upstream: https://artifactory-prod.company.com/artifactory/api/pypi/pypi-remote
registry: pypi
mode: proxyWhy mode: proxy matters:
- The upstream Artifactory returns relative URLs like
../../packages/xyz/file.tar.gz mode: proxypasses these URLs through unchanged- The on-premise Artifactory resolves relative URLs against its own base path
mode: rewritewould rewrite them to firewall paths, which the on-premise instance cannot resolve
Step 2: Configure On-Premise Remote Repositories
Point each on-premise remote repository at the firewall, using the same per-ecosystem URL forms and common settings as Step 2 and Step 3 of the upstream setup. The repository key in the URL is the key of the matching repository on the upstream instance.
Go additionally requires a virtual repository wrapping the remote on both Artifactory instances.
Step 3: Create Virtual Repositories On-Premise
For each ecosystem, create an on-premise virtual repository that aggregates the firewall-facing remote (external packages, scanned) plus any local repositories (internal packages). Developers point at these virtual repositories.
| Ecosystem | Virtual Repo | Includes Remote | Includes Local |
|---|---|---|---|
| npm | npm-virtual | npm-remote | npm-local |
| PyPI | pypi-virtual | pypi-remote | pypi-local |
| Maven | maven-virtual | maven-central-remote | maven-local |
| Go | go-virtual | go-remote | go-local |
Step 4: Test the Chain
# From the on-premise Artifactory, check firewall connectivity
curl -k https://socket-firewall.internal.company.com:8443/health
# Install through the on-premise virtual repo
npm config set registry https://artifactory.company.com/artifactory/api/npm/npm-virtual/
npm install lodash
# Confirm the firewall scanned it
docker compose logs socket-firewall | grep lodashTroubleshooting
Artifactory Can't Reach Firewall
Symptom: Artifactory shows connection errors when fetching packages
Check:
# From Artifactory server, test connectivity
curl -k https://socket-firewall.internal.company.com:8443/health
# Check DNS resolution
nslookup socket-firewall.internal.company.com
# Check firewall from Artifactory
ping socket-firewall.internal.company.comSolution:
- Verify DNS record points to firewall host
- Ensure firewall ports (8080/8443) are accessible from Artifactory
- Check firewall rules/security groups
SSL Certificate Errors
Symptom: Artifactory logs show SSL verification errors
Option 1 - Trust firewall cert in Artifactory:
# Copy firewall cert to Artifactory server
scp ssl/fullchain.pem artifactory-server:/tmp/socket-firewall.crt
# Add to Artifactory's Java trust store
keytool -import -alias socket-firewall \
-keystore $JAVA_HOME/lib/security/cacerts \
-file /tmp/socket-firewall.crt \
-storepass changeit
# Restart ArtifactoryOption 2 - Disable SSL verification (testing only):
- In Artifactory remote repo settings, uncheck "Verify SSL Certificate"
Auto-Discovery Not Finding Repositories
Check Artifactory API access:
# Test API connectivity
curl -H "X-JFrog-Art-Api: your-api-key" \
https://artifactory.company.com/artifactory/api/repositories
# Should return JSON list of repositoriesCheck firewall logs:
docker compose logs socket-firewall | grep -i discovery
docker compose logs socket-firewall | grep -i artifactoryCommon issues:
- API key lacks permissions (needs "Read" on repositories)
api_urlincorrect (should end with/artifactory, not include/api)- Network connectivity from firewall to Artifactory
- The repository is
VIRTUALandinclude_virtualisfalse(the default) — its member repositories are discovered instead - A
REMOTErepository proxies a host that is not a known public registry for its ecosystem (a private Artifactory, an internal mirror, or a service such as Google AOSS). Such repositories get a cooldown route when External Registry Cooldown is enabled and no route otherwise. Gradle repositories are checked against the Maven hosts, so a Gradle remote proxyingplugins.gradle.orgneeds a cooldown entry - Set
log_level: debugto confirm — skipped repositories are reported only at debug level
See the supported_ecosystems_only and include_virtual sections of the Configuration Reference for the full matrix of what gets a route.
Virtual Repo Doubled URLs
Symptom: Artifactory virtual repos return URLs like /artifactory/api/pypi/pypi-virtual/artifactory/api/pypi/pypi-remote/packages/...
Solution: Use config_mode: middle and mode: proxy:
path_routing:
config_mode: middle
routes:
- path: /pypi
upstream: https://artifactory.company.com/artifactory/api/pypi/pypi-remote
registry: pypi
mode: proxy # Critical - prevents URL rewritingPackage Downloads Failing
Check firewall is blocking correctly:
# Try to install known malicious package
npm install some-malicious-package
# Check firewall logs for block
docker compose logs socket-firewall | grep -i blockCheck firewall is allowing correct packages:
# Install known safe package
npm install lodash
# Should succeed - check logs
docker compose logs socket-firewall | grep lodashPrivate npm Packages Return 404 While Public Packages Install
Symptom: the client reports a 404 against the public registry, such as GET https://registry.npmjs.org/@scope/private-pkg/-/private-pkg-1.0.0.tgz: Not Found, together with "No authorization header was set for the request".
Cause: the download URL reached the client without being rewritten, so the client contacted the public registry directly instead of the firewall — and without your credentials.
Check that the metadata the firewall returns points back at the firewall:
curl -s -H "Authorization: Basic $SOCKET_AUTH_B64" \
'https://firewall.company.com/npm/@scope%2fprivate-pkg' \
| grep -o '"tarball":"[^"]*"' | head -3Every tarball URL should name your firewall host. Public packages mask this condition: their un-rewritten downloads still succeed, but they reach the client unscanned — so treat a public-registry URL here as a problem even when installs appear to work.
Tarball URL rewriting across all npm metadata content types and encodings requires version 2.0.12 or higher.
Best Practices
Repository Naming
Use consistent naming in Artifactory to simplify filtering:
npm-public- Public npm registrynpm-internal- Internal npm packagespypi-public- Public PyPI registrypypi-internal- Internal Python packages
Then use filters:
include_pattern: ".*-public" # Only protect public-facing repos
exclude_pattern: ".*-internal" # Don't scan internal packagesCaching Strategy
Artifactory caching + Firewall caching = Maximum efficiency:
- Artifactory caches packages after first fetch
- Firewall caches verdicts, refreshing every 10 minutes for downloads and every hour for metadata checks by default; a stale verdict can still be served for up to 24 hours if the Socket API is unreachable
- Subsequent installs hit Artifactory cache (never reach firewall)
- New packages hit firewall once, then cached by both
Result: Minimal latency overhead after initial fetch
📝 See Configuration Reference for the full set of cache TTL options.
Monitoring
Monitor both Artifactory and Firewall:
Artifactory:
- Monitor remote repository health
- Check artifact download counts
- Review failed download requests
Firewall:
- Monitor block events (malicious packages)
- Check API error rates
- Review cache hit rates
Splunk integration (recommended):
splunk:
enabled: true
hec_url: https://splunk.company.com:8088/services/collector/event
hec_token: ${SPLUNK_HEC_TOKEN}
index: security
source: socket-firewall-artifactoryWebhook integration (any HTTP endpoint):
webhook:
enabled: true
url: https://siem.company.com/api/events
auth_header: "Bearer ${WEBHOOK_TOKEN}"
on_block: true
on_warn: true
# Optional: batch events as NDJSON instead of one POST per event
batch_enabled: true
batch_size: 524288 # flush at 512KB
batch_period: 5 # or every 5 secondsSee Delivery Modes for how batching affects delivery guarantees.
Prometheus metrics:
The firewall always serves GET /metrics on a dedicated port (metrics_port, default 9145). This listener is exempt from the bearer_token client auth gate, so restrict access to it at the network layer with nginx allow/deny rules or a Kubernetes NetworkPolicy. For these topologies the most useful families are the upstream-latency and firewall-overhead histograms, the circuit-breaker state gauges, socket_redis_available, and the cache hit and stale-serve counters.
The
/metricsexemption from the client auth gate requires version 2.0.7 or higher.
High Availability
For production deployments:
-
Multiple firewall instances with shared Redis cache:
services: socket-firewall-1: # ... firewall config socket-firewall-2: # ... firewall config redis: # ... shared Redis -
Load balancer in front of firewall instances
-
Artifactory remote repo points to load balancer VIP
Security Hardening
- Use proper TLS certificates (not self-signed in production)
- Rotate API keys regularly
- Limit Artifactory API key permissions to read-only repositories
- Use
fail_open: falsein production for maximum security - Monitor and alert on block events
External Registry Cooldown for Unsupported Repos
Artifactory often hosts repositories whose package types Socket does not scan natively (Docker, Helm, generic, and others). External registry cooldown covers these repositories by blocking packages published more recently than a configurable window.
Cooldown in local mode requires Redis. In API mode Redis is used for caching when available. See External Registry Cooldown for the mode options.
How it works with auto-discovery:
- Auto-discovery detects all Artifactory repositories, including unsupported package types
- Supported repositories get Socket API-checked routes as normal
- Unsupported repositories are matched against the configured cooldown registries
- Matched repositories get
cooldown-checked routes - Unmatched unsupported repositories are skipped — no route is generated
Matching runs by Artifactory repository key first, then by remote URL (normalized, trailing slashes stripped).
Configuration
redis:
enabled: true
host: redis
port: 6379
path_routing:
enabled: true
domain: socket-firewall.company.com
private_registry:
api_url: https://artifactory.company.com/artifactory
api_key: ${ARTIFACTORY_API_KEY}
mode: artifactory
interval: 5m
supported_ecosystems_only: true # Supported repos get Socket API checks
external_registry_cooldown:
enabled: true
cooldown_period: 7d # Block packages published within 7 days
# Match by repository key or remote URL
registries:
- name: gradle-plugins-remote
url: https://plugins.gradle.org/m2/
ecosystem: maven
- name: docker-hub-remote
url: https://registry-1.docker.io
ecosystem: docker
# Or auto-discover the unsupported repos from Artifactory
private_registry:
enabled: true
source: auto # Detect from path_routing.mode
include_unsupported_only: true # Only repos skipped by supported_ecosystems_onlyA Gradle remote proxying https://plugins.gradle.org/m2/ is checked against the Maven registry hosts, so it needs an entry like the one above to be routed.
Docker and OCI Repositories
Docker/OCI cooldown requires version 2.0.9 or higher.
Docker repositories get cooldown-checked routes on both path forms Artifactory serves: /artifactory/api/docker/<repo> (used by Docker clients and smart remotes) and /artifactory/<repo>. Configure them like any other cooldown registry with ecosystem: docker — oci is accepted as an alias and behaves identically, and PURLs are always emitted as pkg:docker/....
| Request | Behavior |
|---|---|
Tag-referenced manifest (.../v2/<image>/manifests/<tag>) | Gated — a tag pull inside the cooldown window is blocked with 403 before any layer downloads |
Digest-referenced manifest (manifests/sha256:...) | Passes through |
| Blobs and layers | Passes through |
/v2/ ping, _catalog, tags/list | Passes through |
Image names with multiple path segments (myorg/team/app) are supported.
Publish-Date Fallback
When the ecosystem lookup cannot determine a publish date, the firewall can read the artifact's created timestamp from Artifactory instead. It searches both the repository and its <repo>-cache variant and takes the earliest match, and it works on Artifactory OSS — no Pro license needed.
external_registry_cooldown:
enabled: true
fallback: external # Query Artifactory first, ecosystem lookup second
# Or: fallback: artifactory # Ecosystem lookup first, Artifactory secondThe fallback reuses the path_routing.private_registry credentials, so there is no extra authentication to configure. See Publish-Date Fallback for all fallback modes.
Reference
Artifactory Remote Repository Configuration
| Setting | Value |
|---|---|
| Repository Key | npm-remote, pypi-remote, etc. |
| Package Type | npm, pypi, maven, etc. |
| URL | The firewall URL for the ecosystem — see Step 2 |
| Allow Any Host Auth | Yes |
| Verify SSL Certificate | Yes (No only when using self-signed certificates in testing) |
| Store Artifacts Locally | Yes (recommended) |
Firewall Configuration Summary
| Topology | config_mode | route mode | URL Rewriting | Auto-Discovery |
|---|---|---|---|---|
| Direct | N/A | N/A | N/A | N/A |
| Upstream | upstream | rewrite | Yes | Yes |
| Downstream | (default) | rewrite | Yes | Optional |
| Middle | middle | proxy* | No* | Yes |
* In middle, auto-discovery applies proxy to pypi, conda, npm, and nuget routes; other ecosystems use rewrite. Both the API path and the direct path are generated in every config_mode.
Supported Package Types
| Artifactory Package Type | Firewall Registry | Notes |
|---|---|---|
| npm | npm | Full support |
| pypi | pypi | Full support |
| maven | maven | Full support |
| gradle | maven | Maven layout |
| cargo | cargo | Full support |
| gems | rubygems | Full support |
| nuget | nuget | Full support (v2 and v3 paths) |
| go | go | Full support |
| conda | conda | Experimental - treated as PyPI |
| huggingfaceml | huggingface | Requires version 2.0.9 or higher |
| docker | cooldown | Via external registry cooldown |
| helm | cooldown | Via external registry cooldown |
| generic | cooldown | Via external registry cooldown |
| (other) | cooldown | Via external registry cooldown |
Updated about 1 month ago