Self-hosted service
Azure/azure-service-operator avatar
Azure/azure-service-operator

azure-service-operator: Azure resources managed with kubectl

Azure Service Operator allows you to create Azure resources using kubectl

916 stars269 forksGoMIT

At a glance

What is it?
Azure Service Operator lets you create Azure resources from inside Kubernetes with kubectl apply, using custom resource definitions generated from the Azure OpenAPI specifications and a controller that reconciles them against the real Azure state. Version 2 is the line to use, and version 1 is deprecated and unmaintained.
Who is it for?
azure-service-operator suits a team that already runs Kubernetes and wants its Azure dependencies to be declared and reconciled in the same manifests as the workloads that use them, rather than provisioned separately through the Azure CLI or Terraform.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 2 days ago.
What is it written in?
Mainly Go, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on November 7, 2026, and from our analysis. They are not legal advice.

From daily snapshots

Star history

  • Azure/azure-service-operator916 ★ · +1
Star history
Repository2026-10-232026-11-07
Azure/azure-service-operator915916

1 Stars in the last 15 days, measured from the daily GitHub snapshot. Compare with other projects

Editorial analysis

Provisioning Azure from a Kubernetes manifest

Azure Service Operator helps you provision Azure resources and connect your applications to them from within Kubernetes. The README puts the use case plainly: if you want to use Azure resources but would prefer to manage those resources using Kubernetes tooling and primitives, for example kubectl apply, then Azure Service Operator might be for you.

The problem it addresses is a split-brain one. A typical cloud application has two provisioning systems: Kubernetes manifests for the workloads, and a separate tool, often Terraform or a CI pipeline with the Azure CLI, for the Azure-side dependencies such as a database instance, a storage account, a service bus namespace or a key vault. The two lists drift, and nothing in either system knows whether the Azure resource still matches what the application expects.

ASO removes the second system by making the Azure resource a Kubernetes object. The repository consists of two things. There are the Custom Resource Definitions for each of the Azure services a Kubernetes user can provision, and there is the Kubernetes controller that manages the Azure resources represented by the user specified Custom Resources. The controller attempts to synchronize the desired state in the Custom Resource with the actual state of that resource in Azure, creating it if it does not exist, updating it if it has changed, or deleting it.

That last sentence is the whole mechanism. It is the standard Kubernetes reconcile loop, applied to resources that live in a cloud API rather than in the cluster.

Two independent operators, one of them deprecated

There are two major versions of Azure Service Operator, and the README is unusually clear about which to use.

ASO v2 is listed as Stable and under active development, with installation options through a Helm chart, GitHub release 2.x, and the installation section of the documentation site. ASO v1 is listed as Deprecated with its development status Halted, installable from a Helm chart, OperatorHub, or a GitHub release 1.x.

The note under the table is the part that catches people out. ASO v1 and v2 are two totally independent operators. Each has its own unique set of CRDs and controllers. They can be deployed side by side in the same cluster.

That has a practical consequence for an upgrade. You cannot upgrade v1 in place, because there is nothing to upgrade into: the two versions do not share CRDs, and a resource created under a v1 CRD is not read by a v2 controller. The path is a migration, and the README points at a migration guide for moving from ASO v1 to ASO v2, which is a data problem rather than a code problem because the resources being described have to be adopted rather than simply re-applied.

The deprecation statement is blunt. ASO v1 is no longer being maintained, which means no bug fixes and no security updates. A cluster still running v1 is running an operator that will not be patched.

CRDs generated from the Azure OpenAPI specifications

The main architectural difference between v2 and v1 is stated in the README as code-generated CRDs based on Azure OpenAPI specifications, which the project says enables them to quickly add new resources as they are requested.

This is the mechanism that keeps coverage current. Azure publishes the specifications that describe its REST APIs, and those specifications are the input to a generator that emits the Kubernetes CRDs from them. When Azure adds a property or a service, the specification changes and the CRD follows, rather than a maintainer hand-writing a Go type and a manifest for every field of every resource.

The other improvements listed for v2 are consequences of that change. There is a more powerful Status, so you can view the actual state of the resource in Azure through ASO v2, which the README says lets you see server-side applied defaults and more easily debug issues. There are dedicated storage versions, which the README says enable faster and less error prone support for new Azure API versions even when there were significant changes in resource shape. And there is uniformity, because code-generated resources are very uniform in shape, which matters when you are writing policies, scripts or monitoring against many resource types.

The last improvement is about state rather than shape. A clearer resource state is exposed via a Ready condition, and the README links the resource states design document for the details.

The Ready condition is the interface to watch

Since the controller's job is to reconcile a desired state against an actual state somewhere else, the question an operator always has is whether the two have converged. The Ready condition is where ASO v2 answers it.

This is a small design decision with a large effect on how the system behaves in practice. A controller that only logs does not help, and a status field that only says created or not created cannot distinguish a resource that is still provisioning from one that failed. Exposing the state as a Kubernetes condition means the same tooling works: kubectl describe shows it, a policy engine can require it, and a GitOps sync loop can wait for it.

The Status work and the Ready condition are related. The README's point about seeing server-side applied defaults through Status is the practical version of the same idea. Azure APIs fill in defaults, and if the manifest does not show them, the difference between the manifest and reality is invisible. With Status carrying the actual state as Azure reports it, that gap is closed.

