Skip to main content
Cloud DevOps Solutions
Get a quote Talk to an engineer

Azure DevOps

Secure Service Connections to Azure, AWS and Third-Party Tools

A service connection is how an Azure DevOps pipeline authenticates to an external system such as Azure, AWS, a container registry or GitHub. We create them with least privilege, prefer workload identity federation over stored secrets, restrict which pipelines may use them, and add approvals for production targets.

Key takeaways

  • A service connection is a credential that pipeline code can use, so it is a security boundary.
  • Workload identity federation replaces stored secrets with short-lived tokens for Azure.
  • Scope each connection to a resource group or role, not a whole subscription.
  • Restrict use to specific pipelines and add checks on connections that reach production.
  • Connections to AWS and other services follow the same principle: least privilege and no shared keys.

A connection is a credential with a pipeline attached

When engineers think of pipeline security they think of secrets. Service connections are the credentials behind many of those secrets, and they are often the most powerful ones in the organisation. A connection to Azure with Contributor on a subscription, usable by any pipeline in the project, means anyone who can edit a pipeline can change or delete resources.

This page describes how we create, scope and govern service connections as part of our Azure DevOps consulting. It works together with Key Vault integration and the review controls in branch policies.

What good looks like

  • Every connection has a clear purpose, owner and environment.
  • Azure connections use workload identity federation and have no client secret.
  • Roles are the minimum needed, scoped to a resource group or specific resources.
  • Only named pipelines can use a connection, and production connections require approval.
  • Unused connections are removed.

How it works in practice

Azure: federation and scope

For Azure Resource Manager, you can authenticate with an app registration or a managed identity. With workload identity federation, Entra ID is configured to trust tokens issued by Azure DevOps for a specific organisation, project and connection. The pipeline exchanges that token for an Azure access token at run time. No password exists to store.

The identity behind the connection receives an Azure role at the narrowest useful scope. A pipeline that deploys one application needs rights on that application’s resource group, not the subscription. An infrastructure pipeline that runs Terraform may need broader rights, which is why it uses a different connection with stronger checks. Role assignments are defined in code, so they are reviewable:

resource "azurerm_role_assignment" "deploy_shop_dev" {
  scope                = azurerm_resource_group.shop_dev.id
  role_definition_name = "Contributor"
  principal_id         = azuread_service_principal.ado_shop_dev.object_id
}

For a deploy job that only updates a web app, a more specific built-in or custom role is better than Contributor. See our Terraform service for managing these assignments as code.

AWS and other clouds

Azure DevOps can deploy to AWS using the AWS Toolkit for Azure DevOps, with a service connection that assumes an IAM role. The role carries only the permissions the job requires, such as pushing to one container repository or updating one stack. We avoid IAM users with static keys shared by many pipelines, and we agree role boundaries with your AWS administrators so neither side is surprised.

Registries, source control and third parties

Docker registry connections reach Azure Container Registry, Docker Hub or others. For ACR we prefer identity-based access over admin credentials. GitHub connections allow pipelines to build from GitHub repositories, and we limit them to the repositories needed. Generic connections hold tokens or basic credentials for tools such as scanners and notification services. These are the most likely to contain long-lived secrets, so each is documented with an owner and expiry.

Lock down usage

Three settings do most of the work. Do not grant access to all pipelines; authorise specific ones. Add approvals and checks, including branch control so only main can use a production connection. And use the “required template” check where appropriate, so only pipelines extending an approved template reach the connection. This matters because pipeline YAML is code. If any contributor can add a step that uses a powerful connection, the connection is only as safe as your review process.

Separate identities for separate trust levels

Pull request validation builds run code that has not yet been reviewed, sometimes from forks. They should use no connection that can change anything, or only read-only ones. Deployment pipelines running reviewed code from protected branches get the write connections. This split is simple, and it stops the most common route to a pipeline compromise.

Decisions and trade-offs

Managed identity or app registration? Managed identities suit self-hosted agents running in Azure. App registrations with federation work on Microsoft-hosted agents too. We choose by where the pipeline runs.

Automatic or manual connection creation? The wizard is quick but may assign broad roles by default. Manual creation, with federated credentials defined in code, takes longer and is more controlled. We use the latter for production.

