Azure Artifacts: The Complete Guide

Azure Artifacts: The Complete Guide

A friendly, in-depth tour of Microsoft's package management service inside Azure DevOps. Learn how teams store, share, version, and protect the building blocks of their software, and how to keep builds fast, repeatable, and safe from supply chain surprises.

Imagine a workshop where a hundred carpenters build furniture. Almost nobody makes their own screws, hinges, or glass. They buy ready-made parts, and they also make special parts of their own, such as a custom drawer slider that every table needs. Now imagine the parts are scattered across drawers, other people’s garages, and old emails. A carpenter cannot find the right slider, uses the wrong size, and a table collapses. What the workshop needs is one well-organized, locked, labeled parts warehouse, where every part has a version number, nothing is ever swapped silently, and the warehouse keeps spare copies of popular outside parts in case the supplier closes.

Software teams have exactly this problem. Modern applications are built from hundreds of reusable pieces called packages. Azure Artifacts is the parts warehouse. In this guide you will learn what it is, how its pieces fit together, how a package travels from a developer to a build server and into an application, how it protects you from tampered or vanished packages, and how to run it well in a real company. Every new term is explained when it first appears, and every big idea comes with an everyday comparison.

One place
A single home for your team’s packages
Immutable
A published version never changes
Cached
Public packages saved for you on first use

1What Is Azure Artifacts?

A managed service for hosting, sharing, and controlling the reusable pieces of software that your teams create and consume.

Starting with the word “package”

Developers do not write everything from scratch. If you need to read a spreadsheet, send an email, or draw a chart, you use code that someone else wrote and shared. That shared code is bundled into a package: a single file, usually compressed, containing the code, a name, a version number, and a list of other packages it needs. Each programming world has its own package format and its own tool to fetch them. .NET developers use NuGet packages, JavaScript developers use npm packages, Java developers use Maven packages, and Python developers use PyPI-style packages.

The tool that downloads and installs these packages is called a package manager. It reads your project’s list of needed packages, fetches each from a registry (a website that stores packages), and puts them where the build can find them. The famous public registries are open to the world and hold millions of packages.

The company problem

Public registries are wonderful, but companies have needs they do not meet.

  • Private code: You have shared libraries that must not be public, such as your logging helper or your payment client.
  • Reliability: If the public registry is down, or a package is deleted by its author, your builds break.
  • Safety: A malicious package with a name similar to yours could sneak into your product.
  • Control: You want to know who published what, who can use it, and which versions are approved.

What Azure Artifacts does

Azure Artifacts is a package management service that is part of Azure DevOps, Microsoft’s set of tools for planning, building, testing, and releasing software. It lets your organization create private registries called feeds, publish your own packages to them, and download packages from them. It can also act as a middleman for public registries, saving a copy of each public package you use. It supports several package types with their native tools, so developers keep using the commands they already know.

Everyday analogy

Think of a company library with a head librarian. Staff borrow books from the shelves (feeds). The librarian also orders books from outside bookshops when someone asks, and keeps a copy on the shelf for next time (upstream caching). Every book has an edition number, and the librarian never rewrites a printed edition. If a mistake is found, a new edition is issued.

Share

Publish your own

Package shared code once, and let every team reuse it instead of copying and pasting.

Consume

One source for dependencies

Builds fetch everything from one trusted address, whether the package is yours or from the public.

Protect

Control and cache

Saved copies of public packages keep builds working and let you control which versions get in.

Trace

Know what is where

See who published a version, when, and which pipeline produced it.

i
Remember

Azure Artifacts stores packages that code depends on. It is not where you store your source code, and it is not a place for container images. Chapter 2 sorts out these differences.

2Azure Artifacts and Its Neighbors

The word “artifact” is used for several different things in the Microsoft world. Sorting them out now saves a lot of confusion.

flowchart LR
    DEV["Developers write code"] --> REPO["Source repository"]
    REPO --> PIPE["Build pipeline"]
    PIPE --> PKG["Packages published to Azure Artifacts feed"]
    PIPE --> PA["Pipeline artifacts: temporary build outputs"]
    PIPE --> IMG["Container images to Azure Container Registry"]
    PKG --> OTHER["Other projects consume the packages"]
    PUB["Public registries"] --> PKG
    
FIG 2.1 — Where packages, pipeline artifacts and container images each live
ThingWhat it isWhere it livesLifetime
Azure Artifacts packageA versioned, reusable library shared across projectsAn Azure Artifacts feedLong-lived, managed by retention policy
Pipeline artifactFiles produced by one pipeline run, handed to later stages or downloadsAttached to the pipeline runShort, tied to run retention
Container imageA packaged application with its environmentA container registry such as Azure Container RegistryLong-lived, own policies
Source codeThe text files developers writeA repository, such as Azure Repos or GitHubPermanent history

Comparing with other package hosts

Public

Public registries

Open and huge, but outside your control. Anyone can publish, and packages can change or disappear.

Neighbor

GitHub Packages

Package hosting tied to GitHub repositories and permissions. A natural fit when your code lives in GitHub.

Neighbor

Third-party repository managers

Products such as Artifactory and Nexus offer many formats and advanced features, often self-hosted or sold as services.

Neighbor

Azure Container Registry

The place for container images, with its own scanning and geo-replication features.

Choosing between them

If your teams already use Azure DevOps for pipelines and permissions, Azure Artifacts is the smoothest choice, because identities, projects, and pipelines are already connected. If your code and pipelines live in GitHub, GitHub Packages fits better. If you need unusual package formats or very advanced policy features, a dedicated repository manager may be worth considering. Many large companies use more than one and connect them.

Everyday analogy

A pipeline artifact is the leftover sawdust and offcuts from today’s job, kept briefly and swept away. An Azure Artifacts package is a finished, labeled part that goes into the warehouse for other carpenters to use for years. A container image is a fully assembled piece of furniture, shipped in its own crate.

i
Check current details

Supported package types, limits, and pricing are updated over time. Use this guide to understand the shape of the service, then confirm exact capabilities on Microsoft’s official pages before you decide.

