Search code examples
azureterraform

App Service Plan is never created in Terraform


I'm pretty new to Terraform so I'm probably doing something very stupid but please bear with me. I've got the following script, I run Terraform plan and everything is ok but when I go to apply it, it never ends because it can never finish creating the App Service Plan and then I get a 429 HTTP status code

Here's my main.tf:

terraform {
  required_providers {
    azurerm = {
      source  = "hashicorp/azurerm"
      version = "~>3.0"
    }
  }
}
provider "azurerm" {
  features {}
}

resource "azurerm_resource_group" "rg" {
  name     = "name12a6-rg1"
  location = "westeurope"
}

resource "azurerm_virtual_network" "vnet" {
  name                = "name12a6-vnet1"
  location            = azurerm_resource_group.rg.location
  resource_group_name = azurerm_resource_group.rg.name
  address_space       = ["10.0.0.0/16"]
}

resource "azurerm_subnet" "integrationsubnet" {
  name                 = "name12a6-integrationsubnet1"
  resource_group_name  = azurerm_resource_group.rg.name
  virtual_network_name = azurerm_virtual_network.vnet.name
  address_prefixes     = ["10.0.1.0/24"]
  delegation {
    name = "delegation"
    service_delegation {
      name = "Microsoft.Web/serverFarms"
    }
  }
}

resource "azurerm_subnet" "backendendpointsubnet" {
  name                                      = "name12a6-backendendpointsubnet1"
  resource_group_name                       = azurerm_resource_group.rg.name
  virtual_network_name                      = azurerm_virtual_network.vnet.name
  address_prefixes                          = ["10.0.2.0/24"]
  private_endpoint_network_policies_enabled = true
}

resource "azurerm_subnet" "databaseendpointsubnet" {
  name                                      = "name12a6-databaseendpointsubnet1"
  resource_group_name                       = azurerm_resource_group.rg.name
  virtual_network_name                      = azurerm_virtual_network.vnet.name
  address_prefixes                          = ["10.0.3.0/24"]
  private_endpoint_network_policies_enabled = true

  delegation {
    name = "dbFlexibleServer"
    service_delegation {
      name    = "Microsoft.DBforMySQL/flexibleServers"
      actions = ["Microsoft.Network/virtualNetworks/subnets/join/action"]
    }
  }
}

resource "azurerm_service_plan" "appserviceplan1" {
  name                = "name12a6-appserviceplan1"
  location            = azurerm_resource_group.rg.location
  resource_group_name = azurerm_resource_group.rg.name
  os_type             = "Linux"
  sku_name            = "B1"
}

resource "azurerm_linux_web_app" "frontwebapp" {
  name                = "frontend-name12a061"
  location            = azurerm_resource_group.rg.location
  resource_group_name = azurerm_resource_group.rg.name
  service_plan_id     = azurerm_service_plan.appserviceplan1.id

  site_config {
    vnet_route_all_enabled = true
  }
  app_settings = {
    "WEBSITE_DNS_SERVER" : "168.63.129.16"
  }
}

resource "azurerm_app_service_virtual_network_swift_connection" "vnetintegrationconnection" {
  app_service_id = azurerm_linux_web_app.frontwebapp.id
  subnet_id      = azurerm_subnet.integrationsubnet.id
}

resource "azurerm_linux_web_app" "backwebapp" {
  name                = "backend-name12a061"
  location            = azurerm_resource_group.rg.location
  resource_group_name = azurerm_resource_group.rg.name
  service_plan_id     = azurerm_service_plan.appserviceplan1.id

  site_config {}
}

resource "azurerm_private_dns_zone" "dnsprivatezone" {
  name                = "privatelink.azurewebsites.net"
  resource_group_name = azurerm_resource_group.rg.name
}

# Confirm
resource "azurerm_private_dns_a_record" "dnsrecord_frontend" {
  name                = "name12a6-dns-frontend1"
  zone_name           = azurerm_private_dns_zone.dnsprivatezone.name
  resource_group_name = azurerm_resource_group.rg.name
  ttl                 = 300
  records             = [azurerm_linux_web_app.frontwebapp.name]
}

# Confirm
resource "azurerm_private_dns_a_record" "dnsrecord_backend" {
  name                = "name12a6-dns-backend1"
  zone_name           = azurerm_private_dns_zone.dnsprivatezone.name
  resource_group_name = azurerm_resource_group.rg.name
  ttl                 = 300
  records             = [azurerm_linux_web_app.backwebapp.name]
}

resource "azurerm_private_dns_zone_virtual_network_link" "dnszonelink" {
  name                  = "name12a6dnszonelink1"
  resource_group_name   = azurerm_resource_group.rg.name
  private_dns_zone_name = azurerm_private_dns_zone.dnsprivatezone.name
  virtual_network_id    = azurerm_virtual_network.vnet.id
}

resource "azurerm_private_endpoint" "privateendpoint" {
  name                = "backwebappprivateendpoint1"
  location            = azurerm_resource_group.rg.location
  resource_group_name = azurerm_resource_group.rg.name
  subnet_id           = azurerm_subnet.backendendpointsubnet.id

  private_dns_zone_group {
    name                 = "privatednszonegroup1"
    private_dns_zone_ids = [azurerm_private_dns_zone.dnsprivatezone.id]
  }

  private_service_connection {
    name                           = "privateendpointconnection1"
    private_connection_resource_id = azurerm_linux_web_app.backwebapp.id
    subresource_names              = ["sites"]
    is_manual_connection           = false
  }
}

# For the database
# 1 - create subnet
# 2 - create private dns zone
# 3 - assign private dns to the vnet
# 4 - create private endpoint to the new vnet

resource "azurerm_private_dns_zone" "dbdnsprivatezone" {
  name                = "dbserver.mysql.database.azure.com"
  resource_group_name = azurerm_resource_group.rg.name
}

