Azure Bicep: How to Provision an API Management

Somebody who likes to code
Search for a command to run...

Somebody who likes to code
No comments yet. Be the first to comment.
Google processes tens of thousands of code changes every day across a codebase of hundreds of millions of lines. The secret isn't magic tooling — it's a documented, principled approach to code review

Amazon Simple Notification Service (SNS) looks straightforward on the surface — publish a message, deliver it to subscribers — but the gap between a topic that "works in dev" and one that is productio

Amazon Simple Queue Service (SQS) is deceptively simple to get started with, but surprisingly easy to misconfigure in ways that cause silent message loss, runaway costs, duplicate processing storms, o

HTTP API is the right default choice for the majority of .NET serverless workloads. At 70% less cost than REST API, lower latency, and native JWT authorization, it covers most production requirements

AWS Lambda has become a cornerstone of modern serverless architectures, but writing a function that "just works" is very different from writing one that is performant, cost-effective, secure, and read

Azure API Management is a fully managed service that helps organizations publish, secure, transform, maintain, and monitor APIs. It provides a scalable and secure environment for API hosting, allowing developers to create, manage, and analyze APIs in a streamlined manner. While there are many benefits to using a tool like this, there are some challenges, such as keeping all our environments in sync, particularly if we are managing this task manually. To address this particular issue, we can use Azure Bicep for provisioning API management and maintaining consistency across our environments.
Ensure you have an Azure Account
Install Azure CLI
Install Bicep CLI (az bicep install)
Before diving into the details, let's clarify some key concepts:
Operation: An action performed on a resource.
API: Represents a set of operations.
Product: A collection of one or more APIs.
Subscription: Permissions to access a product or API.
Policies: Collection of statements executed sequentially on the request or response to change the behavior of an API.
Create a main.bicep file containing the following content:
param apiManagementName string
param location string = resourceGroup().location
resource apiManagementInstance 'Microsoft.ApiManagement/service@2020-12-01' = {
name: apiManagementName
location: location
sku:{
capacity: 0
name: 'Consumption'
}
properties:{
virtualNetworkType: 'None'
publisherEmail: 'raulnq@gmail.com'
publisherName: 'MyCompany'
}
}
resource apiManagementInstancePolicy 'Microsoft.ApiManagement/service/policies@2020-12-01' = {
name: 'policy'
parent: apiManagementInstance
properties: {
value: '<policies><inbound></inbound><backend><forward-request/></backend><outbound></outbound></policies>'
format: 'xml'
}
}
We are creating an API Management instance with a Consumption SKU and its corresponding policy.
Add the following content to the main.bicep file to create one of the many APIs we can define. In this case, we are using https://restcountries.com/ API:
resource apiManagementApi 'Microsoft.ApiManagement/service/apis@2023-03-01-preview' = {
parent: apiManagementInstance
name: 'countries-api'
properties: {
apiRevision: '1'
displayName: 'Contries API'
description: 'Contries API'
subscriptionRequired: true
serviceUrl: 'https://restcountries.com/'
subscriptionKeyParameterNames: {
header: 'Ocp-Apim-Subscription-Key'
query: 'subscription-key'
}
protocols: [
'https'
]
path: ''
}
}
resource apiManagementApiPolicy 'Microsoft.ApiManagement/service/apis/policies@2020-12-01' = {
name: 'policy'
parent: apiManagementApi
properties: {
value: '<policies> <inbound> <base /> <set-header name="X-API-KEY" exists-action="append"> <value>${thirdPartyApiKey}</value> </set-header> </inbound> <backend> <base /> </backend> <outbound> <base /> </outbound> <on-error> <base /> </on-error> </policies>'
format: 'xml'
}
}
Add the following content to the main.bicep file to add an operation that retrieves information about a country based on its name:
resource apiManagementOperationGetCountry 'Microsoft.ApiManagement/service/apis/operations@2023-03-01-preview' = {
parent: apiManagementApi
name: 'get-countries'
properties: {
displayName: '/v3.1/name/{name} - GET'
method: 'GET'
urlTemplate: '/v3.1/name/{name}'
templateParameters: [
{
name: 'name'
type: 'string'
required: true
}
]
request: {
queryParameters: [
{
name: 'fullText'
type: 'boolean'
}
]
}
responses:[
{
statusCode: 200
description: 'Success'
representations:[
{
contentType:'application/json'
}
]
}
]
}
}
resource apiManagementOperationGetCountryPolicy 'Microsoft.ApiManagement/service/apis/operations/policies@2020-12-01' = {
name: 'policy'
parent: apiManagementOperationGetCountry
properties: {
value: '<policies><inbound><base/></inbound><backend><base/></backend><outbound><base/></outbound><on-error><base/></on-error></policies>'
format: 'xml'
}
}
Add the following content to the main.bicep file to define a product and the link against our API:
resource product 'Microsoft.ApiManagement/service/products@2020-12-01' = {
name: 'product'
parent: apiManagementInstance
properties: {
displayName: 'Product'
description: 'Product'
subscriptionRequired: true
approvalRequired: true
state: 'published'
subscriptionsLimit: 1
terms: 'These are the terms of use ...'
}
}
resource productPolicies 'Microsoft.ApiManagement/service/products/policies@2020-12-01' = {
name: 'policy'
parent: product
properties: {
value: '<policies><inbound><base/></inbound><backend><base/></backend><outbound><base/></outbound><on-error><base/></on-error></policies>'
format: 'xml'
}
}
resource linkApiToProduct 'Microsoft.ApiManagement/service/products/apiLinks@2023-03-01-preview' = {
name: 'link'
parent: product
properties: {
apiId: apiManagementApi.id
}
}
And finally, add a subscription to our product by including the following content in the main.bicep file:
resource developerSubscription 'Microsoft.ApiManagement/service/subscriptions@2023-03-01-preview' = {
parent: apiManagementInstance
name: 'developer'
properties: {
scope: '/products/${product.id}'
state: 'active'
displayName: 'developer'
}
}
First, create a resource group using the following command:
az group create -l eastus -n MyResourceGroup
And deploy the main.bicep file:
az deployment group create --resource-group MyResourceGroup --template-file .\main.bicep
There are several other resources to create, such as users, groups, schemas, etc. However, we believe this is a good starting point for using Azure Bicep with API Management. Thanks, and happy coding.