3Core Concepts You Must Know

A handful of words appear in every Azure Artifacts conversation. Learn them once and the rest becomes easy.

Organization and project

In Azure DevOps, an organization is the top-level account of your company. Inside it live projects, each holding the work of a team: code, pipelines, boards, and packages. Both matter for Artifacts, since a feed can belong to either.

Feed

A feed is a private registry: a named container that holds packages and controls who may read or publish them. You can have many feeds, for example one per team, one per product, or one shared by the whole company. Developers point their package manager at the feed’s address.

Package and version

A package is the reusable unit, identified by name. A version is one specific release of it. Versions usually follow semantic versioning, written as three numbers separated by dots, such as 2.4.1. The first number (major) changes when something breaks compatibility, the second (minor) when new features are added safely, and the third (patch) for small fixes. A suffix such as “beta” marks a pre-release, a version not yet considered final.

Immutability

Once a version is published, it can never be changed. You cannot overwrite version 2.4.1 with different contents. This immutability guarantees that every build that asked for 2.4.1 got identical bits, today or next year. To fix a mistake, you publish a new version.

Upstream source

An upstream source is another registry that a feed can pull from, such as a public registry or another feed. When someone asks the feed for a package it does not hold, it fetches it from upstream and keeps a copy.

View

A view is a filtered window onto a feed, showing only versions that have been promoted into it, for example “pre-release” or “release”. Consumers who want only approved versions point at a view instead of the whole feed.

Retention policy

A retention policy is an automatic cleanup rule, such as “keep at most the latest fifty versions of each package”, to control storage use.

Permissions

Access is given through roles on a feed. A reader can download, a collaborator can also save packages from upstream, a contributor can publish, and an owner can manage settings and permissions.

flowchart TD
    ORG["Azure DevOps organization"] --> PRJ["Project"]
    ORG --> OF["Organization scoped feed"]
    PRJ --> PF["Project scoped feed"]
    PF --> PK["Package"]
    PK --> V1["Version 1.0.0"]
    PK --> V2["Version 1.1.0"]
    PK --> V3["Version 1.2.0-beta"]
    PF --> VW["Views: prerelease and release"]
    PF --> UP["Upstream sources"]
    PF --> RP["Retention policy"]
    
FIG 3.1 — How organizations, feeds, packages, versions and views relate
Everyday analogy

The organization is the whole company building. A feed is one warehouse room. A package is a type of part, such as “drawer slider”. A version is the numbered model of that part. A view is the “approved parts” shelf at the front. Upstream is the outside supplier that the warehouse orders from.

!
Common confusion

A feed is not a package and not a project. It is the registry that holds packages. Projects can have many feeds, and one feed can serve many projects if it is scoped to the organization.

4Package Types and Protocols

Azure Artifacts speaks the native language of several ecosystems, so developers use the tools they already know.

.NET

NuGet

Libraries for C# and other .NET languages. Used with the dotnet and NuGet command tools and the major .NET editors.

JavaScript

npm

Packages for web and server JavaScript. Works with the npm tool and compatible clients.

Java

Maven and Gradle

Java libraries and build plugins, for projects built with Maven or Gradle.

Python

Python packages

Libraries installed with pip and published with standard Python publishing tools.

Rust

Cargo

Crates for Rust projects, using the standard Rust package tool.

Anything

Universal Packages

A Microsoft format for any collection of files: models, datasets, tools, installers, or large binaries, with its own command line.

Why native protocols matter

A protocol is the agreed way for a tool and a server to talk. Because Azure Artifacts implements each ecosystem’s protocol, a feed looks to the npm tool like any other npm registry, and to the NuGet tool like any other NuGet source. Developers change an address and a sign-in, not their habits. Build scripts keep working with tiny changes.

Universal Packages in detail

Not everything is a library. Teams also share large files: trained machine learning models, test data sets, installers, or tool kits. Universal Packages give such files a name, a version, and a home in a feed, with the same permissions and retention as other packages. They can be very large, and uploads and downloads are handled efficiently by breaking content into pieces and reusing pieces that already exist.

NeedBest fitWhy
Shared .NET helper libraryNuGet packageNative to the language and tools
Front-end component librarynpm packageStandard in the JavaScript world
Shared Java service clientMaven packageFits the Java build chain
Data science helpersPython packageInstallable with pip
Big model file or toolsetUniversal PackageVersioned storage for any file collection
Application image to runContainer registry, not ArtifactsDifferent format and tooling
i
Mixed teams

One feed can hold several package types side by side. A full-stack team can keep its NuGet, npm, and Python packages in one feed, with one set of permissions.

5Feeds: Scope, Structure and Access

The feed is the central decision you make. Design it well and everything else becomes simpler.

Project-scoped and organization-scoped feeds

A feed can be project-scoped, belonging to a single project and inheriting its visibility, or organization-scoped, living at the top level and usable across all projects. Project-scoped feeds are the recommended default for new feeds in most cases, since they follow the project’s boundaries and are easier to reason about. Older feeds are often organization-scoped. Each style has its place.

Narrow

Project-scoped

Owned by one team’s project. Permissions and visibility follow the project, which makes ownership clear.

Wide

Organization-scoped

Shared across projects. Good for company-wide libraries, but it needs more careful permission planning.

How many feeds?

There is no single right answer, but the options have clear trade-offs.

One shared feed

  • Simple to find everything
  • One set of upstream rules
  • Easy for small companies

One shared feed, drawbacks

  • Everyone sees everything
  • Cleanup rules must suit all teams
  • A mistake affects the whole company

Feed per team or product

  • Clear ownership and permissions
  • Separate retention and cleanup
  • Smaller blast radius for mistakes

Feed per team, drawbacks

  • Consumers must know many addresses
  • Duplicate upstream copies use more storage
  • More setup to maintain

A popular middle path: one feed for publicly sourced packages with upstreams enabled, which acts as the controlled gateway to the outside world, plus a separate feed per team for its own published packages. Teams then chain these using upstream sources.