The repository layout supports a project of this size. Alongside v2/ and docs there are charts/ for the Helm charts, v2/ for the current operator, ci/, hack/ and scripts/ for build automation, a Taskfile.yml and dev.sh for local development, a.devcontainer/ directory, and a set of governance and support files: CONTRIBUTING.md, CODE_OF_CONDUCT.md, SECURITY.md, SUPPORT.md, ROADMAP.md, AGENTS.md and a.agents/ directory. codecov.yml and.golangci.yml cover coverage and linting.

Installing v2 and the choice of chart

For v2, the README lists two installation routes: a Helm chart at the v2 charts path, and the GitHub release 2.x artefacts, with a pointer to the installation section of the documentation site for an example.

The v1 row lists three: a Helm chart, OperatorHub and a GitHub release 1.x. The extra v1 option is a hint about the shape of the project over time. v1 was distributed widely enough to be catalogued in OperatorHub, while v2 is documented as being installed with a chart or a release artefact, which is the more common pattern for a project that wants you to manage the version explicitly.

Choosing the chart path is the more significant decision, because a Helm chart pins a version of the operator and therefore a version of the CRD set and the Azure API specifications they were generated from. That is the point of the storage versions and the uniformity work: an operator upgrade can bring new resource shapes without breaking the resources you already declared.

The release artefact route installs a fixed version rather than tracking a chart, which suits an environment where the operator version is managed as part of the release process rather than as part of the cluster lifecycle. The repository also ships a Taskfile.yml, dev.sh and a devcontainer, which are aimed at contributors running the operator locally against a development cluster rather than at end users installing it.

MIT terms and the cost of the v1 to v2 move

The licence field on the repository says MIT, with the LICENSE file at the top of the tree. For a controller that runs inside a cluster, the permissive terms mean no obligation on the surrounding product beyond keeping the notice with redistributed copies.

On maintenance, the facts are clear and current. The repository is not archived, the last push was on 2026-10-20, and the release list shows an experimental tag from 2026-10-19 alongside v2.21.1 from 2026-09-10 and v2.21.0 from 2026-08-28. The README's own table describes v2 as under active development and v1 as halted.

The upgrade cost falls into two categories, and they are not equal. Moving from v1 to v2 is expensive in engineering time rather than in code, because the resources you already have in Azure have to be adopted by the new operator rather than created by it, and the CRDs are different objects. Moving between v2 point releases is comparatively routine, since the operator and its CRDs are versioned together and the storage versions exist precisely to absorb changes in resource shape.

The other cost is coverage. ASO can only manage what appears in the Azure API specifications the CRDs are generated from. A service that has not published an OpenAPI specification, or a resource shape that is not expressible in the generated CRD, is simply not available, and there is no hand-written extension path in the v2 design. That is the trade you accept for the speed of adding new resources, and it is the first thing to check before you commit a whole platform to this model.

Editorial conclusion

azure-service-operator suits a team that already runs Kubernetes and wants its Azure dependencies to be declared and reconciled in the same manifests as the workloads that use them, rather than provisioned separately through the Azure CLI or Terraform. It does not suit a team on ASO v1, which the README states is no longer maintained with no bug fixes and no security updates, and it does not suit anyone who needs a resource that has not been added to the Azure API specifications the CRDs are generated from. Before adopting v2, read the ASOv1 to ASOv2 migration guide if you are upgrading, check the resource states documentation for the Ready condition semantics, and confirm that the Azure resources you need exist as CRDs in the v2 charts before you commit to the model.

Frequently asked questions

What does Azure Service Operator do?

ASO helps you provision Azure resources and connect your applications to them from within Kubernetes. It consists of the Custom Resource Definitions for the Azure services a user can provision, and a controller that synchronises the desired state in each Custom Resource with the actual state of that resource in Azure.

Should I use ASO v1 or v2?

Use v2. The README lists v2 as stable and under active development, and states that ASO v1 is deprecated and no longer maintained, which means no bug fixes and no security updates. The two are totally independent operators with separate CRDs and controllers, so a v1 to v2 move is a migration rather than an upgrade.

How are the ASO CRDs produced?

They are code-generated from the Azure OpenAPI specifications, which the README says enables new resources to be added quickly as they are requested. The same generation gives v2 resources a uniform shape and makes it easier to support new Azure API versions.

How do I install Azure Service Operator v2?

The README lists a Helm chart under the v2 charts path and the GitHub release 2.x artefacts, and points to the installation section of the documentation site for an example. For v1 there is also an OperatorHub listing.

How do I check whether an Azure resource has converged with ASO?

The state of a resource is exposed through a Ready condition, and the Status of the resource shows the actual state in Azure, including server-side applied defaults, which the README says makes debugging easier.

Official sources

  1. Azure/azure-service-operator on GitHub
  2. License: MIT
  3. Project website
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/azure-azure-service-operator.svg)](https://hysenlabs.com/projects/azure-azure-service-operator)

Star history chart for your README

markdown
[![Star history](https://hysenlabs.com/chart/azure-azure-service-operator.svg)](https://hysenlabs.com/projects/azure-azure-service-operator)

Was this useful?