Connection per team or central platform ownership? Central ownership gives consistent security. Delegated ownership gives speed. Many organisations let teams own non-production connections and the platform team own production.

When not to over-engineer. For a small sandbox project with disposable resources, a single scoped connection is fine. Add structure as the blast radius grows.

Common failure modes

  • Expired secrets. A client secret lapses and releases stop. Federation removes this class of failure.
  • Subscription-level Owner. Often granted by the wizard. We reduce it.
  • Orphaned connections. Created for a former project and still powerful.
  • Shared tokens. One personal token used by many pipelines, tied to someone who has since left.

Auditing and retiring connections

A connection inventory is only useful if it stays true. We review the list of connections in each project and ask three questions of each: who owns it, which pipelines used it recently, and what is the highest role it holds. Azure DevOps keeps an audit log of connection creation, permission changes and usage, which can be streamed to a log store so changes to production connections raise a notification rather than waiting for a quarterly review.

A worked example: a team has a connection called azure-prod that was created by the wizard with Contributor across a whole subscription and authorised for all pipelines. We create two replacements, one scoped to the application resource group for deployments and one read-only for pipelines that only inspect state. We switch the pipelines over one at a time, confirm each run succeeds, and only then delete the original. Deleting first and fixing breakage afterwards is how releases get blocked on a Friday afternoon.

Delivery and handover

You receive a connection inventory with owners, rebuilt connections, role assignments as code, enforced checks and a short standard for creating new ones. We also test denied access: a pipeline that should not reach production must fail.

How to tell it is working

No connection holds a long-lived secret that matters, an audit can list who and what can reach production in minutes, credentials never expire unexpectedly, and nobody needs subscription Owner to ship software. To get your connections reviewed, book a consultation.

References

How we deliver it

  1. 01

    Inventory existing connections

    We list every connection, what it can reach, which pipelines use it, and when its credentials were last rotated.

  2. 02

    Define the access model

    Connections are planned per environment and purpose, with the least role that lets each job work.

  3. 03

    Create federated identities

    Entra ID app registrations or managed identities with federated credentials replace client secrets for Azure.

  4. 04

    Connect other platforms

    AWS, container registries, GitHub and other systems are connected with scoped roles or tokens stored properly.

  5. 05

    Lock down usage

    Pipeline permissions, approvals and checks restrict who can use each connection and from which branch.

  6. 06

    Review and retire

    Unused connections are removed, and a regular review catches new ones that are over-privileged.

Tools and technologies

Azure DevOpsMicrosoft Entra IDAzure RBACManaged IdentityAWS IAMAzure Container RegistryDocker HubGitHubTerraformAzure Key Vault

Frequently asked questions

What is a service connection in Azure DevOps?
A service connection is a stored, named way for pipelines to authenticate to an external service. Pipelines refer to it by name and Azure DevOps supplies the credential at run time. Types include Azure Resource Manager, AWS, Docker registry, Kubernetes, GitHub and generic connections.
What is workload identity federation for service connections?
It lets a connection authenticate to Azure using a short-lived token issued by Azure DevOps and trusted by Entra ID, instead of a stored client secret. There is nothing to leak or rotate, and the trust can be limited to a specific project and connection. It is the recommended option for Azure.
How do pipelines authenticate to AWS?
Typically through an AWS service connection, using the AWS Toolkit for Azure DevOps, that assumes an IAM role with limited permissions. Avoid long-lived access keys with broad rights. We scope the role to the exact actions and resources needed and review it with your AWS administrators.
How do we stop pipelines misusing a connection?
Turn off access for all pipelines, authorise only specific pipelines, and add checks such as approvals and branch control on connections that reach production. Pair this with branch policies so pipeline YAML cannot be changed without review. Otherwise anyone who can edit a pipeline can use its connections.
Should we use one connection or many?
Use one per environment and purpose. A single powerful connection used everywhere is convenient but turns any compromised pipeline into full access. Separate dev and production connections, and separate read-only from deploy connections, so permissions match the job.

Talk to an engineer about azure devops service connections

Book a free 30-minute call. We review your current setup and tell you honestly whether and how we can help.

Written by Saddique Khan, DevOps / SRE / Cloud Consultant Engineer. Last updated 2026-10-08.