Programmatically create Azure Enterprise Agreement subscriptions with the latest APIs

This article helps you programmatically create Azure Enterprise Agreement (EA) subscriptions for an EA billing account using the most recent API versions. If you are still using the older preview version, see Programmatically create Azure subscriptions legacy APIs.

In this article, you learn how to create subscriptions programmatically using Azure Resource Manager.

When you create an Azure subscription programmatically, that subscription is governed by the agreement under which you obtained Azure services from Microsoft or an authorized reseller. For more information, see Microsoft Azure Legal Information.

Note

We recommend that you use the Azure Az PowerShell module to interact with Azure. See Install Azure PowerShell to get started. To learn how to migrate to the Az PowerShell module, see Migrate Azure PowerShell from AzureRM to Az.

You can't create support plans programmatically. You can buy a new support plan or upgrade one in the Azure portal. Navigate to Help + support and then at the top of the page, select Choose the right support plan.

Prerequisites

A user must either have the Enterprise Administrator role or the Owner role on an Enrollment Account to create a subscription. There are two ways to get the Owner role on an Enrollment Account:

  • The Enterprise Administrator of your enrollment can make you an Account Owner (sign in required) which makes you an Owner of the Enrollment Account.
  • An existing Owner of the Enrollment Account can grant you access.

To use a service principal to create an EA subscription, an Owner of the Enrollment Account must grant that service principal the ability to create subscriptions.

When using a service principal to create subscriptions, use the ObjectId of the Microsoft Entra Enterprise application as the Service Principal ID using Microsoft Graph PowerShell or Azure CLI. You can also use the steps at Find your service principal and tenant IDs to find the object ID in the Azure portal for an existing service principal.

For more information about the EA role assignment API request, see Assign roles to Azure Enterprise Agreement service principal names. The article includes a list of roles (and role definition IDs) that can be assigned to a service principal.

Note

  • Ensure that you use the correct API version to give the enrollment account owner permissions. For this article and for the APIs documented in it, use the 2019-10-01-preview API.
  • If you're migrating to use the newer APIs, your previous configuration made with the 2015-07-01 version doesn't automatically convert for use with the newer APIs.
  • The Enrollment Account information is only visible when the user's role is Account Owner. When a user has multiple roles, the API uses the user's least restrictive role.

Find accounts you have access to

After you're added to an Enrollment Account associated to an Account Owner, Azure uses the account-to-enrollment relationship to determine where to bill the subscription charges. All subscriptions created under the account are billed to the EA enrollment that the account is in. To create subscriptions, you must pass in values about the enrollment account and the user principals to own the subscription.

To run the following commands, you must be logged in to the Account Owner's home directory, which is the directory that subscriptions are created in by default.

Request to list all enrollment accounts you have access to:

GET https://management.azure.com/providers/Microsoft.Billing/billingaccounts/?api-version=2020-05-01

The API response lists all enrollment accounts you have access to:

{
  "value": [
    {
      "id": "/providers/Microsoft.Billing/billingAccounts/1234567",
      "name": "1234567",
      "properties": {
        "accountStatus": "Unknown",
        "accountType": "Enterprise",
        "agreementType": "EnterpriseAgreement",
        "soldTo": {
          "companyName": "Contoso",
          "country": "US "
        },
        "billingProfiles": {
          "hasMoreResults": false
        },
        "displayName": "Contoso",
        "enrollmentAccounts": [
          {
            "id": "/providers/Microsoft.Billing/billingAccounts/1234567/enrollmentAccounts/7654321",
            "name": "7654321",
            "type": "Microsoft.Billing/enrollmentAccounts",
            "properties": {
              "accountName": "Contoso",
              "accountOwnerEmail": "kenny@contoso.onmicrosoft.com",
              "costCenter": "Test",
              "isDevTest": false
            }
          }
        ],
        "hasReadAccess": false
      },
      "type": "Microsoft.Billing/billingAccounts"
    }
  ]
}

The values for a billing scope and id are the same thing. The id for your enrollment account is the billing scope under which the subscription request is initiated. It's important to know the ID because it's a required parameter that you use later in the article to create a subscription.

Create subscriptions under a specific enrollment account

The following example creates a subscription named Dev Team Subscription in the enrollment account selected in the previous step.

Using one of the following methods, you'll create a subscription alias name. We recommend that when you create the alias name, you:

  • Use alphanumeric characters and hyphens
  • Start with a letter and end with an alphanumeric character
  • Don't use periods

An alias is used for simple substitution of a user-defined string instead of the subscription GUID. In other words, you can use it as a shortcut. You can learn more about alias at Alias - Create. In the following examples, sampleAlias is created but you can use any string you like.

If you have multiple user roles in addition to the Account Owner role, then you must retrieve the account ID from the Azure portal. Then you can use the ID to programmatically create subscriptions.

Call the PUT API to create a subscription creation request/alias.

PUT  https://management.azure.com/providers/Microsoft.Subscription/aliases/sampleAlias?api-version=2021-10-01

In the request body, provide as the billingScope the id from one of your enrollmentAccounts.

{
  "properties": {
        "billingScope": "/providers/Microsoft.Billing/BillingAccounts/1234567/enrollmentAccounts/7654321",
        "DisplayName": "Dev Team Subscription", //Subscription Display Name
        "Workload": "Production"
  }
}