flowchart TD
    PUB["Public registries"] --> GW["Company gateway feed with public upstreams"]
    GW --> TA["Team A feed"]
    GW --> TB["Team B feed"]
    TA --> BA["Team A builds"]
    TB --> BB["Team B builds"]
    TA -.->|"upstream"| TB
    
FIG 5.1 — A gateway feed in front of team feeds

Visibility

A feed can be visible only to specific people and groups, to everyone in the organization, or, for feeds in public projects, to anyone on the internet. Pick the narrowest visibility that works, and remember that anything public cannot easily be taken back.

Everyday analogy

One big warehouse is easy to find things in but everyone has a key to everything. Many small rooms are safer but you need to know which door to knock on. The gateway feed is the receiving dock, where all outside deliveries are checked before being passed to individual rooms.

!
Gotcha: scope cannot always be changed

The scope of a feed, project or organization, is a design decision that is hard to reverse. Think before you create a feed, and write down who owns it.

6Architecture and Components

What sits behind a feed address, seen from a distance.

You never see the machines behind Azure Artifacts, because it is a cloud service run by Microsoft as part of Azure DevOps Services. Still, a rough picture explains its behavior. A request for a package enters through a protocol endpoint, passes an identity check and a permission check, is resolved against the feed’s metadata, and is served from durable storage, or fetched from an upstream source if needed.

flowchart TD
    CL["Client tools: dotnet, npm, pip, Maven, Cargo, universal"] --> EP["Protocol endpoints per package type"]
    EP --> AUTH["Identity and token validation"]
    AUTH --> PERM["Feed permission check"]
    PERM --> META["Feed metadata and package index"]
    META --> STORE["Durable package storage"]
    META --> UPS["Upstream proxy and cache"]
    UPS --> EXT["Public registries and other feeds"]
    EP -.-> AUD["Audit and usage records"]
    
FIG 6.1 — The path of a package request inside the service
1

Protocol endpoints

Each package type has an address that speaks that ecosystem’s protocol, so ordinary tools work unchanged.

2

Identity and permissions

The caller is identified by a token. The service checks that the identity holds a role on the feed that allows the requested action.

3

Metadata index

A catalog of package names, versions, dependencies, views, and status. Tools query this to decide what to download.

4

Package storage

Durable cloud storage that holds the package files themselves, replicated by the platform for safety.

5

Upstream proxy

When a requested package is not in the feed, this part asks the configured upstream, saves what it receives, and serves it.

6

Audit trail

Key actions, such as publishing, deleting, and changing permissions, are recorded for review.

A shared, multi-tenant service

Azure Artifacts serves many customers on shared infrastructure, with strict separation between organizations. Because the platform is shared, it applies usage limits and fair-use throttling, so one very busy client cannot slow down everyone else. A build that hammers the service with thousands of requests may see “too many requests” responses, and should be written to slow down and retry.

Cloud service and self-hosted server

Azure DevOps also comes as a product you can install in your own data center, called Azure DevOps Server. It includes package management too, with its own limits and feature set. This guide focuses on the cloud service, since that is what most teams use. If you must keep everything on your own servers, check the current feature list for the server version.

Everyday analogy

The endpoint is the loading bay with a label for each kind of delivery. The guard checks your badge, the clerk checks the catalog to find the shelf, the shelves hold the parts, and a courier fetches anything missing from the outside supplier, shelving a spare copy as it passes through.

7Internal Working: Versions, Resolution and Immutability

How a package manager decides which files to download, and why the answer is the same every time.

The dependency tree

Packages depend on other packages, which depend on others in turn, forming a dependency tree. Your application may list ten packages, but the full tree can contain hundreds. The package manager walks this tree, asks the feed for the list of available versions of each package, and picks versions that satisfy every rule. This is called dependency resolution.

Version ranges

A project rarely demands one exact version. It often says “any version from 2.4 up to, but not including, 3.0”. The package manager chooses the highest allowed version, or the lowest, depending on the ecosystem’s rules. Because a feed can publish new versions at any time, two builds run a week apart could pick different versions, unless you pin them. Many ecosystems offer a lock file, a record of the exact versions chosen, so that every build repeats the same choice.

Everyday analogy

A recipe that says “use any flour from this brand between type 1 and type 3” might give different cakes on different days. A recipe that says “use exactly this bag, batch number 4471” always gives the same cake. A lock file is the batch number.

Why immutability matters

Immutability protects three things. First, repeatability: version 2.4.1 means the same bits forever. Second, caching: tools and servers can safely keep copies of an immutable file without checking for changes. Third, trust: a security review of 2.4.1 stays valid, since nobody can swap its contents. Azure Artifacts enforces this: once a version has been published, publishing the same name and version again with different content is refused.

What you can do with a published version

Soft

Unlist or deprecate

Hide it from search and discourage new use, while existing builds can still fetch it.

Soft

Promote to a view

Mark it as approved by adding it to a view such as release.

Hard

Delete

Remove it. Deleted versions can be recovered from a recycle bin for a limited period, and the version number can never be reused for different content.

Rule

Fix forward

If a version is broken, publish a newer one. Do not try to replace the old one.

Metadata and the package index

Every package carries metadata: name, version, description, authors, dependencies, and license. The feed indexes this so that searches and resolution are fast without opening each file. For tools that need only to know “which versions exist?”, the index answers in a blink and the heavy file is downloaded only after the choice is made.

Storage efficiency

The service stores each package version once, however many feeds or views refer to it. Promoting a version into a view does not copy the file. It only adds a label. That is why promotion is instant and cheap, and why views are a good way to express approval without duplicating storage.

i
Interview-ready

If asked why package versions are immutable, say: it makes builds repeatable, lets clients cache safely, and keeps security reviews valid, because version 2.4.1 always means the same bytes. Mistakes are fixed by publishing a newer version.

8Data Flow: Publish and Restore

Follow one package from the moment a developer creates it to the moment another team’s build uses it.