resource "azurerm_private_dns_zone_virtual_network_link" "db-dnszonelink" {
  name                  = "dbname12a6dnszonelink.com"
  resource_group_name   = azurerm_resource_group.rg.name
  private_dns_zone_name = azurerm_private_dns_zone.dbdnsprivatezone.name
  virtual_network_id    = azurerm_virtual_network.vnet.id

  depends_on = [azurerm_subnet.databaseendpointsubnet]
}

resource "azurerm_mysql_flexible_server" "serverMysql" {
  name                         = "dbservername12a61"
  location                     = azurerm_resource_group.rg.location
  resource_group_name          = azurerm_resource_group.rg.name
  administrator_login          = "admin1"
  administrator_password       = "adminAdmin1"
  backup_retention_days        = 7
  delegated_subnet_id          = azurerm_subnet.databaseendpointsubnet.id
  geo_redundant_backup_enabled = false
  private_dns_zone_id          = azurerm_private_dns_zone.dbdnsprivatezone.id
  sku_name                     = "GP_Standard_D2ds_v4"
  version                      = "8.0.21"

  high_availability {
    mode = "SameZone"
  }
  maintenance_window {
    day_of_week  = 0
    start_hour   = 8
    start_minute = 0
  }
  storage {
    iops    = 360
    size_gb = 20
  }

  depends_on = [azurerm_private_dns_zone_virtual_network_link.db-dnszonelink]
}

# resource "azurerm_mysql_flexible_database" "databaseMysql" {
#   name                = "databasedbserver"
#   resource_group_name = azurerm_resource_group.rg.name
#   server_name         = azurerm_mysql_flexible_server.serverMysql.name
#   charset             = "utf8mb4"
#   collation           = "utf8mb4_unicode_ci"
# }

# resource "azurerm_private_dns_a_record" "dnsrecord_database" {
#   name                = "database"
#   zone_name           = azurerm_private_dns_zone.dbdnsprivatezone.name
#   resource_group_name = azurerm_resource_group.rg.name
#   ttl                 = 300
#   records             = [azurerm_mysql_flexible_server.serverMysql.name] # has wrong name
# }

Here is the error I get:

 Error: creating App Service Plan (Subscription: "817c1532-85ce-4a4f-bea2-6ea18491ba01"
│ Resource Group Name: "name12a6-rg1"
│ Server Farm Name: "name12a6-appserviceplan1"): performing CreateOrUpdate: unexpected status 429 (429 Too Many Requests) with response: {"Code":"429","Message":"App Service Plan Create operation is throttled for subscription 817c1532-85ce-4a4f-bea2-6ea18491ba01. Please contact support if issue persists.","Target":null,"Details":[{"Message":"App Service Plan Create operation is throttled for subscription 817c1532-85ce-4a4f-bea2-6ea18491ba01. Please contact support if issue persists."},{"Code":"429"},{"ErrorEntity":{"ExtendedCode":"51025","MessageTemplate":"App Service Plan {0} operation is throttled for subscription {1}. Please contact support if issue persists.","Parameters":["Create","817c1532-85ce-4a4f-bea2-6ea18491ba01"],"Code":"429","Message":"App Service Plan Create operation is throttled for subscription 817c1532-85ce-4a4f-bea2-6ea18491ba01. Please contact support if issue persists."}}],"Innererror":null}   
│
│   with azurerm_service_plan.appserviceplan1,
│   on main.tf line 62, in resource "azurerm_service_plan" "appserviceplan1":
│   62: resource "azurerm_service_plan" "appserviceplan1" {
│
│ creating App Service Plan (Subscription: "817c1532-85ce-4a4f-bea2-6ea18491ba01"
│ Resource Group Name: "name12a6-rg1"
│ Server Farm Name: "name12a6-appserviceplan1"): performing CreateOrUpdate: unexpected status 429 (429 Too Many Requests) with response:
│ {"Code":"429","Message":"App Service Plan Create operation is throttled for subscription 817c1532-85ce-4a4f-bea2-6ea18491ba01. Please contact support if 
│ issue persists.","Target":null,"Details":[{"Message":"App Service Plan Create operation is throttled for subscription
│ 817c1532-85ce-4a4f-bea2-6ea18491ba01. Please contact support if issue
│ persists."},{"Code":"429"},{"ErrorEntity":{"ExtendedCode":"51025","MessageTemplate":"App Service Plan {0} operation is throttled for subscription {1}.   
│ Please contact support if issue persists.","Parameters":["Create","817c1532-85ce-4a4f-bea2-6ea18491ba01"],"Code":"429","Message":"App Service Plan       
│ Create operation is throttled for subscription 817c1532-85ce-4a4f-bea2-6ea18491ba01. Please contact support if issue persists."}}],"Innererror":null}

Solution

  • "Message":"App Service Plan Create operation is throttled for subscription xxxxx:

    The above error is transient when it comes to terraform deployments.

    Need to check below:

    • Check the subscription API quotas are sufficiently available for creating an app service plan in the corresponding subscription. Increase the quota limit if you have owner access or reach out to administrator for increasing the limit.

    • Check if there are any policies created by any user which might block creation of Azure resources like this.

    • Check all the required resource providers are registered in your environment using az provider list CLI command. If not registered, use az provider register for registration.

    • Basically, terraform creates resources simultaneously, which can accelerate deployments but also increase the rate limits.

      To avoid this, you can use the parallelism environment variable which is available in TF_variables along with the terraform apply during deployment.

    • Try simplifying the code by splitting the complete code into smaller modules to avoid conflicts.

    After all the above, I tried to deploy your code in my environment without any changes and was to deploy it successfully as shown below.

    enter image description here

    enter image description here