Allowed values for Workload are Production and DevTest.

Response

{
  "id": "/providers/Microsoft.Subscription/aliases/sampleAlias",
  "name": "sampleAlias",
  "type": "Microsoft.Subscription/aliases",
  "properties": {
    "subscriptionId": "b5bab918-e8a9-4c34-a2e2-ebc1b75b9d74",
    "provisioningState": "Accepted"
  }
}

You can do a GET on the same URL to get the status of the request.

Request

GET https://management.azure.com/providers/Microsoft.Subscription/aliases/sampleAlias?api-version=2021-10-01

Response

{
  "id": "/providers/Microsoft.Subscription/aliases/sampleAlias",
  "name": "sampleAlias",
  "type": "Microsoft.Subscription/aliases",
  "properties": {
    "subscriptionId": "b5bab918-e8a9-4c34-a2e2-ebc1b75b9d74",
    "provisioningState": "Succeeded"
  }
}

An in-progress status is returned as an Accepted state under provisioningState.

Create subscriptions in a different enrollment

Using the subscription Alias REST API, you can use the subscriptionTenantId parameter in the request body. Your service principal must get the token from the home tenant to create the subscription. After you create the service principal, you get the token from subscriptionTenantId and accept the transfer using the Accept Ownership API.

For more information about creating EA subscriptions in another tenant, see Create subscription in other tenant and view transfer requests.

Use ARM template or Bicep

The previous section showed how to create a subscription with PowerShell, CLI, or REST API. If you need to automate creating subscriptions, consider using an Azure Resource Manager template (ARM template) or Bicep file.

The following ARM template creates a subscription. For billingScope, provide the enrollment account ID. The subscription is created in the root management group. After creating the subscription, you can move it to another management group.

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "subscriptionAliasName": {
            "type": "string",
            "metadata": {
                "description": "Provide a name for the alias. This name will also be the display name of the subscription."
            }
        },
        "billingScope": {
            "type": "string",
            "metadata": {
                "description": "Provide the full resource ID of billing scope to use for subscription creation."
            }
        }
    },
    "resources": [
        {
            "scope": "/",
            "name": "[parameters('subscriptionAliasName')]",
            "type": "Microsoft.Subscription/aliases",
            "apiVersion": "2021-10-01",
            "properties": {
                "workLoad": "Production",
                "displayName": "[parameters('subscriptionAliasName')]",
                "billingScope": "[parameters('billingScope')]"
            }
        }
    ],
    "outputs": {}
}

Or, use a Bicep file to create the subscription.

targetScope = 'managementGroup'

@description('Provide a name for the alias. This name will also be the display name of the subscription.')
param subscriptionAliasName string

@description('Provide the full resource ID of billing scope to use for subscription creation.')
param billingScope string

resource subscriptionAlias 'Microsoft.Subscription/aliases@2021-10-01' = {
  scope: tenant()
  name: subscriptionAliasName
  properties: {
    workload: 'Production'
    displayName: subscriptionAliasName
    billingScope: billingScope
  }
}

Deploy the template at the management group level. The following examples show deploying the JSON ARM template, but you can deploy a Bicep file instead.

PUT https://management.azure.com/providers/Microsoft.Management/managementGroups/mg1/providers/Microsoft.Resources/deployments/exampledeployment?api-version=2020-06-01

With a request body:

{
  "location": "eastus",
  "properties": {
    "templateLink": {
      "uri": "http://mystorageaccount.blob.core.windows.net/templates/template.json"
    },
    "parameters": {
      "subscriptionAliasName": {
        "value": "sampleAlias"
      },
      "billingScope": {
        "value": "/providers/Microsoft.Billing/BillingAccounts/1234567/enrollmentAccounts/7654321"
      }
    },
    "mode": "Incremental"
  }
}

To move a subscription to a new management group, use the following ARM template.

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "targetMgId": {
            "type": "string",
            "metadata": {
                "description": "Provide the ID of the management group that you want to move the subscription to."
            }
        },
        "subscriptionId": {
            "type": "string",
            "metadata": {
                "description": "Provide the ID of the existing subscription to move."
            }
        }
    },
    "resources": [
        {
            "scope": "/",
            "type": "Microsoft.Management/managementGroups/subscriptions",
            "apiVersion": "2020-05-01",
            "name": "[concat(parameters('targetMgId'), '/', parameters('subscriptionId'))]",
            "properties": {
            }
        }
    ],
    "outputs": {}
}

Or, the following Bicep file.

targetScope = 'managementGroup'

@description('Provide the ID of the management group that you want to move the subscription to.')
param targetMgId string

@description('Provide the ID of the existing subscription to move.')
param subscriptionId string

resource subToMG 'Microsoft.Management/managementGroups/subscriptions@2020-05-01' = {
  scope: tenant()
  name: '${targetMgId}/${subscriptionId}'
}

Limitations of Azure Enterprise subscription creation API

  • Only Azure Enterprise subscriptions are created using the API.
  • There's a limit of 5000 subscriptions per enrollment account. After that, more subscriptions for the account can only be created in the Azure portal. To create more subscriptions through the API, create another enrollment account. Canceled, deleted, and transferred subscriptions count toward the 5000 limit.
  • Users who aren't Account Owners, but were added to an enrollment account via Azure RBAC, can't create subscriptions in the Azure portal.

Next steps