sequenceDiagram
    participant D as Developer or pipeline
    participant F as Azure Artifacts feed
    participant S as Package storage
    participant C as Consumer build
    participant U as Public registry upstream
    D->>F: Publish package version 1.2.0 with token
    F->>F: Check identity, permission and version is new
    F->>S: Store package file and index metadata
    F-->>D: Success
    C->>F: Ask for versions of the package
    F-->>C: List of available versions
    C->>F: Download chosen version
    F->>S: Fetch file
    S-->>C: Package delivered
    C->>F: Ask for a public package not yet in feed
    F->>U: Fetch from upstream and save a copy
    U-->>F: Package
    F-->>C: Package delivered
    
FIG 8.1 — Publishing a private package and restoring both private and public ones

The publish journey

1

Build and pack

The library is compiled and tested, and then bundled into a package file with a name and a version number.

2

Authenticate

The tool sends the package with an access token, so the service knows who is publishing.

3

Validate

The service checks that the caller may publish to this feed and that this exact version does not already exist.

4

Store and index

The file is saved and its metadata added to the catalog. From now on, it is immutable.

5

Announce

The package appears in the feed. Other pipelines and developers can find and use it, often with notifications or automated updates.

The restore journey

Restore is the step where a build downloads all the packages it needs before compiling. The package manager first reads the project’s list of dependencies and its configured feeds. It then asks each feed for the available versions, resolves the dependency tree, downloads missing files, and stores them in a local cache on the build machine. Later builds on the same machine find them in the local cache, which is faster.

Where each delay comes from

  • First restore on a fresh machine: every package must be downloaded, so it is the slowest.
  • First request for a new public package: the feed must fetch it from upstream before serving it, adding a short extra delay once.
  • Repeated restores: served from the feed or the local cache, which is quick.
Everyday analogy

A new employee’s first day needs a full toolkit handed out from the warehouse. Later days only need the tools that are missing or updated. If the toolkit has a part the warehouse does not stock, the clerk orders it once, shelves a spare, and every later employee gets it instantly.

!
Gotcha: version conflicts on publish

A pipeline that publishes a fixed version number on every run will succeed once and then fail. Automate version numbers, for example by adding a build counter or tying them to release tags, so each run produces a new, unique version.

9Upstream Sources and Supply Chain Defense

Your product is only as safe as the packages inside it. Upstream rules are your first line of defense.

How upstream works

When you enable an upstream source on a feed, the feed becomes a smart middleman. A developer asks the feed for a public package. If the feed does not yet hold it, the feed fetches the right version from the public registry, saves a copy, and serves it. From then on, that version is served from your feed, even if the public registry is down or the original author deletes it. The feed also shows available public versions, so tools can resolve ranges, although only the versions actually used are copied.

flowchart TD
    B["Build asks for a package"] --> Q{"Is the version in the feed"}
    Q -->|"yes"| S["Serve from feed storage"]
    Q -->|"no"| U["Look in upstream sources in order"]
    U --> F{"Found upstream"}
    F -->|"yes"| SV["Save copy in feed"]
    SV --> S
    F -->|"no"| E["Return not found"]
    
FIG 9.1 — How a feed answers a request using upstream sources

Benefits

Resilience

Survive outages

Builds keep working when the public registry is unreachable, because used packages are already saved.

Stability

Survive deletions

If an author removes a package, your saved copy remains, so your builds do not suddenly break.

Control

One address

Developers configure a single feed address, and the company decides what is reachable behind it.

Audit

Know what you use

The saved list shows exactly which public packages and versions your organization has pulled in.

The dependency confusion attack

Imagine your company has a private package called “acme-billing-helper”. An attacker discovers the name, publishes a package with the same name to the public registry, and gives it a very high version number. A poorly configured build asks both places for the latest version, sees that the public one has a higher number, and downloads the attacker’s code into your product. This is called dependency confusion, and it has hit well-known companies.

Azure Artifacts defends against this with a control on each package: whether versions that come from outside are allowed or blocked. When a package name exists in your own feed, outside versions of the same name can be blocked, so a public lookalike is never served. Keep the setting at its protective choice for internal package names, and never let public and private packages with the same name mix.

Everyday analogy

A mailroom receives two parcels addressed to the same department, one from the company’s known supplier and one from a stranger who claims a newer edition. The mailroom rule says: for items we make ourselves, never accept look-alikes from outside.

Other supply chain risks

  • Typosquatting: a malicious package named almost like a popular one, hoping for a typing mistake.
  • Compromised maintainers: a trusted public package gets a poisoned update after an account is hijacked.
  • Vulnerable versions: an honest package has a security hole discovered later.
  • Abandoned packages: something your product depends on is no longer maintained.
Habit 1

Use lock files

Pin exact versions so a surprise new release cannot slip in during a build.

Habit 2

Gate the gateway

Let only a small group save new packages from public sources, and review additions.

Habit 3

Scan dependencies

Run automated checks for known vulnerabilities and unusual licenses during the build.

Habit 4

Keep an inventory

Maintain a list of packages in each release, so that when a hole is announced you know quickly whether you are affected.

i
Collaborator role

In a feed with upstream sources, only identities with at least the collaborator role can cause new public packages to be saved. Giving this role to every build account makes your feed a free-for-all, so grant it with thought.

10Views and Promotion: From Beta to Release

Not every published version is ready for everyone. Views let you stage trust.

The problem views solve

When a team publishes a new version, it is untested by other teams. If every consumer’s build picked it up at once, one bug could break dozens of projects. Teams want a way to say “this version is a candidate” and later “this one is approved for everyone”.

Default views

A feed commonly offers three views. The local view contains every version published to the feed and any version saved from upstream. The prerelease view contains candidate versions. The release view contains versions that have been approved. Consumers who point their tools at the release view only ever see approved versions, and the feed’s view addresses look slightly different from the main feed address.

flowchart LR
    PUB["Publish new version"] --> L["Local view: all versions"]
    L -->|"passes automated tests"| PR["Prerelease view: candidates"]
    PR -->|"approved after review and wider testing"| RL["Release view: approved only"]
    RL --> PRODB["Production builds"]
    PR --> TESTB["Test and early adopter builds"]
    L --> DEVB["Developers on the same team"]
    
FIG 10.1 — Promoting a version through views as confidence grows
1

Publish

A new version lands in the feed, visible in the local view to the owning team.

2

Test automatically

A pipeline runs deeper tests, scans, and license checks against that exact version.

3

Promote to prerelease

If tests pass, the version is added to the prerelease view, so early adopters can try it.

4

Promote to release

After feedback and approval, the version joins the release view. Production builds can now use it.

Why promotion is cheap and safe

Promotion adds a label. It does not copy or change the package, so the bytes tested in prerelease are exactly the bytes shipped in release. This avoids the dangerous habit of rebuilding “the same” code for production, which can yield subtly different results.

Views and version labels together

Views describe approval status, while version numbers describe change. A team can publish 3.0.0-beta.1, 3.0.0-beta.2, and so on, as pre-release versions, then publish 3.0.0 as the final. Combining semantic version suffixes with views gives consumers two signals about stability.

Everyday analogy

A new medicine goes through trial stages before pharmacies can sell it. The same box is moved from the “in trial” shelf to the “approved” shelf. Nobody repacks it. Views are those shelves.

!
Gotcha

A consumer pointing to the default feed address, not to a view, sees every version, including untested ones. Make sure production builds reference the release view address, and document it for new team members.

11Authentication and Permissions

Who may read, who may publish, and how they prove who they are.

Feed roles

RoleCan doTypical holder
ReaderSearch and download packagesDevelopers who only consume
CollaboratorEverything a reader can, plus save packages from upstreamDevelopers and builds that restore with upstream sources enabled
ContributorEverything a collaborator can, plus publish and promoteLibrary teams and their release pipelines
OwnerEverything, including changing settings and permissionsA small group of feed administrators

Proving identity from a developer machine

Developers can sign in to package tools in several ways.

Best for people

Credential providers

A helper plug-in that opens a normal company sign-in window the first time, and then handles tokens automatically. Available for NuGet and .NET tools, and helper tools exist for other ecosystems.

Flexible

Personal access tokens

A generated secret text with limited permissions and an expiry date. Handy for scripts, but it must be guarded like a password.

Proving identity from a pipeline

Pipelines have their own identity, a build service account. Pipeline steps called authentication tasks, one for each ecosystem, set up the package tool with a short-lived token for that identity, so no secret needs to be stored. For the pipeline to publish or restore, its identity must be granted a role on the feed. If a build fails with “unauthorized” for a feed in another project, the missing role grant is the most common cause.

flowchart TD
    P["Pipeline run starts"] --> ID["Pipeline uses build service identity"]
    ID --> T["Authentication step creates short lived token"]
    T --> TOOL["Package tool uses token"]
    TOOL --> F["Feed checks role of the identity"]
    F -->|"role allows"| OK["Restore or publish succeeds"]
    F -->|"no role"| NO["Unauthorized error"]
    
FIG 11.1 — How a pipeline proves who it is and what it may do

Managing tokens safely

  • Least privilege: give tokens only the scope they need, such as read-only package access.
  • Short life: choose short expiry dates, and rotate before they run out.
  • Never in code: do not commit tokens to source repositories or paste them into chat. Use secret variables or a key vault.
  • Prefer identities: where possible, use managed or federated identities and sign-in providers instead of long-lived tokens.
  • Organization controls: administrators can limit how long tokens may live, or who may create them.

Groups, not individuals

Grant feed roles to groups from your identity system instead of to single people. When someone joins or leaves a team, their access changes automatically with their group membership, which is both safer and easier to audit.

Everyday analogy

A warehouse badge is better than a copy of the master key. The badge works only at certain doors, expires, and can be cancelled. A personal access token is a numbered key: handy, but if it is lost, anyone who finds it can use it until it expires.

!
Classic mistakes

Using a never-expiring full-access token in a shared script, giving every build account contributor rights on every feed, and leaving a former employee’s tokens active.

12Pipeline Integration: Build, Version, Publish, Restore

Packages come alive when pipelines produce and consume them automatically.

A typical library pipeline

1

Restore

Authenticate to the feed and download the library’s own dependencies.

2

Build and test

Compile and run unit tests. A failing test stops the pipeline.

3

Version

Calculate a unique version number, using semantic rules plus a build counter or branch name for pre-releases.

4

Pack and scan

Create the package file and run security and license scans.

5

Publish

Push the package to the feed, usually from the main branch or a release tag, not from every experimental branch.

6

Promote

After tests of consumers pass, add the version to the next view.

flowchart LR
    LIB["Library repository"] --> LP["Library pipeline"]
    LP --> FD["Feed"]
    FD --> AP["Application pipeline restores package"]
    FD --> AP2["Another application pipeline"]
    AP --> APPA["Application A release"]
    AP2 --> APPB["Application B release"]
    
FIG 12.1 — One library pipeline feeding many application pipelines

Choosing version numbers

Good versioning is a team agreement, ideally automated. Many teams keep the major and minor numbers in a file in the repository, and let the pipeline fill in the patch number from the build counter. Builds from side branches get a pre-release suffix that includes the branch name, so experiments never look like official releases. Tags in source control can trigger the final release version.

Making restores fast

Speed

Pipeline caching

Save the downloaded packages between runs, keyed by the lock file, so unchanged dependencies are not fetched again.

Speed

One feed address

Listing many feeds makes tools query each one in turn. Use one feed with upstreams where possible.

Stability

Lock files

Avoid repeating version resolution and avoid surprise upgrades.

Fewer

Trim dependencies

Each unneeded package adds download time and risk, so remove what you do not use.

Using packages from other places

Azure Artifacts feeds are ordinary registries to ordinary tools, so they also work from GitHub Actions workflows, from developer laptops, from other build systems, and from container builds. In each place you provide the feed address and a suitable sign-in.

i
Do not publish from everywhere

Limit publishing to trusted pipelines on protected branches, and grant contributor rights only to those pipelines. A package from a laptop is harder to trace than one built by a controlled, logged pipeline.

13Security: Layers Around Your Packages

A package is code that your product trusts completely. Protect the warehouse and everything that enters it.

flowchart TD
    A["Who may use the feed: identity and roles"] --> B["How they sign in: short lived tokens"]
    B --> C["What may enter: upstream rules and review"]
    C --> D["How it is built: protected pipelines"]
    D --> E["What is inside: vulnerability and license scans"]
    E --> F["Who changed what: audit logs"]
    F --> G["Fast response: inventory and alerts"]
    
FIG 13.1 — Layers of supply chain protection

Control who can publish

Publishing rights are powerful. A malicious or careless publish can plant code in many products at once. Restrict contributor roles to release pipelines and a few owners, protect the branches those pipelines run from, and require code review before changes reach them.

Control what comes in

Treat the gateway to public packages as a checkpoint. Limit who can save new public packages, review newly added ones, and block outside versions of your private names. Consider an approval process for packages with unusual licenses or low maintenance.

Scan and inventory

Automated tools can check the full dependency tree for known security issues and risky licenses. Azure DevOps offers security features that include dependency scanning for supported repositories, and many third-party scanners work in pipelines. Keep a record of the exact package versions inside each release, sometimes called a software bill of materials. When a new vulnerability is announced, you can answer “are we affected?” in minutes.

Audit trail

Azure DevOps keeps an audit log of important actions, such as changing feed permissions, creating or deleting feeds, and changing upstream settings. The log can be viewed in the portal and sent to a monitoring system. Review it periodically and set alerts for suspicious changes, like permissions widened late at night.

Network and sign-in policies

Organization-level controls, such as conditional access policies and allowed network ranges, apply to Azure DevOps and therefore protect access to feeds. Combine them with multi-factor sign-in for people.

Strong signs

  • Only release pipelines can publish
  • Outside versions of internal names are blocked
  • New public packages are reviewed
  • Lock files and scans are standard
  • Audit logs are watched

Warning signs

  • Everyone is a contributor on every feed
  • Packages are built and pushed from laptops
  • Long-lived tokens pasted into scripts
  • No record of which versions each release contains
  • Nobody owns the feed
Everyday analogy

A food factory checks suppliers, inspects each delivery, keeps batch records for every product, and can recall exactly the affected batches when a problem is found. Your package process needs the same traceability.

14Reliability, Scalability and Performance

Builds stop when the warehouse is closed. Plan so that one failure does not halt your whole company.

Availability of the service

Azure Artifacts is part of a Microsoft-run cloud service with a published availability promise, called a service level agreement. The platform stores data redundantly and recovers from machine failures on its own. No service is perfect, though. Occasional incidents on Azure DevOps will affect pipelines and feeds, and your design should make them survivable.

Upstream caching as resilience

One of the best protections is already built in. Public packages saved in your feed keep serving even if the public registry is offline. The weak spot is a package version you have never used before, which cannot be fetched during a public registry outage. Teams with strict needs pre-warm the feed by restoring their common dependencies after each approval, so nothing is fetched for the first time during an emergency.

Local and build-agent caches

Package managers keep a local cache on each machine. Build agents that are re-created for every run lose this cache, so use pipeline caching or agents that keep their cache between runs. A warm cache lets builds proceed even if the feed is briefly unreachable, because the needed files are already on the machine.

Throttling and fair use

Azure DevOps protects itself with rate limits. A build farm that starts hundreds of jobs at once, each downloading thousands of small files, can hit “too many requests” responses and slow down. Spread the load, enable caching, trim unused dependencies, and make scripts retry politely with increasing waits.

Plan A

Cache everything reasonable

Pipeline caches, local caches, and upstream-saved copies mean most requests never go far.

Plan B

Retry with backoff

Temporary errors are normal. Wait and try again before declaring failure.

Plan C

Know your emergency path

Decide how critical hotfix builds could proceed if the service is down, such as using a pre-populated cache on a build machine.

Plan D

Keep sources recoverable

Because packages are built from source, the real insurance is a repository and pipeline that can rebuild any version.

Large packages

Very large files, such as machine learning models, are best shared as Universal Packages, which upload and download in chunks and reuse unchanged pieces between versions. Even so, big downloads are slow on poor links. Place build agents close to the service, cache large downloads, and avoid pulling them on every run.

Scaling with the organization

As the number of packages and consumers grows, the main challenges are human, not technical: naming rules, ownership, cleanup, and discoverability. Write a short package policy covering naming prefixes, version rules, who owns each feed, and how to deprecate packages. A large catalog without ownership turns into a junk drawer.

i
Disaster recovery in plain words

The feed holds copies of built outputs, but your source code and pipeline definitions are the real recipe. If everything in a feed were lost, you could rebuild your own packages from source, and public packages could be fetched again. Make sure that rebuilding is actually possible, and test it.

15Monitoring, Retention and Cost

A warehouse that never throws anything away eventually fills the building. Watching usage and cleaning up keeps it healthy and affordable.

What to watch

Storage

Size over time

Azure DevOps shows how much storage the organization uses and which feeds use the most. Check it regularly so growth is never a surprise.

Failures

Pipeline errors

Failed restores and publishes show up in pipeline results. A sudden rise in unauthorized or not-found errors often means a permission or upstream change.

Changes

Audit events

Permission changes, new upstream sources, and deleted feeds are recorded and can be reviewed or exported.

Usage

Who uses what

Package pages show download counts and the versions consumers actually use, which helps decide when an old version can be retired.

Retention policies

Continuous publishing creates many versions. Most are never used again after a newer one appears. A retention policy automatically removes the oldest versions beyond a number you choose for each package. Versions that have been promoted to a view are normally kept, so the approved ones that real products use are safe from cleanup. Choose the number with care: keep enough history to roll back and to rebuild older product releases.

The recycle bin

Deleted package versions move to a recycle bin for a limited time before being permanently removed. This gives a safety net for mistakes. Remember, though, that once a version is truly gone, its number cannot be reused for different contents, so consumers who needed it must move to another version.

Cost awareness

Azure Artifacts offers a free allowance of storage for each organization, and usage above it is billed according to Microsoft’s current pricing. Because prices and allowances change, check the official pricing page for today’s numbers. What stays true is the cost drivers: total stored size, number of retained versions, and big files like Universal Packages or large binaries.

Cost driverWhy it growsHow to control it
Many old versionsEvery pipeline run publishes a new oneRetention policies, and publish only from main or release branches
Large binariesModels, installers, or media in packagesStore only what must be versioned, and compress files
Abandoned feedsOld projects keep their packages foreverAssign owners, review yearly, archive or delete
Upstream copiesEvery used public version is savedRemove unused dependencies and old saved versions
Everyday analogy

A pantry needs a regular check. Keep the staples and recent items, discard the expired cans, and write down what you actually use. Without that, you pay for shelf space full of things nobody will ever eat.

16Design Patterns and Anti-Patterns

Ways of organizing feeds that experienced teams repeat, and traps that they learned to avoid.

Pattern: one organization feed with upstreams

A single organization-wide feed with public upstreams gives every team one address, one set of rules, and one cache. It suits small to medium companies where teams share most libraries.

Pattern: team feeds plus a shared gateway feed

Each team has its own feed for its internal libraries, and each team feed uses one shared “gateway” feed as an upstream. The gateway feed is the only one connected to public registries and is managed by a platform team. Teams get independence, and the company gets a single controlled entrance.

flowchart TD
    PUBR["Public registries"] --> GW["Gateway feed managed by platform team"]
    GW --> TA["Team A feed"]
    GW --> TB["Team B feed"]
    GW --> TC["Team C feed"]
    TA --> BA["Team A builds"]
    TB --> BB["Team B builds"]
    TC --> BC["Team C builds"]
    TA -.->|"upstream of other feeds if allowed"| TB
    
FIG 16.1 — Team feeds sharing a single controlled gateway

Pattern: promotion by views

Every library publishes once, then moves through prerelease and release views. Consumers choose their level of risk by choosing a view.

Pattern: build once, promote the same bits

Never rebuild for production. The package tested is the package shipped.

Anti-patterns

Do this

  • Use a gateway or upstream-enabled feed
  • Name internal packages with a company prefix
  • Automate versions and publishing
  • Give roles to groups
  • Assign an owner to every feed

Avoid this

  • Letting each developer add their own package sources
  • Publishing manually from laptops
  • Reusing a version number for new contents
  • Putting secrets, such as passwords, inside packages
  • Using a feed as a general file dump
ADR-01Accepted
Decision: use a single gateway feed for all public packages

Context: Teams each configured their own package sources, causing inconsistent versions, hidden risk, and long restore times.

Decision: A platform team owns one gateway feed with public upstreams. All team feeds use it as their only upstream.

Consequences: One place to review, block, and audit public packages. A small approval step adds slight delay for brand-new dependencies, which the team accepts for the safety gained.

Make the safe way the easy way, and people will follow it without being told.

17Best Practices and Common Mistakes

A checklist you can adopt on the first day, and a list of stumbles to skip.

Best practices

1

Choose scope on purpose

Prefer project-scoped feeds for team libraries, and organization-scoped for truly shared ones. Decide before creating feeds, since changing later is awkward.

2

Write naming rules

Use a consistent prefix or namespace for internal packages so they are easy to find and impossible to confuse with public ones.

3

Follow semantic versioning

Major for breaking changes, minor for new features, patch for fixes. Consumers rely on this promise.

4

Automate the lifecycle

Pipelines build, version, scan, publish, and promote. Humans review and approve.

5

Protect the entrance

Control upstream additions, block lookalike names, and use lock files.

6

Use least privilege

Readers by default, contributors only for release pipelines, owners for a small group.

7

Clean up on a schedule

Retention policies, yearly feed reviews, and a plan for deprecated packages.

8

Document for newcomers

A one-page guide with the feed address, how to sign in, how to publish, and who to ask.

Common mistakes

MistakeWhat happensBetter approach
Mixing private and public packages without blocking rulesDependency confusion riskBlock outside versions for internal names
Hard-coded version number in the pipelineSecond publish failsGenerate a unique version per run
Build account lacks feed permissionUnauthorized errors, especially across projectsGrant the build identity the right role
Long-lived token in a repositoryAnyone with repo access gets feed accessUse pipeline authentication and secret stores
Pointing production to the default feed viewUntested versions get usedUse the release view address
Treating Artifacts as a container registryContainer images cannot be storedUse Azure Container Registry for images
Never cleaning upGrowing bills and clutterRetention policies and ownership
!
The unpublished package problem

Famous incidents in the wider industry show that when a widely used tiny package disappears, thousands of builds break. Saved upstream copies and pinned versions are your protection. Never assume that something is permanently available just because it was available yesterday.

18Real-World Scenarios

These are composite examples that show typical situations. They are illustrations, not reports about specific companies.

Scenario 1: A shared UI component library

Situation: A retail company has six web applications that all need the same buttons, forms, and color rules. Developers were copying files between repositories and they had drifted apart.

Solution: The design team publishes the component library as an npm package to a project feed. Application teams install a specific version. Fixes are made in one place, released as a new version, and consumers upgrade when ready.

Result: Consistent appearance, faster fixes, and clear version history.

Scenario 2: Protecting a bank-style build from outages

Situation: A financial services team lost a day when a public registry had an outage during a release.

Solution: They moved all restores through a feed with upstreams, locked dependency versions, and added a nightly job that restores every product so that all used packages are saved in the feed in advance.

Result: Later registry hiccups did not stop releases.

Scenario 3: Sharing .NET libraries across many services

Situation: A logistics company has dozens of microservices that share logging, security, and messaging libraries.

Solution: Library teams publish NuGet packages with semantic versions. Prerelease versions are tested by two pilot services, then promoted to release. A dependency update tool opens automatic update requests in service repositories.

Result: Services stay current, and breaking changes are spotted in pilots before everybody receives them.

Scenario 4: Shipping large data files with software

Situation: A data science group needs to version trained models of several hundred megabytes together with their applications.

Solution: Models are published as Universal Packages with version numbers matching the application release. Pipelines download only the version they need.

Result: Reproducible releases and no binary files stuffed into source repositories.

Scenario 5: Responding to a newly announced vulnerability

Situation: A widely used library is announced to have a serious flaw.

Solution: Because the company keeps a list of package versions inside each release, security staff query the list and find three affected services within the hour. Fixed versions are published to the feed, promoted, and pipelines rebuild the services.

Result: Quick, targeted response instead of a company-wide scramble.

19Azure Artifacts Compared with Related Tools

Several tools store build outputs. Knowing which does what avoids wasted effort.

ToolBest forKey difference
Azure ArtifactsReusable libraries and packages across projectsVersioned, shared, with upstreams and views
Pipeline artifactsPassing build output between stages of one pipeline runTied to a run, temporary, not a shared registry
Azure Container RegistryContainer images and related artifactsSpeaks the container protocol, which Artifacts does not
GitHub PackagesPackages close to GitHub repositoriesIntegrated with GitHub permissions and Actions
Third-party repository managersOrganizations that want one tool across many clouds and formatsOften broader format support, separate to run or buy
Azure Blob StorageRaw file storageNo package semantics such as versions or dependency lookup
flowchart TD
    Q["What are you storing"] --> A{"Container image"}
    A -->|"yes"| ACR["Azure Container Registry"]
    A -->|"no"| B{"Reusable package for other projects"}
    B -->|"yes"| ART["Azure Artifacts feed"]
    B -->|"no"| C{"Only passed between stages of one pipeline"}
    C -->|"yes"| PA["Pipeline artifacts"]
    C -->|"no"| BLOB["Blob storage or another store"]
    
FIG 19.1 — Choosing where a build output should live

When to look elsewhere

  • If your code and workflows live in GitHub, GitHub Packages may be simpler.
  • If you need package formats Azure Artifacts does not offer, a third-party repository manager may fit.
  • If you run Azure DevOps Server on your own machines, remember it is a separate product with its own feature set and versions, so check its documentation.
i
Check current details

Supported package types, limits, and pricing change over time. Before making a final design decision, confirm them on Microsoft’s current documentation pages.

20Frequently Asked Questions

Q1What is Azure Artifacts in one sentence?

It is a managed package repository inside Azure DevOps where teams store, share, and control versioned libraries and other packages.

Q2Is Azure Artifacts only for .NET?

No. It supports NuGet, npm, Maven, Gradle, Python, Cargo, and Universal Packages, so many languages can share one service.

Q3Can I store Docker images in it?

No. Container images belong in a container registry such as Azure Container Registry.

Q4What is the difference between a feed and a package?

A feed is the shelf or catalog. A package is one item, with many versions, stored on that shelf.

Q5Can I overwrite a version that I already published?

No. Published versions are immutable. Fix the problem and publish a new version. You may unlist or delete a bad version, but its number cannot be reused for different contents.

Q6What does an upstream source do?

It lets your feed fetch packages from a public registry or another feed, save a copy, and serve it from your own feed afterward.

Q7How do I stop dependency confusion?

Block outside versions of your internal package names, use a distinctive naming prefix, pin versions with lock files, and limit who can save new public packages.

Q8What are views for?

They label versions by readiness, such as prerelease and release, so consumers can choose how much risk they accept without copying packages around.

Q9Why does my pipeline get an unauthorized error?

The most common reasons are that the build identity has no role on the feed, the authentication step is missing, or the feed lives in another project and the identity was never granted access.

Q10Project feed or organization feed?

Use project feeds when packages belong to one team’s work and should follow that project’s permissions. Use organization feeds for packages that many projects share. Decide early.

Q11Is it free?

There is a free storage allowance, and usage beyond it is billed. Check Microsoft’s pricing page for current amounts.

Q12Can people outside my company use my feed?

Feeds can be opened to chosen users or, in public projects, to wider audiences, depending on organization settings. By default, treat feeds as private and grant access deliberately.

Q13How is it different from pipeline artifacts?

Pipeline artifacts carry files between stages of one run and expire. Azure Artifacts packages are long-lived, versioned, and shared across projects and teams.

Q14What happens if a public package is deleted?

If your feed already saved that version from upstream, you can still use it. If not, you cannot fetch it. That is why saving through upstreams and pre-warming matter.

Q15Do I need to be an expert to start?

No. Create a feed, publish one small package from a pipeline, consume it from another project, and you have learned the core loop. The rest is policy and good habits.

21Summary and Key Takeaways

Azure Artifacts turns scattered code copies into a controlled, versioned supply of building blocks.

You began with a simple idea: a good workshop keeps a labeled parts warehouse instead of letting every craftsperson make their own copies. Azure Artifacts is that warehouse for software. Feeds hold packages, packages hold immutable versions, upstream sources bring in public packages safely, and views let you promote trust step by step. Authentication, roles, and pipelines connect all of it to everyday work, while retention, monitoring, and clear ownership keep it tidy and affordable.

The deeper lesson is about trust. Every package you use is code you did not write running inside your product. The practices in this guide, such as pinned versions, blocked lookalikes, reviewed additions, protected pipelines, inventories, and audit logs, are how you keep that trust earned rather than assumed.

Key Takeaways

  • Azure Artifacts is a managed package repository in Azure DevOps supporting NuGet, npm, Maven, Gradle, Python, Cargo, and Universal Packages.
  • Published versions are immutable, so every release can be trusted and reproduced; fix mistakes by publishing a new version.
  • Upstream sources save copies of public packages, which improves resilience, but block outside versions of your internal names to prevent dependency confusion.
  • Views promote the same package from prerelease to release without copying, and production should only use the release view.
  • Use group-based roles, pipeline identities, and short-lived tokens, and publish only from protected, automated pipelines.
  • Plan for retention, cost, and ownership early, and keep an inventory of package versions in every release.
  • Use Azure Container Registry for images and pipeline artifacts for temporary stage handoffs; always confirm current limits and prices on Microsoft’s pages.