Azure API Management overview and key concepts | Microsoft Docs
Transcript of Azure API Management overview and key concepts | Microsoft Docs
Table of ContentsTable of Contents
Azure API Management Documentation Overview
About API Management Quickstarts
Create an instance - Portal Create an instance - PowerShell
Tutorials 1 - Import your first API 2 - Create and publish a product 3 - Mock an API responses 4 - Protect your API 5 - Monitor published APIs 6 - Debug your APIs 7 - Add revisions 8 - Add multiple versions 9 - Customize the Developer portal
Samples Policies Azure PowerShell
Concepts Terminology Policies
Overview Policy reference index
Manage using automation Error handling API import restrictions
How-to guides Define APIs
Add an API manually Import an OpenAPI Specification Import a SOAP API Import a SOAP API and convert to REST Import an API App Import a Function App Import a Logic App Import a Service Fabric app Edit an API
Provision and scale Upgrade and scale Configure a custom domain
Cache Add caching to improve performance
Secure your backend Protect your API with Azure AD Connect to a virtual network Connect to an internal virtual network Integrate Application Gateway in an internal VNET Mutual Certificate authentication
Customize the developer experience Modify page content and layout Customize system pages using templates Authentication with Azure AD Authentication with Azure AD B2C Delegated authentication E-mail notifications and templates Enable console OAuth support
Define policies Set or edit policies Policy expressions Custom caching
Advanced monitoring Advanced request throttling Using external services Manage secrets using properties Secure APIs using client certificate authentication Access restriction policies Advanced policies Authentication policies Caching policies Cross-domain policies Transformation policies
Template reference Templates APIs Products Applications Issues User profile Pages Template resources
Data model reference Page controls Manage in production
Manage groups Deploy to multiple Azure regions Log events to Azure Event Hubs Set up DR using backup/restore Manage user accounts Configure using Git Use role-based access control Use Managed Service Identity Integrate with Service Fabric
Reference Azure PowerShell REST REST (original)
Resources FAQ Regional availability API design guidance API implementation guidance MSDN forum Stack Overflow Videos Roadmap Power BI solution template for API Management Blog Feature requests
What is API Management?2/28/2018 • 6 min to read • Edit Online
Overview
API Management (APIM) helps organizations publish APIs to external, partner, and internal developers to unlockthe potential of their data and services. Businesses everywhere are looking to extend their operations as a digitalplatform, creating new channels, finding new customers and driving deeper engagement with existing ones. APIManagement provides the core competencies to ensure a successful API program through developerengagement, business insights, analytics, security, and protection. You can use Azure API Management to take anybackend and launch a full-fledged API program based on it.
This article provides an overview of common scenarios that involve APIM. It also gives a brief overview of theAPIM system's main components. The article, then, gives a more detailed overview of each component.
To use API Management, administrators create APIs. Each API consists of one or more operations, and each APIcan be added to one or more products. To use an API, developers subscribe to a product that contains that API,and then they can call the API's operation, subject to any usage policies that may be in effect. Common scenariosinclude:
Securing mobile infrastructure by gating access with API keys, preventing DOS attacks by using throttling,or using advanced security policies like JWT token validation.Enabling ISV partner ecosystems by offering fast partner onboarding through the developer portal andbuilding an API facade to decouple from internal implementations that are not ripe for partner consumption.Running an internal API program by offering a centralized location for the organization to communicateabout the availability and latest changes to APIs, gating access based on organizational accounts, all based on asecured channel between the API gateway and the backend.
The system is made up of the following components:
The API gateway is the endpoint that:
Accepts API calls and routes them to your backends.Verifies API keys, JWT tokens, certificates, and other credentials.Enforces usage quotas and rate limits.Transforms your API on the fly without code modifications.Caches backend responses where set up.Logs call metadata for analytics purposes.
The Azure portal is the administrative interface where you set up your API program. Use it to:
Define or import API schema.Package APIs into products.Set up policies like quotas or transformations on the APIs.Get insights from analytics.Manage users.
The Developer portal serves as the main web presence for developers, where they can:
Read API documentation.Try out an API via the interactive console.Create an account and subscribe to get API keys.
APIs and operations
Products
Groups
Access analytics on their own usage.
For more information, see the Cloud-based API Management: Harnessing the Power of APIs PDF whitepaper.This introductory whitepaper on API Management by CITO Research covers:
Common API requirements and challengesDecoupling APIs and presenting facadesGetting developers up and running quicklySecuring accessAnalytics and metricsGaining control and insight with an API Management platformUsing cloud vs on-premises solutionsAzure API Management
APIs are the foundation of an API Management service instance. Each API represents a set of operations availableto developers. Each API contains a reference to the back-end service that implements the API, and its operationsmap to the operations implemented by the back-end service. Operations in API Management are highlyconfigurable, with control over URL mapping, query and path parameters, request and response content, andoperation response caching. Rate limit, quotas, and IP restriction policies can also be implemented at the API orindividual operation level.
For more information, see How to create APIs and How to add operations to an API.
Products are how APIs are surfaced to developers. Products in API Management have one or more APIs, and areconfigured with a title, description, and terms of use. Products can be Open or Protected. Protected productsmust be subscribed to before they can be used, while open products can be used without a subscription. When aproduct is ready for use by developers, it can be published. Once it is published, it can be viewed (and in the caseof protected products subscribed to) by developers. Subscription approval is configured at the product level andcan either require administrator approval, or be auto-approved.
Groups are used to manage the visibility of products to developers. Products grant visibility to groups, anddevelopers can view and subscribe to the products that are visible to the groups in which they belong.
Groups are used to manage the visibility of products to developers. API Management has the followingimmutable system groups:
Administrators - Azure subscription administrators are members of this group. Administrators manage APIManagement service instances, creating the APIs, operations, and products that are used by developers.Developers - Authenticated developer portal users fall into this group. Developers are the customers thatbuild applications using your APIs. Developers are granted access to the developer portal and buildapplications that call the operations of an API.Guests - Unauthenticated developer portal users, such as prospective customers visiting the developer portalof an API Management instance fall into this group. They can be granted certain read-only access, such as theability to view APIs but not call them.
In addition to these system groups, administrators can create custom groups or leverage external groups inassociated Azure Active Directory tenants. Custom and external groups can be used alongside system groups ingiving developers visibility and access to API products. For example, you could create one custom group for
Developers
Policies
Developer portal
API Management and the API economy
Next steps
developers affiliated with a specific partner organization and allow them access to the APIs from a productcontaining relevant APIs only. A user can be a member of more than one group.
For more information, see How to create and use groups.
Developers represent the user accounts in an API Management service instance. Developers can be created orinvited to join by administrators, or they can sign up from the Developer portal. Each developer is a member ofone or more groups, and can be subscribe to the products that grant visibility to those groups.
When developers subscribe to a product, they are granted the primary and secondary key for the product. Thiskey is used when making calls into the product's APIs.
For more information, see How to create or invite developers and How to associate groups with developers.
Policies are a powerful capability of API Management that allow the Azure portal to change the behavior of theAPI through configuration. Policies are a collection of statements that are executed sequentially on the request orresponse of an API. Popular statements include format conversion from XML to JSON and call rate limiting torestrict the number of incoming calls from a developer, and many other policies are available.
Policy expressions can be used as attribute values or text values in any of the API Management policies, unless thepolicy specifies otherwise. Some policies such as the Control flow and Set variable policies are based on policyexpressions. For more information, see Advanced policies and Policy expressions.
For a complete list of API Management policies, see Policy reference. For more information on using andconfiguring policies, see API Management policies. For a tutorial on creating a product with rate limit and quotapolicies, see How create and configure advanced product settings.
The developer portal is where developers can learn about your APIs, view and call operations, and subscribe toproducts. Prospective customers can visit the developer portal, view APIs and operations, and sign up. The URLfor your developer portal is located on the dashboard in the Azure portal for your API Management serviceinstance.
You can customize the look and feel of your developer portal by adding custom content, customizing styles, andadding your branding.
To learn more about API Management, watch the following presentation from the Microsoft Ignite 2017conference.
Complete the following quickstart and start using Azure API Management:
Create an Azure API Management instance
Create a new Azure API Management serviceinstance2/16/2018 • 2 min to read • Edit Online
Log in to Azure
Create a new service
Azure API Management (APIM) helps organizations publish APIs to external, partner, and internal developersto unlock the potential of their data and services. API Management provides the core competencies to ensurea successful API program through developer engagement, business insights, analytics, security, andprotection. APIM enables you to create and manage modern API gateways for existing backend serviceshosted anywhere. For more information, see the Overview topic.
This quickstart describes the steps for creating a new API Management instance using the Azure portal.
If you don't have an Azure subscription, create a free account before you begin.
Log in to the Azure portal at http://portal.azure.com.
1. In the Azure portal, select Create a resource > Enterprise Integration > API management.
Alternatively, choose New, type API management in the search box, and press Enter. Click Create.
2. In the API Management service window, enter settings.
SETTING SUGGESTED VALUE DESCRIPTION
Name A unique name for your APIManagement service
The name can't be changed later.Service name is used to generate adefault domain name in the form of{name}.azure-api.net. If you wouldlike to use a custom domain name,see Configure a custom domain. Service name is used to refer to theservice and the correspondingAzure resource.
Subscription Your subscription The subscription under which thisnew service instance will be created.You can select the subscriptionamong the different Azuresubscriptions that you have accessto.
Resource Group apimResourceGroup You can select a new or existingresource. A resource group is acollection of resources that sharelifecycle, permissions, and policies.Learn more here.
Navigate to your APIM instance
Location West USA Select the geographic region nearyou. Only the available APIManagement service regionsappear in the drop-down list box.
Organization name The name of your organization This name is used in a number ofplaces, including the title of thedeveloper portal and sender ofnotification emails.
Administrator email [email protected] Set email address to which all thenotifications from APIManagement will be sent.
Pricing tier Developer Set Developer tier to evaluate theservice. This tier is not forproduction use. For moreinformation about scaling the APIManagement tiers, see upgradeand scale.
SETTING SUGGESTED VALUE DESCRIPTION
TIPTIP
3. Choose Create.
It usually takes between 20 and 30 minutes to create an API Management service. Selecting Pin to dashboardmakes finding a newly created service easier.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
TIPTIP
Clean up resources
Next steps
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
When no longer needed, you can remove the resource group and all related resources by following thesesteps:
1. In the Azure portal, select .2. Select Resource groups.3. Find your resource group.4. Click ". . ." and delete your group.
Import and publish your first API
Create a new Azure API Management serviceinstance12/4/2017 • 1 min to read • Edit Online
Log in to Azure
Launch Azure Cloud Shell
Click Try It in the upper right corner of a code block.
Open Cloud Shell in your browser.
Click the Cloud Shell button on the menu in the upper rightof the Azure portal.
Create resource group
New-AzureRmResourceGroup -Name myResourceGroup -Location WestUS
Azure API Management (APIM) helps organizations publish APIs to external, partner, and internal developers tounlock the potential of their data and services. API Management provides the core competencies to ensure asuccessful API program through developer engagement, business insights, analytics, security, and protection. APIMenables you to create and manage modern API gateways for existing backend services hosted anywhere. For moreinformation, see the Overview topic.
This quickstart describes the steps for creating a new API Management instance using the PowerShell scripts. Thequickstart shows you how to use the Azure Cloud Shell that you can run from Azure portal.
If you don't have an Azure subscription, create a free account before you begin.
Log in to the Azure portal at http://portal.azure.com.
The Azure Cloud Shell is a free interactive shell that you can use to run the steps in this article. It has commonAzure tools preinstalled and configured to use with your account. Just click the Copy to copy the code, paste it intothe Cloud Shell, and then press enter to run it. There are a few ways to launch the Cloud Shell:
If you choose to install and use the PowerShell locally, this tutorial requires the Azure PowerShell module version3.6 or later. Run Get-Module -ListAvailable AzureRM to find the version. If you need to upgrade, see Install AzurePowerShell module. If you are running PowerShell locally, you also need to run Login-AzureRmAccount to create aconnection with Azure.
Create an Azure resource group with New-AzureRmResourceGroup. A resource group is a logical container intowhich Azure resources are deployed and managed.
Create an API Management service
New-AzureRmApiManagement -ResourceGroupName "myResourceGroup" -Location "West US" -Name "apim-name" -Organization "myOrganization" -AdminEmail "myEmail" -Sku "Developer"
Clean up resources
Remove-AzureRmResourceGroup -Name myResourceGroup
Next steps
This is long running operation and could take up to 15 minutes.
When no longer needed, you can use the Remove-AzureRmResourceGroup command to remove the resourcegroup and all related resources.
Import and publish your first API
Import and publish your first API3/20/2018 • 4 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
This tutorial shows how to import an "OpenAPI specification" backend API residing athttp://conferenceapi.azurewebsites.net?format=json. This backend API is provided by Microsoft and hosted onAzure.
Once the backend API is imported into API Management (APIM), the APIM API becomes a facade for thebackend API. At the time you import the backend API, both the source API and the APIM API are identical.APIM enables you to customize the facade according to your needs without touching the backend API. For moreinformation, see Transform and protect your API.
In this tutorial, you learn how to:
Import your first APITest the API in the Azure portalTest the API in the Developer portal
Complete the following quickstart: Create an Azure API Management instance.
TIPTIP
Import and publish a backend API
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
This section shows how to import and publish an OpenAPI specification backend API.
1. Select APIs from under API MANAGEMENT.2. Select OpenAPI specification from the list.
SETTING VALUE DESCRIPTION
OpenAPI Specification http://conferenceapi.azurewebsites.net?format=json
References the service implementingthe API. API management forwardsrequests to this address.
Display name Demo Conference API If you press tab after entering theservice URL, APIM will fill out thisfield based on what is in the json. This name is displayed in theDeveloper portal.
Name demo-conference-api Provides a unique name for the API. If you press tab after entering theservice URL, APIM will fill out thisfield based on what is in the json.
Description Provide an optional description ofthe API.
If you press tab after entering theservice URL, APIM will fill out thisfield based on what is in the json.
URL scheme HTTPS Determines which protocols can beused to access the API.
API URL suffix conference The suffix is appended to the baseURL for the API managementservice. API Managementdistinguishes APIs by their suffix andtherefore the suffix must be uniquefor every API for a given publisher.
Products Unlimited Products are associations of one ormore APIs. You can include anumber of APIs into a Product andoffer them to developers throughthe developer portal. You publish the API by associatingthe API with a product (in thisexample, Unlimited). To add this newAPI to a product, type the productname (you can also do it later fromthe Settings page). This step can berepeated multiple times to add theAPI to multiple products.To get access to the API, developersmust first subscribe to a product.When they subscribe, they get asubscription key that is good for anyAPI in that product. If you created the APIM instance,you are an administrator already, soyou are subscribed to every product.By default, each API Managementinstance comes with two sampleproducts: Starter and Unlimited.
You can set the API values during creation or later by going to the Settings tab. The red star next to afield indicates that the field is required.
Test the new APIM API in the Azure portal
Call an operation from the developer portal
Version this API? For more information aboutversioning, see Publish multipleversions of your API
SETTING VALUE DESCRIPTION
NOTENOTETo publish the API, you must associate it with a porduct. You can do it from the Settings page.
3. Select Create.
Operations can be called directly from the Azure portal, which provides a convenient way to view and test theoperations of an API.
1. Select the API you created in the previous step (from the APIs tab).2. Press the Test tab.
3. Click on GetSpeakers. The page displays fields for query parameters but in this case we don't have any. Thepage also displays fields for the headers. One of the headers is "Ocp-Apim-Subscription-Key", for thesubscription key of the product that is associated with this API. The key is filled in automatically.
4. Press Send.
Backend responds with 200 OK and some data.
Operations can also be called from the Developer portal to test APIs.
1. Select Demo Conference API.2. Click GetSpeakers.
The page displays fields for query parameters but in this case we don't have any. The page also displaysfields for the headers. One of the headers is "Ocp-Apim-Subscription-Key", for the subscription key of theproduct that is associated with this API. If you created the APIM instance, you are an administratoralready, so the key is filled in automatically.
Next steps
3. Press Try it.4. Press Send.
After an operation is invoked, the developer portal shows the responses.
In this tutorial, you learned how to:
Import your first APITest the API in the Azure portalTest the API in the Developer portal
Advance to the next tutorial:
Create and publish a product
Create and publish a product2/28/2018 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
In Azure API Management, a product contains one or more APIs as well as a usage quota and the terms of use.Once a product is published, developers can subscribe to the product and begin to use the product's APIs.
In this tutorial, you learn how to:
Create and publish a productAdd an API to the product
Complete the following quickstart: Create an Azure API Management instance.Also, complete the following tutorial: Import and publish your first API.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
TIPTIP
Create and publish a product
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Click on Products in the menu on the left to display the Products page.
NAME DESCRIPTION
Display name The name as you want it to be shown in the Developerportal.
Name A descriptive name of the product.
2. Click + Product.
When you add a product, you need to supply the following information:
Add more configurationsAdd more configurations
Add APIs to a product
Add an API to an existing productAdd an API to an existing product
Next steps
Description The Description field allows you to provide detailedinformation about the product such as its purpose, theAPIs it provides access to, and other useful information.
State Press Published if you want to publish the product.Before the APIs in a product can be called, the productmust be published. By default new products areunpublished, and are visible only to the Administratorsgroup.
Requires approval Check Require subscription approval if you want anadministrator to review and accept or reject subscriptionattempts to this product. If the box is unchecked,subscription attempts are auto-approved.
Subscription count limit To limit the count of multiple simultaneous subscriptions,enter the subscription limit.
Legal terms You can include the terms of use for the product whichsubscribers must accept in order to use the product.
APIs Products are associations of one or more APIs. You caninclude a number of APIs and offer them to developersthrough the developer portal. You can add an existing API during the product creation.You can add an API to the product later, either from theProducts Settings page or while creating an API.
NAME DESCRIPTION
3. Click Create to create the new product.
You can continue configuring the product after saving it by choosing the Settings tab.
View/add subscribers to the product from the Subscriptions tab.
Set a visibility of a product for developers or guest from the Access control tab.
Products are associations of one or more APIs. You can include a number of APIs and offer them to developersthrough the developer portal. You can add an existing API during the product creation. You can add an API to theproduct later, either from the Products Settings page or while creating an API.
Developers must first subscribe to a product to get access to the API. When they subscribe, they get a subscriptionkey that is good for any API in that product. If you created the APIM instance, you are an administrator already, soyou are subscribed to every product by default.
1. Select a product.2. Select the APIs tab.3. Click +API.4. Choose an API and click Create.
In this tutorial, you learned how to:
Create and publish a productAdd an API to the product
Advance to the next tutorial:
Create blank API and mock API responses
Mock API responses12/4/2017 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
Backend APIs can be imported into an APIM API or created and managed manually. The steps in this tutorialshow you how to use APIM to create a blank API and manage it manually. The tutorial shows how to set a policyon an API so it returns a mocked response. This method enables developers to proceed with implementation andtesting of the APIM instance even if the backend is not available to send real responses. Ability to mock upresponses can be useful in a number of scenarios:
When the API façade is designed first and the backend implementation comes later. Or, the backend is beingdeveloped in parallel.When the backend is temporarily not operational or not able to scale.
In this tutorial, you learn how to:
Create a test APIAdd an operation to the test APIEnable response mockingTest the mocked API
Complete the following quickstart: Create an Azure API Management instance.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.
TIPTIP
Create a test API
Add an operation to the test API
3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
The steps in this section show how to create a blank API with no backend. It also shows how to add an operationto the API. Calling the operation after completing steps in this section produces an error. You will get no errorsafter you complete steps in the "Enable response mocking" section.
1. Select APIs from under API MANAGEMENT.2. From the left menu, select + Add API.3. Select Blank API from the list.4. Enter "Test API" for Display name.5. Enter "Unlimited" for Products.6. Select Create.
1. Select the API you created in the previous step.2. Click + Add Operation.
SETTING VALUE DESCRIPTION
URL (HTTP verb) GET You can choose from one of thepredefined HTTP verbs.
URL /test A URL path for the API.
Display name Test call The name that is displayed in theDeveloper portal.
Description Provide a description of theoperation that is used to providedocumentation to the developersusing this API in the Developerportal.
Query tab You can add query parameters.Besides providing a name anddescription, you can provide valuesthat can be assigned to thisparameter. One of the values can bemarked as default (optional).
Request tab You can define request content types,examples, and schemas.
Response tab See steps that follow this table. Define response status codes,content types, examples, andschemas.
3. Select the Response tab, located under the URL, Display name, and Description fields.
Enable response mocking
Test the mocked API
Video
Next steps
4. Click + Add response.5. Select 200 OK from the list.6. Under the Representations heading on the right, select + Add representation.7. Enter "application/json" into the search box and select the application/json content type.8. In the Sample text box, enter "{ 'sampleField' : 'test' }".9. Select Save.
1. Select the API you created in the "Create a test API" step.2. Select the test operation that you added.3. In the window on the right, click the Design tab.4. In the Inbound processing window, click the pencil icon.5. In the Mocking tab, select Static responses for Mocking behavior.6. In the API Management returns the following response: text box, type 200 OK, application/json. This
selection indicates that your API should return the response sample you defined in the previous section.7. Select Save.
1. Select the API you created in the "Create a test API" step.2. Open the Test tab.
TIPTIP
5. The HTTP response displays the JSON provided as a sample in the first section of the tutorial.
3. Ensure the Test call API is selected.
A yellow bar with the text Mocking is enabled indicates that responses returned from the API Management, sendsa mocking policy and not an actual backend response.
4. Select Send to make a test call.
In this tutorial, you learned how to:
Create a test APIAdd an operation to the test APIEnable response mockingTest the mocked API
Advance to the next tutorial:
Transform and protect a published API
Transform and protect your API3/20/2018 • 5 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
The tutorial shows how to transform your API so it does not reveal a private backend info. For example, youmight want to hide the info about technology stack that is running on the backend. You might also want to hideoriginal URLs that appear in the body of API's HTTP response and instead redirect them to the APIM gateway.
This tutorial also shows you how easy it is to add protection for your backend API by configuring rate limit withAzure API Management. For example, you may want to limit a number of calls the API is called so it is notoverused by developers. For more information, see API Management policies
In this tutorial, you learn how to:
Transform an API to strip response headersReplace original URLs in the body of the API response with APIM gateway URLsProtect an API by adding rate limit policy (throttling)Test the transformations
Complete the following quickstart: Create an Azure API Management instance.Also, complete the following tutorial: Import and publish your first API.
To navigate to your APIM instance, follow these steps:
TIPTIP
Transform an API to strip response headers
Test the original responseTest the original response
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
This section shows how to hide the HTTP headers that you do not want to show to your users. In this example,the following headers get deleted in the HTTP response:
X-Powered-ByX-AspNet-Version
To see the original response:
1. Select the API tab.2. Click Demo Conference API from your API list.3. Select the GetSpeakers operation.4. Click the Test tab, on the top of the screen.5. Press the Send button, at the bottom of the screen.
As you can see the original response looks like this:
Set the transformation policySet the transformation policy1. Browse to your APIM instance.2. Select the API tab.3. Click Demo Conference API from your API list.4. Select All operations.5. On the top of the screen, select Design tab.6. In the Outbound processing window, click the triangle (next to the pencil).
8. Position the cursor inside the <outbound> element.
7. Select Code editor.
9. In the right window, under Transformation policies, click + Set HTTP header twice (to insert twopolicy snippets).
10. Modify your code to look like this:
Replace original URLs in the body of the API response with APIMgateway URLs
Test the original responseTest the original response
Set the transformation policySet the transformation policy
Protect an API by adding rate limit policy (throttling)
<set-header name="X-Powered-By" exists-action="delete" /><set-header name="X-AspNet-Version" exists-action="delete" />
This section shows how to hide original URLs that appear in the body of API's HTTP response and insteadredirect them to the APIM gateway.
To see the original response:
1. Select the API tab.2. Click Demo Conference API from your API list.3. Select the GetSpeakers operation.4. Click the Test tab, on the top of the screen.5. Press the Send button, at the bottom of the screen.
As you can see the original response looks like this:
1. Browse to your APIM instance.2. Select the API tab.3. Click Demo Conference API from your API list.4. Select All operations.5. On the top of the screen, select Design tab.6. In the Outbound processing window, click the triangle (next to the pencil).7. Select Code editor.8. Position the cursor inside the <outbound> element.9. In the right window, under Transformation policies, click + Find and replace string in body.
<find-and-replace from="://conferenceapi.azurewebsites.net" to="://apiphany.azure-api.net/conference"/>
10. Modify your <find-and-replace code (in the element) to replace the URL to match your APIM gateway.For example:
Test the transformations
<policies> <inbound> <rate-limit-by-key calls="3" renewal-period="15" counter-key="@(context.Subscription.Id)" /> <base /> </inbound> <backend> <base /> </backend> <outbound> <set-header name="X-Powered-By" exists-action="delete" /> <set-header name="X-AspNet-Version" exists-action="delete" /> <find-and-replace from="://conferenceapi.azurewebsites.net" to="://apiphany.azure-api.net/conference"/> <base /> </outbound> <on-error> <base /> </on-error></policies>
Test the stripped response headersTest the stripped response headers
This section shows how to add protection for your backend API by configuring rate limits. For example, youmay want to limit a number of calls the API is called so it is not overused by developers. In this example, thelimit is set to 3 calls per 15 seconds for each subscription Id. After 15 seconds, a developer can retry calling theAPI.
1. Browse to your APIM instance.2. Select the API tab.3. Click Demo Conference API from your API list.4. Select All operations.5. On the top of the screen, select Design tab.6. In the Inbound processing window, click the triangle (next to the pencil).7. Select Code editor.8. Position the cursor inside the <inbound> element.9. In the right window, under Access restriction policies, click + Limit call rate per key.
<rate-limit-by-key calls="3" renewal-period="15" counter-key="@(context.Subscription.Id)" />
10. Modify your <rate-limit-by-key code (in the element) to the following code:
At this point your polices code looks like this:
The rest of this section tests policy transformations that you set in this article.
1. Browse to your APIM instance.2. Select the API tab.3. Click Demo Conference API from your API list.4. Click the GetSpeakers operation.5. Select the Test tab.6. Press Send.
As you can see the headers have been stripped:
Test the replaced URLTest the replaced URL
Test the rate limit (throttling)Test the rate limit (throttling)
1. Browse to your APIM instance.2. Select the API tab.3. Click Demo Conference API from your API list.4. Click the GetSpeakers operation.5. Select the Test tab.6. Press Send.
As you can see the URL has been replaced.
1. Browse to your APIM instance.2. Select the API tab.3. Click Demo Conference API from your API list.4. Click the GetSpeakers operation.5. Select the Test tab.6. Press Send three times in a row.
After sending the request 3 times, you get 429 Too many requests response.
7. Wait 15 seconds or so and press Send again. This time you should get a 200 OK response.
Video
Next stepsIn this tutorial, you learned how to:
Transform an API to strip response headersReplace original URLs in the body of the API response with APIM gateway URLsProtect an API by adding rate limit policy (throttling)Test the transformations
Advance to the next tutorial:
Monitor your API
Monitor published APIs4/9/2018 • 6 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
Azure Monitor is an Azure service that provides a single source for monitoring all your Azure resources. WithAzure Monitor, you can visualize, query, route, archive, and take actions on the metrics and logs coming fromAzure resources such as API Management.
In this tutorial, you learn how to:
View activity logsView diagnostic logsView metrics of your APISet up an alert rule when your API gets unauthorized calls
The following video shows how to monitor API Management using Azure Monitor.
Complete the following quickstart: Create an Azure API Management instance.Also, complete the following tutorial: Import and publish your first API.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
TIPTIP
View metrics of your APIs
Set up an alert rule for unauthorized request
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
API Management emits metrics every minute, giving you near real-time visibility into the state and health of yourAPIs. Following is a summary of some of the available metrics:
Capacity (preview): helps you make decisions about upgrading/downgrading your APIM services. The metric isemitted per minute and reflects the gateway capacity at the time of reporting. The metric ranges from 0-100and is calculated based on gateway recourses such as CPU and memory utilization.Total Gateway Requests: the number of API requests in the period.Successful Gateway Requests: the number of API requests that received successful HTTP response codesincluding 304, 307 and anything smaller than 301 (for example, 200).Failed Gateway Requests: the number of API requests that received erroneous HTTP response codes including400 and anything larger than 500.Unauthorized Gateway Requests: the number of API requests that received HTTP response codes including401, 403, and 429.Other Gateway Requests: the number of API requests that received HTTP response codes that do not belong toany of the preceding categories (for example, 418).
To access metrics:
1. Select Metrics from the menu near the bottom of the page.
3. The chart shows the total number of API calls. It also shows the number of API calls that failed.
2. From the drop-down, select metrics you are interested in (you can add multiple metrics).
For example, select Total Gateway Requests and Failed Gateway Requests from the list of availablemetrics.
You can configure to receive alerts based on metrics and activity logs. Azure Monitor allows you to configure analert to do the following when it triggers:
Send an email notificationCall a webhookInvoke an Azure Logic App
To configure alerts:
1. Select Alert rules from the menu bar near the bottom of the page.2. Select Add metric alert.3. Enter a Name for this alert.4. Select Unauthorized Gateway Requests as the metric to monitor.5. Select Email owners, contributors, and readers.6. Press OK.7. Try to call our Conference API without an API key. As the owner of this API Management service, you
receive an email alert.
Activity Logs
NOTENOTE
Diagnostic Logs
TIPTIPThe alert rule can also call a Web Hook or an Azure Logic App when it is triggered.
Activity logs provide insight into the operations that were performed on your API Management services. Usingactivity logs, you can determine the "what, who, and when" for any write operations (PUT, POST, DELETE) taken onyour API Management services.
Activity logs do not include read (GET) operations or operations performed in the Azure portal or using the originalManagement APIs.
You can access activity logs in your API Management service, or access logs of all your Azure resources in AzureMonitor.
To view activity logs:
1. Select your APIM service instance.2. Click Activity log.
Diagnostic logs provide rich information about operations and errors that are important for auditing as well astroubleshooting purposes. Diagnostics logs differ from activity logs. Activity logs provide insights into theoperations that were performed on your Azure resources. Diagnostics logs provide insight into operations thatyour resource performed itself.
To configure diagnostic logs:
1. Select your APIM service instance.2. Click Diagnostic log.3. Click Turn on diagnostics. You can archive diagnostic logs along with metrics to a storage account, stream
{      "isRequestSuccess" : "", "time": "",   "operationName": "",          "category": "",       "durationMs": ,       "callerIpAddress": "",       "correlationId": "",       "location": "",          "httpStatusCodeCategory": "",          "resourceId": "",          "properties": {   "method": "", "url": "", "clientProtocol": "", "responseCode": , "backendMethod": "", "backendUrl": "", "backendResponseCode": , "backendProtocol": "", "requestSize": , "responseSize": , "cache": "", "cacheTime": "", "backendTime": , "clientTime": , "apiId": "", "operationId": "", "productId": "", "userId": "", "apimSubscriptionId": "", "backendId": "", "lastError": { "elapsed" : "", "source" : "", "scope" : "", "section" : "" , "reason" : "", "message" : "" } }   } 
PROPERTY TYPE DESCRIPTION
isRequestSuccess boolean True if the HTTP request completed withresponse status code within 2xx or 3xxrange
time date-time Timestamp of receiving the HTTPrequest by the gateway
operationName string Constant value'Microsoft.ApiManagement/GatewayLogs'
category string Constant value 'GatewayLogs'
them to an Event Hub, or send them to Log Analytics.
API Management currently provides diagnostics logs (batched hourly) about individual API request with eachentry having the following schema:
durationMs integer Number of miliseconds from themoment gateway received request tillthe moment response sent in full
callerIpAddress string IP address of immediate Gateway caller(can be an intermediary)
correlationId string Unique http request identifier assignedby API Management
location string Name of the Azure region where theGateway that processed the requestwas located
httpStatusCodeCategory string Category of http response status code:Successful (301 or less or 304 or 307),Unauthorized (401, 403, 429),Errorneous (400, between 500 and600), Other
resourceId string "Id of the API Management resource/SUBSCRIPTIONS//RESOURCEGROUPS//PROVIDERS/MICROSOFT.APIMANAGEMENT/SERVICE/
properties object Properties of the current request
method string HTTP method of the incoming request
url string URL of the incoming request
clientProtocol string HTTP protocol version of the incomingrequest
responseCode integer Status code of the HTTP response sentto a client
backendMethod string HTTP method of the request sent to abackend
backendUrl string URL of the request sent to a backend
backendResponseCode integer Code of the HTTP response recievedfrom a backend
backendProtocol string HTTP protocol version of the requestsent to a backend
requestSize integer Number of bytes received from a clientduring request processing
responseSize integer Number of bytes sent to a client duringrequest processing
PROPERTY TYPE DESCRIPTION
cache string Status of API Management cacheinvolvement in request processing (i.e.,hit, miss, none)
cacheTime integer Number of miliseconds spent on overallAPI Management cache IO (connecting,sending and receiving bytes)
backendTime integer Number of miliseconds spent on overallbackend IO (connecting, sending andreceiving bytes)
clientTime integer Number of miliseconds spent on overallclient IO (connecting, sending andreceiving bytes)
apiId string API entity identifier for current request
operationId string Operation entity identifier for currentrequest
productId string Product entity identifier for currentrequest
userId string User entity identifier for current request
apimSubscriptionId string Subscription entity identifier for currentrequest
backendId string Backend entity identifier for currentrequest
LastError object Last request processing error
elapsed integer Number of miliseconds elapsed sinceGateway received request till themoment the error occured
source string Name of the policy or processinginternal handler caused the error
scope string Scope of the policy documentcontaining the policy that caused theerror
section string Section of the policy documentcontaining the policy that caused theerror
reason string Error reason
message string Error message
PROPERTY TYPE DESCRIPTION
Next stepsIn this tutorial, you learned how to:
View activity logsView diagnostic logsView metrics of your APISet up an alert rule when your API gets unauthorized calls
Advance to the next tutorial:
Trace calls
Debug your APIs using request tracing12/4/2017 • 1 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
This tutorial describes how to inspect request processing to help you with debugging and troubleshooting yourAPI.
In this tutorial, you learn how to:
Trace a call
Complete the following quickstart: Create an Azure API Management instance.Also, complete the following tutorial: Import and publish your first API.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.
TIPTIP
Trace a call
Next steps
4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select APIs.2. Click Demo Conference API from your API list.3. Select GetSpeakers operation.4. Switch to the Test tab.5. Make sure to include an HTTP header named Ocp-Apim-Trace with the value set to true.6. Click "Send" to make an API call.7. Wait for the call to complete.
TIPTIP
8. Go to the Trace tab in the API console. You can click any of the following links to jump to detailed traceinfo: inbound, backend, outbound.
In the inbound section, you see the original request API Management received from the caller and all thepolicies applied to the request including the rate-limit and set-header policies we added in step 2.
In the backend section, you see the requests API Management sent to the API backend and the response itreceived.
In the outbound section, you see all the policies applied to the response before sending back to the caller.
Each step also shows the elapsed time since the request is received by API Management.
In this tutorial, you learned how to:
Trace a call
Advance to the next tutorial:
Use revisions
Use revisions to make non-breaking changes safely12/4/2017 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
When your API is ready to go and starts to be used by developers, you usually need to take care in makingchanges to that API and at the same time not to disrupt callers of your API. It's also useful to let developers knowabout the changes you made. We can do this in Azure API Management using revisions. For more information,see Versions & revisions and API Versioning with Azure API Management.
In this tutorial, you learn how to:
Add a new revisionMake non-breaking changes to your revisionMake your revision current and add a change log entryBrowse the developer portal to see changes and change log
Complete the following quickstart: Create an Azure API Management instance.Also, complete the following tutorial: Import and publish your first API.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
TIPTIP
Add a new revision
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select APIs page.2. Select Conference API from the API list (or other API to which you want to add revisions).3. Click the Revisions tab from the menu near the top of the page.
TIPTIP
4. Select + Add Revision
You can also choose Add Revision in the context menu (...) of the API.
5. Provide a description for your new revision, to help remember what it will be used for.
Make non-breaking changes to your revision
Make your revision current and add a change log entry
Browse the developer portal to see changes and change log
6. Select Create
NOTENOTE
7. Your new revision is now created.
Your original API remains in Revision 1. This is the revision your users continue to call, until you choose to make adifferent revision current.
1. Select Conference API from the API list.2. Select the Design tab near the top of the screen.
TIPTIP
5. Set your new operation to be POST, and the Name & Display Name of the operation as test6. Save your new operation.7. We have now made a change to Revision 2. Use the Revision Selector near the top of the page to switch back
to Revision 1.8. Notice that your new operation does not appear in Revision 1.
3. Notice that the revision selector (directly above the design tab) shows your current revision as Revision 2.
Use the revision selector to switch between revisions that you wish to work on.
4. Select + Add Operation.
2. Open the context menu (...) for Revision 2.3. Select Make Current. Check Post to Public Change log for this API, if you want to post notes about this
change.4. Select Post to Public Change Log for this API5. Provide a description for your change that developers see, for example Testing revisions. Added new "test"
operation.6. Revision 2 is now current.
1. Select the Revisions tab from the menu near the top of the page.
Next steps
1. In the Azure portal, select APIs2. Select Developer Portal from the top menu.3. Select APIs, and then select Conference API.4. Notice your new test operation is now available.5. Select API Change History from below the API name.6. Notice that your change log entry appears in this list.
In this tutorial, you learned how to:
Add a new revisionMake non-breaking changes to your revisionMake your revision current and add a change log entryBrowse the developer portal to see changes and change log
Advance to the next tutorial:
Publish multiple versions of your API
Publish multiple versions of your API12/4/2017 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
There are times when it is impractical to have all callers to your API use exactly the same version. Sometimes youwant to publish new or different API features to some users, while others want to stick with the API that currentlyworks for them. When callers want to upgrade to a later version, they want to be able to do this using an easy tounderstand approach. We can do this using versions in Azure API Management. For more information, seeVersions & revisions.
In this tutorial, you learn how to:
Add a new version to an existing APIChoose a version schemeAdd the version to a productBrowse the developer portal to see the version
Complete the following quickstart: Create an Azure API Management instance.Also, complete the following tutorial: Import and publish your first API.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.
TIPTIP
Add a new version
Choose a versioning scheme
2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select Conference API from the API list.2. Select the context menu (...) next to it.
TIPTIP
3. Select + Add Version.
Versions can also be enabled when you first create a new API - select Version this API? on the Add API screen.
Add the version to a product
Azure API Management allows you to choose the way in which you allow callers to specify which version of yourAPI they want. You do this by choosing a versioning scheme. This scheme can be either path, header or querystring. In our example, we use path.
1. Leave path selected as your versioning scheme.
TIPTIP
4. Select Create to set up your new version.
NOTENOTE
2. Add v1 as your version identifier.
If you select header or query string as a versioning scheme, you need to provide an additional value - the name ofthe header or query string parameter.
3. Provide a description if you wish.
5. Underneath Big Conference API in the API List, you now see two distinct APIs - Original, and v1.
If you add a version to a non-versioned API, we always create an Original for you - responding on the default URL.This ensures that any existing callers are not broken by the process of adding a version. If you create a new API withversions enabled at the start, an Original is not created.
6. You can now edit and configure v1 as an API that is separate to Original. Changes to one version do notaffect another.
For callers to see your new version, it must be added to a product (products are not inherited from parentversions).
1. Select Products from the service management page.2. Select Unlimited.
Browse the developer portal to see the version
Next steps
3. Select APIs.4. Select Add.5. Select Conference API, Version v1.6. Return to the service management page and select APIs.
1. Select Developer Portal from the top menu.2. Select APIs, notice that Conference API shows Original and v1 versions.3. Select v1.4. Notice the Request URL of the first operation in the list. It shows that the API URL path includes v1.
In this tutorial, you learn how to:
Add a new version to an existing APIChoose a version schemeAdd the version to a productBrowse the developer portal to see the version
Advance to the next tutorial:
Upgrade and scale
Customize the style of the Developer portal pages12/4/2017 • 2 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
There are three most common ways to customize the Developer portal in Azure API Management:
Edit the contents of static pages and page layout elementsUpdate the styles used for page elements across the developer portal (explained in this guide)Modify the templates used for pages generated by the portal (for example, API docs, products, userauthentication)
In this tutorial, you learn how to:
Customize the style of elements on pages of the Developer portalView your change
Complete the following quickstart: Create an Azure API Management instance.Also, complete the following tutorial: Import and publish your first API.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
TIPTIP
Customize the Developer portal
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select Overview.2. Click the Developer portal button on the top of the Overview window. Alternatively, you can click the
Developer portal URL link.3. On the upper left side of the screen, you see an icon comprised of two paint brushes. Hover over this icon to
open the portal customization menu.
4. Select Styles from the menu to open the styling customization pane.
All elements that you can customize using Styles appear on the page
5. Enter "headings-color" in the Change variable values to customize developer portal appearance:field.
The @headings-color element appears on the page. This variable controls the color of the text.
View your change
Next steps
TIPTIP
9. Select Publish customizations to make the changes publicly available.
6. Click on the field for the @headings-color variable.
Color picker drop-down opens.
7. From the color pickers drop-down select a new color.
Real-time preview is available for all changes. A progress indicator appears at the top of the customization pane. Aftera couple seconds the header text changes in color to the newly selected.
8. Select Publish from the lower left on the customization pane menu.
1. Navigate to the Developer portal.2. You can see the change that you made.
In this tutorial, you learned how to:
Customize the style of elements on pages of the Developer portalView your change
Customize the Azure API Management developer portal using templates
API Management policy samples12/13/2017 • 1 min to read • Edit Online
Inbound policies
Add a Forwarded header to allow the backend API toconstruct proper URLs
Demonstrates how to add a Forwarded header in theinbound request to allow the backend API to constructproper URLs.
Add a header containing a correlation id Demonstrates how to add a header containing a correlationID to the inbound request.
Add capabilities to a backend service and cache the response Shows how to add capabilities to a backend service. Forexample, accept a name of the place instead of latitude andlongitude in a weather forecast API.
Authorize access based on JWT claims Shows how to authorize access to specific HTTP methods onan API based on JWT claims.
Authorize access using Google OAuth token Shows how to authorize access to your endpoints usingGoogle as an OAuth token provider.
Generate Shared Access Signature and forward request toAzure storage
Shows how to generate Shared Access Signature usingexpressions and forward the request to Azure storage withrewrite-uri policy.
Get OAuth2 access token from AAD and forward it to thebackend
Provides and example of using OAuth2 for authorizationbetween the gateway and a backend. It shows how to obtainan access token from AAD and forward it to the backend.
Get X-CSRF token from SAP gateway using send requestpolicy
Shows how to implement X-CSRF pattern used by many APIs.This example is specific to SAP Gateway.
Route the request based on the size of its body Demonstrates how to route requests based on the size oftheir bodies.
Send request context information to the backend service Shows how to send some context information to the backendservice for logging or processing.
Set response cache duration Demonstrates how to set response cache duration usingmaxAge value in Cache-Control header sent by the backend.
Outbound policies
Filter response content Demonstrates how to filter data elements from the responsepayload based on the product associated with the request.
Policies are a powerful capability of the system that allows the publisher to change the behavior of the APIthrough configuration. Policies are a collection of statements that are executed sequentially on the request orresponse of an API. The following table includes links to samples and gives a brief description of each sample.
On-error policies
Log errors to Stackify Shows how to add an error logging policy to send errors toStackify for logging.
Azure PowerShell samples for API Management12/13/2017 • 1 min to read • Edit Online
Provision and manage
Add a user Creates a user in API Management and gets a subscriptionkey.
Create an APIM service Creates a Developer SKU API Management Service.
Restore service Backups and restores an APIM service.
Scale an APIM service Scales and adds region to the APIM service.
Set up custom domain Sets up custom domain on proxy and portal endpoint of theAPI Management service.
Define API
Import API Imports an API and adds to an APIM product.
Secure
Secure backend Secures backend with mutual certificate authentication.
Protect
Set up rate limit policy Applies rate limit to policy at the product Level .
The following table includes links to bash scripts built using the Azure PowerShell.
Terminology12/4/2017 • 1 min to read • Edit Online
Term definitions
Next steps
This article gives definitions for the terms that are specific to API Management (APIM).
Backend API - An HTTP service that implements your API and its operations.Frontend API/APIM API - An APIM API does not host APIs, it creates facades for your APIs in order tocustomize the facade according to your needs without touching the back end API. For more information, seeImport and publish an API.APIM product - a product contains one or more APIs as well as a usage quota and the terms of use. You caninclude a number of APIs and offer them to developers through the Developer portal. For more information,see Create and publish a product.APIM API operation - Each APIM API represents a set of operations available to developers. Each APIM APIcontains a reference to the back end service that implements the API, and its operations map to the operationsimplemented by the back end service. For more information, see Mock API responses.Version - Sometimes you want to publish new or different API features to some users, while others want tostick with the API that currently works for them. For more information, see Publish multiple versions of yourAPI.Revision - When your API is ready to go and starts to be used by developers, you usually need to take care inmaking changes to that API and at the same time not to disrupt callers of your API. It's also useful to letdevelopers know about the changes you made. For more information, see Use revisions.Developer portal - Your customers (developers) should use the Developer portal to access your APIs. TheDeveloper portal can be customized. For more information, see Customize the Developer portal.
Create an instance
Policies in Azure API Management2/28/2018 • 3 min to read • Edit Online
Understanding policy configuration
NOTENOTE
<policies> <inbound> <!-- statements to be applied to the request go here --> </inbound> <backend> <!-- statements to be applied before the request is forwarded to the backend service go here --> </backend> <outbound> <!-- statements to be applied to the response go here --> </outbound> <on-error> <!-- statements to be applied if there is an error condition go here --> </on-error></policies>
In Azure API Management (APIM), policies are a powerful capability of the system that allow the publisher tochange the behavior of the API through configuration. Policies are a collection of Statements that are executedsequentially on the request or response of an API. Popular Statements include format conversion from XML toJSON and call rate limiting to restrict the amount of incoming calls from a developer. Many more policies areavailable out of the box.
Policies are applied inside the gateway which sits between the API consumer and the managed API. The gatewayreceives all requests and usually forwards them unaltered to the underlying API. However a policy can applychanges to both the inbound request and outbound response.
Policy expressions can be used as attribute values or text values in any of the API Management policies, unlessthe policy specifies otherwise. Some policies such as the Control flow and Set variable policies are based onpolicy expressions. For more information, see Advanced policies and Policy expressions.
The policy definition is a simple XML document that describes a sequence of inbound and outbound statements.The XML can be edited directly in the definition window. A list of statements is provided to the right andstatements applicable to the current scope are enabled and highlighted.
Clicking an enabled statement will add the appropriate XML at the location of the cursor in the definition view.
If the policy that you want to add is not enabled, ensure that you are in the correct scope for that policy. Each policystatement is designed for use in certain scopes and policy sections. To review the policy sections and scopes for a policy,check the Usage section for that policy in the Policy Reference.
The configuration is divided into inbound , backend , outbound , and on-error . The series of specified policystatements is executes in order for a request and a response.
If there is an error during the processing of a request, any remaining steps in the inbound , backend , or outbound sections are skipped and execution jumps to the statements in the on-error section. By placing policy
statements in the on-error section you can review the error by using the context.LastError property, inspect
How to configure policies
Policy Reference
Policy samples
ExamplesApply policies specified at different scopesApply policies specified at different scopes
<policies> <inbound> <cross-domain /> <base /> <find-and-replace from="xyz" to="abc" /> </inbound></policies>
Restrict incoming requestsRestrict incoming requests
and customize the error response using the set-body policy, and configure what happens if an error occurs.There are error codes for built-in steps and for errors that may occur during the processing of policy statements.For more information, see Error handling in API Management policies.
For information on how to configure policies, see Set or edit policies.
See the Policy reference for a full list of policy statements and their settings.
See Policy samples for more code examples.
If you have a policy at the global level and a policy configured for an API, then whenever that particular API isused both policies will be applied. API Management allows for deterministic ordering of combined policystatements via the base element.
In the example policy definition above, the cross-domain statement would execute before any higher policieswhich would in turn, be followed by the find-and-replace policy.
To add a new statement to restrict incoming requests to specified IP addresses, place the cursor just inside thecontent of the inbound XML element and click the Restrict caller IPs statement.
This will add an XML snippet to the inbound element that provides guidance on how to configure the statement.
<ip-filter action="allow | forbid"> <address>address</address> <address-range from="address" to="address"/></ip-filter>
<ip-filter action="allow"> <address>1.2.3.4</address></ip-filter>
Next steps
To limit inbound requests and accept only those from an IP address of 1.2.3.4 modify the XML as follows:
For more information working with policies, see:
Transform APIsPolicy Reference for a full list of policy statements and their settingsPolicy samples
API Management policies2/28/2018 • 4 min to read • Edit Online
Policies
This section provides a reference for the following API Management policies. For information on adding andconfiguring policies, see Policies in API Management.
Policies are a powerful capability of the system that allow the publisher to change the behavior of the API throughconfiguration. Policies are a collection of Statements that are executed sequentially on the request or response ofan API. Popular Statements include format conversion from XML to JSON and call rate limiting to restrict theamount of incoming calls from a developer. Many more policies are available out of the box.
Policy expressions can be used as attribute values or text values in any of the API Management policies, unless thepolicy specifies otherwise. Some policies such as the Control flow and Set variable policies are based on policyexpressions. For more information, see Advanced policies and Policy expressions.
Access restriction policies
Advanced policies
Authentication policies
Check HTTP header - Enforces existence and/or value of a HTTP Header.Limit call rate by subscription - Prevents API usage spikes by limiting call rate, on a per subscriptionbasis.Limit call rate by key - Prevents API usage spikes by limiting call rate, on a per key basis.Restrict caller IPs - Filters (allows/denies) calls from specific IP addresses and/or address ranges.Set usage quota by subscription - Allows you to enforce a renewable or lifetime call volume and/orbandwidth quota, on a per subscription basis.Set usage quota by key - Allows you to enforce a renewable or lifetime call volume and/or bandwidthquota, on a per key basis.Validate JWT - Enforces existence and validity of a JWT extracted from either a specified HTTP Headeror a specified query parameter.
Control flow - Conditionally applies policy statements based on the evaluation of Boolean expressions.Forward request - Forwards the request to the backend service.Log to Event Hub - Sends messages in the specified format to a message target defined by a Loggerentity.Retry - Retries execution of the enclosed policy statements, if and until the condition is met. Executionwill repeat at the specified time intervals and up to the specified retry count.Return response - Aborts pipeline execution and returns the specified response directly to the caller.Send one way request - Sends a request to the specified URL without waiting for a response.Send request - Sends a request to the specified URL.Set variable - Persist a value in a named context variable for later access.Set request method - Allows you to change the HTTP method for a request.Set status code - Changes the HTTP status code to the specified value.Trace - Adds a string into the API Inspector output.Wait - Waits for enclosed Send request, Get value from cache, or Control flow policies to completebefore proceeding.
Authenticate with Basic - Authenticate with a backend service using Basic authentication.
Next steps
Caching policies
Cross domain policies
Transformation policies
Authenticate with client certificate - Authenticate with a backend service using client certificates.
Get from cache - Perform cache look up and return a valid cached response when available.Store to cache - Caches response according to the specified cache control configuration.Get value from cache - Retrieve a cached item by key.Store value in cache - Store an item in the cache by key.Remove value from cache - Remove an item in the cache by key.
Allow cross-domain calls - Makes the API accessible from Adobe Flash and Microsoft Silverlightbrowser-based clients.CORS - Adds cross-origin resource sharing (CORS) support to an operation or an API to allow cross-domain calls from browser-based clients.JSONP - Adds JSON with padding (JSONP) support to an operation or an API to allow cross-domaincalls from JavaScript browser-based clients.
Convert JSON to XML - Converts request or response body from JSON to XML.Convert XML to JSON - Converts request or response body from XML to JSON.Find and replace string in body - Finds a request or response substring and replaces it with a differentsubstring.Mask URLs in content - Re-writes (masks) links in the response body so that they point to the equivalentlink via the gateway.Set backend service - Changes the backend service for an incoming request.Set body - Sets the message body for incoming and outgoing requests.Set HTTP header - Assigns a value to an existing response and/or request header or adds a newresponse and/or request header.Set query string parameter - Adds, replaces value of, or deletes request query string parameter.Rewrite URL - Converts a request URL from its public form to the form expected by the web service.Transform XML using an XSLT - Applies an XSL transformation to XML in the request or response body.
For more information working with policies, see:
Policies in API ManagementTransform APIsPolicy Reference for a full list of policy statements and their settingsPolicy samples
Managing Azure API Management using AzureAutomation3/19/2018 • 1 min to read • Edit Online
What is Azure Automation?
How can Azure Automation help manage Azure API Management?
Next Steps
This guide introduces you to the Azure Automation service, and how it can be used to simplify management ofAzure API Management.
Azure Automation is an Azure service for simplifying cloud management through process automation. UsingAzure Automation, manual, repeated, long-running, and error-prone tasks can be automated to increase reliability,efficiency, and time to value for your organization.
Azure Automation provides a highly reliable, highly available workflow execution engine that scales to meet yourneeds. In Azure Automation, processes can be kicked off manually, by 3rd-party systems, or at scheduled intervalsso that tasks happen exactly when needed.
Reduce operational overhead and free up IT and DevOps staff to focus on work that adds business value bymoving your cloud management tasks to be run automatically by Azure Automation.
API Management can be managed in Azure Automation by using the Windows PowerShell cmdlets for Azure APIManagement API. Within Azure Automation, you can write PowerShell workflow scripts to perform many of yourAPI Management tasks using the cmdlets. You can also pair these cmdlets in Azure Automation with the cmdletsfor other Azure services, to automate complex tasks across Azure services and 3rd party systems.
Here are some examples of using API Management with Automation:
Azure API Management – Using PowerShell for backup and restore
Now that you've learned the basics of Azure Automation and how it can be used to manage Azure APIManagement, follow these links to learn more.
See the Azure Automation getting started tutorial.
Error handling in API Management policies12/4/2017 • 4 min to read • Edit Online
Error handling in API Management
<policies> <inbound> <!-- statements to be applied to the request go here --> </inbound> <backend> <!-- statements to be applied before the request is forwarded to the backend service go here --> </backend> <outbound> <!-- statements to be applied to the response go here --> </outbound> <on-error> <!-- statements to be applied if there is an error condition go here --> </on-error> </policies>
NOTENOTE
Policies allowed in on-errorPolicies allowed in on-error
Azure API Management allows publishers to respond to error conditions that may occur during the processing ofrequests to the proxy by providing a ProxyError object. The ProxyError object is accessed through thecontext.LastError property and can be used by policies in the on-error policy section. This topic provides areference for the error handling capabilities in Azure API Management.
Policies in Azure API Management are divided into inbound , backend , outbound , and on-error sections as shownin the following example.
During the processing of a request, built-in steps are executed along with any policies that are in scope for therequest. If an error occurs, processing immediately jumps to the on-error policy section. The on-error policysection can be used at any scope, and API publishers can configure custom behavior such as logging the error toevent hubs or creating a new response to return to the caller.
The on-error section is not present in policies by default. To add the on-error section to a policy, browse to the desiredpolicy in the policy editor and add it. For more information about configuring policies, see Policies in API Management.
If there is no on-error section, callers will receive 400 or 500 HTTP response messages if an error condition occurs.
The following policies can be used in the on-error policy section.
chooseset-variablefind-and-replacereturn-responseset-headerset-methodset-status
LastError
NAME TYPE DESCRIPTION REQUIRED
Source string Names the element wherethe error occurred. Could beeither policy or a built-inpipeline step name.
Yes
Reason string Machine-friendly error code,which could be used in errorhandling.
No
Message string Human-readable errordescription.
Yes
Scope string Name of the scope wherethe error occurred and couldbe one of "global", "product","api", or "operation"
No
Section string Section name where erroroccurred and could one of"inbound", "backend","outbound", or "on-error".
No
Path string Specifies nested policy, e.g."choose[3]/when[2]".
No
PolicyId string Value of the id attribute, ifspecified by the customer,on the policy where erroroccurred
No
NOTENOTE
Predefined errors for built-in steps
send-requestsend-one-way-requestlog-to-eventhubjson-to-xmlxml-to-json
When an error occurs and control jumps to the on-error policy section, the error is stored in context.LastErrorproperty which can be accessed by policies in the on-error section and has the following properties.
All policies have an optional id attribute that can be added to the root element of the policy. If this attribute is present in apolicy when an error condition occurs, the value of the attribute can be retrieved using the context.LastError.PolicyId
property.
The following errors are predefined for error conditions that can occur during the evaluation of built-in processingsteps.
SOURCE CONDITION REASON MESSAGE
configuration Uri doesn't match to any Apior Operation
OperationNotFound Unable to match incomingrequest to an operation.
authorization Subscription key notsupplied
SubscriptionKeyNotFound Access denied due tomissing subscription key.Make sure to includesubscription key whenmaking requests to this API.
authorization Subscription key value isinvalid
SubscriptionKeyInvalid Access denied due to invalidsubscription key. Make sureto provide a valid key for anactive subscription.
Predefined errors for policies
SOURCE CONDITION REASON MESSAGE
rate-limit Rate limit exceeded RateLimitExceeded Rate limit is exceeded
quota Quota exceeded QuotaExceeded Out of call volume quota.Quota will be replenished inxx:xx:xx. -or- Out ofbandwidth quota. Quota willbe replenished in xx:xx:xx.
jsonp Callback parameter value isinvalid (contains wrongcharacters)
CallbackParameterInvalid Value of callback parameter{callback-parameter-name} isnot a valid JavaScriptidentifier.
ip-filter Failed to parse caller IP fromrequest
FailedToParseCallerIP Failed to establish IP addressfor the caller. Access denied.
ip-filter Caller IP is not in allowed list CallerIpNotAllowed Caller IP address {ip-address}is not allowed. Accessdenied.
ip-filter Caller IP is in blocked list CallerIpBlocked Caller IP address is blocked.Access denied.
check-header Required header notpresented or value is missing
HeaderNotFound Header {header-name} wasnot found in the request.Access denied.
check-header Required header notpresented or value is missing
HeaderValueNotAllowed Header {header-name} valueof {header-value} is notallowed. Access denied.
validate-jwt Jwt token is missing inrequest
TokenNotFound JWT not found in therequest. Access denied.
The following errors are predefined for error conditions that can occur during policy evaluation.
validate-jwt Signature validation failed TokenSignatureInvalid <message from jwt library>.Access denied.
validate-jwt Invalid audience TokenAudienceNotAllowed <message from jwt library>.Access denied.
validate-jwt Invalid issuer TokenIssuerNotAllowed <message from jwt library>.Access denied.
validate-jwt Token expired TokenExpired <message from jwt library>.Access denied.
validate-jwt Signature key was notresolved by id
TokenSignatureKeyNotFound <message from jwt library>.Access denied.
validate-jwt Required claims are missingfrom token
TokenClaimNotFound JWT token is missing thefollowing claims: <c1>,<c2>, … Access denied.
validate-jwt Claim values mismatch TokenClaimValueNotAllowed Claim {claim-name} value of{claim-value} is not allowed.Access denied.
validate-jwt Other validation failures JwtInvalid <message from jwt library>
SOURCE CONDITION REASON MESSAGE
Next stepsFor more information working with policies, see:
Policies in API ManagementTransform APIsPolicy Reference for a full list of policy statements and their settingsPolicy samples
API import restrictions and known issues4/11/2018 • 1 min to read • Edit Online
About this list
Open API/Swagger
IMPORTANTIMPORTANT
WSDL
WADL
When importing an API, you might come across some restrictions or identify issues that need to be rectified beforeyou can successfully import. This article documents these, organized by the import format of the API.
If you are receiving errors importing your Open API document, ensure you have validated it - either using thedesigner in the Azure portal (Design - Front End - Open API Specification Editor), or with a third-party tool such asSwagger Editor.
Only JSON format for OpenAPI is supported.Schemas referenced using $ref properties can't contain other $ref properties.$ref pointers can't reference external files.x-ms-paths and x-servers are the only supported extensions.Custom extensions are ignored on import and are not saved or preserved for export.
See this document for important information and tips related to OpenAPI import.
WSDL files are used to generate SOAP Pass-through APIs or serve as the backend of a SOAP-to-REST API.
SOAP bindings -Only SOAP bindings of style ”document” and “literal” encoding are supported. There is nosupport for “rpc” style or SOAP-Encoding.WSDL:Import - This attribute is not supported. Customers should merge the imports into one document.Messages with multiple parts - These types of messages are not supported.WCF wsHttpBinding - SOAP services created with Windows Communication Foundation should usebasicHttpBinding - wsHttpBinding is not supported.MTOM - Services using MTOM may work. Official support is not offered at this time.Recursion - Types that are defined recursively (for example, refer to an array of themselves) are not supportedby APIM.
Currently, there are no known WADL import issues.
Add an API manually12/4/2017 • 5 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
TIPTIP
Create an API
The steps in this article show how to use the Azure portal to add an API manually to the API Management (APIM)instance. A common scenario when you would want to create a blank API and define it manually is when you wantto mock the API. For details about mocking an API, see Mock API responses.
If you want to import an existing API, see related topics section.
In this article, we create a blank API and specify httpbin.org (a public testing service) as a back-end API.
Complete the following quickstart: Create an Azure API Management instance
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select APIs from under API MANAGEMENT.2. From the left menu, select + Add API.3. Select Blank API from the list.
NAME VALUE DESCRIPTION
Display name "Blank API" This name is displayed in theDeveloper portal.
Web Service URL (optional) "http://httpbin.org" If you want to mock an API, youmight not enter anything. In this case, we enterhttp://httpbin.org. This is a publictesting service. If you want to import an API that ismapped to a back end automatically,see one of the topics in the relatedtopics section.
URL scheme "HTTPS" In this case, even though the backend has non-secure HTTP access, wespecify a secure HTTPS APIM accessto the back end. This kind of scenario (HTTPS to HTTP)is called HTTPS termination. Youmight do it if your API exists within avirtual network (where you know theaccess is secure even if HTTPS is notused). You might want to use "HTTPStermination" to save on some CPUcycles.
4. Enter settings for the API.
NOTENOTE
Add and test an operation
Add the operationAdd the operation
Test the operationTest the operation
URL suffix "hbin" The suffix is a name that identifiesthis specific API in this APIM instance.It has to be unique in this APIMinstance.
Products "Unlimited" Publish the API by associating theAPI with a product. If you want forthe API to be published and beavailable to developers, add it to aproduct. You can do it during APIcreation or set it later.
Products are associations of one ormore APIs. You can include a numberof APIs and offer them to developersthrough the developer portal. Developers must first subscribe to aproduct to get access to the API.When they subscribe, they get asubscription key that is good for anyAPI in that product. If you createdthe APIM instance, you are anadministrator already, so you aresubscribed to every product bydefault.
By default, each API Managementinstance comes with two sampleproducts: Starter and Unlimited.
NAME VALUE DESCRIPTION
5. Select Create.
At this point, you have no operations in APIM that map to the operations in your back-end API. If you call anoperation that is exposed through the back end but not through the APIM, you get a 404.
By default, when you add an API, even if it is connected to some back-end service, APIM will not expose any operations untilyou whitelist them. To whitelist an operation of your back-end service, create an APIM operation that maps to the back-endoperation.
This section shows how to add a "/get" operation in order to map it to the back end "http://httpbin.org/get"operation.
1. Select the API you created in the previous step.2. Click + Add Operation.3. In the URL, select GET and enter "/get" in the resource.4. Enter "FetchData" for Display name.5. Select Save.
Test the operation in the Azure portal. Alternatively, you can test it in the Developer portal.
Add and test a parameterized operation
Add the operationAdd the operation
Test the operationTest the operation
Append other APIs
1. Select the Test tab.2. Select FetchData.3. Press Send.
The response that the "http://httpbin.org/get" operation generates appears. If you want to transform youroperations, see Transform and protect your API.
This section shows how to add an operation that takes a parameter. In this case, we map the operation to"http://httpbin.org/status/200".
1. Select the API you created in the previous step.2. Click + Add Operation.3. In the URL, select GET and enter "/status/{code}" in the resource. Optionally, you can provide some information
associated with this parameter. For example, enter "Number" for TYPE , "200" (default) for VALUES.4. Enter "GetStatus" for Display name.5. Select Save.
Test the operation in the Azure portal. Alternatively, you can test it in the Developer portal.
1. Select the Test tab.2. Select GetStatus. By default the code value is set to "200". You can change it to test other values. For example,
type "418".3. Press Send.
The response that the "http://httpbin.org/status/200" operation generates appears. If you want to transformyour operations, see Transform and protect your API.
An API can be composed of APIs exposed by different services: OpenAPI Specification, SOAP API, API App,Function App, Logic App, Service Fabric.
To append a different API to your existing API, follow the steps below. Once you import another API, theoperations are appended to your current API.
1. Navigate to your APIM instance in the Azure portal.2. Select APIs from under API MANAGEMENT.3. Press ellipsis ". . ." next tp the API that you want to append another API to.
Related topics
Next steps
4. Select Import from the drop-down menu.5. Select one of services from which you want to import an API.
Import an OpenAPI SpecificationImport a SOAP APIImport a SOAP API and convert to RESTImport an API AppImport a Function AppImport a Logic AppImport a Service Fabric appEdit an API
Transform and protect a published API
Import an OpenAPI specification4/9/2018 • 4 min to read • Edit Online
IMPORTANTIMPORTANT
Prerequisites
Navigate to your APIM instance
TIPTIP
This article shows how to import an "OpenAPI specification" back-end API residing athttp://conferenceapi.azurewebsites.net?format=json. This back-end API is provided by Microsoft and hosted onAzure. The article also shows how to test the APIM API.
See this document for important information and tips related to OpenAPI import.
In this article, you learn how to:
Import an "OpenAPI specification" back-end APITest the API in the Azure portalTest the API in the Developer portal
Complete the following quickstart: Create an Azure API Management instance
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
Import and publish a back-end API1. Select APIs from under API MANAGEMENT.
2. Select OpenAPI specification from the Add a new API list.
SETTING VALUE DESCRIPTION
OpenAPI Specification http://conferenceapi.azurewebsites.net?format=json
References the service implementingthe API. API management forwardsrequests to this address.
Display name Demo Conference API If you press tab after entering theservice URL, APIM will fill out thisfield based on what is in the json. This name is displayed in theDeveloper portal.
Name demo-conference-api Provides a unique name for the API. If you press tab after entering theservice URL, APIM will fill out thisfield based on what is in the json.
Description Provide an optional description ofthe API.
If you press tab after entering theservice URL, APIM will fill out thisfield based on what is in the json.
3. Enter appropriate settings. You can set all the API values during creation. Alternately, you can set some ofthem later by going to the Settings tab. If you press tab some (or all) of the fields get filled up with the info from the specified back-end service.
Test the new APIM API in the Azure portal
API URL suffix conference The suffix is appended to the baseURL for the API managementservice. API Managementdistinguishes APIs by their suffix andtherefore the suffix must be uniquefor every API for a given publisher.
URL scheme HTTPS Determines which protocols can beused to access the API.
Products Unlimited Publish the API by associating theAPI with a product. To optionally addthis new API to a product, type theproduct name. This step can berepeated multiple times to add theAPI to multiple products.Products are associations of one ormore APIs. You can include a numberof APIs and offer them to developersthrough the developer portal.Developers must first subscribe to aproduct to get access to the API.When they subscribe, they get asubscription key that is good for anyAPI in that product. If you createdthe APIM instance, you are anadministrator already, so you aresubscribed to every product bydefault.By default, each API Managementinstance comes with two sampleproducts: Starter and Unlimited.
SETTING VALUE DESCRIPTION
4. Select Create.
Operations can be called directly from the Azure portal, which provides a convenient way to view and test theoperations of an API.
1. Select the API you created in the previous step.2. Press the Test tab.
Call an operation from the Developer portal
3. Click on GetSpeakers.
The page displays fields for query parameters but in this case we don't have any. The page also displaysfields for the headers. One of the headers is "Ocp-Apim-Subscription-Key", for the subscription key of theproduct that is associated with this API. If you created the APIM instance, you are an administrator already,so the key is filled in automatically.
4. Press Send.
Backend responds with 200 OK and some data.
Operations can also be called Developer portal to test APIs.
1. Select the API you created in the "Import and publish a back-end API" step.
3. Select API.4. Select Demo Conference API.
2. Press Developer portal.
The "Developer portal" site opens up.
5. Click GetSpeakers.
Append other APIs
Related topics
Next steps
6. Press Try it.
The page displays fields for query parameters but in this case we don't have any. The page also displaysfields for the headers. One of the headers is "Ocp-Apim-Subscription-Key", for the subscription key of theproduct that is associated with this API. If you created the APIM instance, you are an administrator already,so the key is filled in automatically.
7. Press Send.
After an operation is invoked, the developer portal displays the Response status, the Response headers,and any Response content.
An API can be composed of APIs exposed by different services: OpenAPI Specification, SOAP API, API App,Function App, Logic App, Service Fabric.
To append a different API to your existing API, follow the steps below. Once you import another API, theoperations are appended to your current API.
1. Navigate to your APIM instance in the Azure portal.2. Select APIs from under API MANAGEMENT.3. Press ellipsis ". . ." next tp the API that you want to append another API to.4. Select Import from the drop-down menu.5. Select one of services from which you want to import an API.
Import an OpenAPI SpecificationImport a SOAP APIImport a SOAP API and convert to RESTImport an API AppImport a Function AppImport a Logic AppImport a Service Fabric appEdit an API
Transform and protect a published API
Import SOAP API12/4/2017 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
TIPTIP
Import and publish a back-end API
This article shows how to import a standard XML representation of a SOAP API. The article also shows how totest the APIM API.
In this article, you learn how to:
Import SOAP APITest the API in the Azure portalTest the API in the Developer portal
Complete the following quickstart: Create an Azure API Management instance
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select APIs from under API MANAGEMENT.2. Select WSDL from the Add a new API list.
Test the new APIM API in the administrative portalTest the new APIM API in the administrative portal
Call an operation from the developer portalCall an operation from the developer portal
3. In the WSDL specification, enter the URL to where your SOAP API resides.
6. Add an API URL suffix. The suffix is a name that identifies this specific API in this APIM instance. It has to beunique in this APIM instance.
8. Select Create.
4. The SOAP pass-through radio button is selected by default. With this selection, the API is going to beexposed as SOAP. Consumer has to use SOAP rules. If you want to "restify" the API, follow the steps inImport a SOAP API and convert it to REST.
5. Press tab.
The following fields get filled up with the info from the SOAP API: Display name, Name, Description.
7. Publish the API by associating the API with a product. In this case, the "Unlimited" product is used. If youwant for the API to be published and be available to developers, add it to a product. You can do it duringAPI creation or set it later.
Products are associations of one or more APIs. You can include a number of APIs and offer them todevelopers through the developer portal. Developers must first subscribe to a product to get access to theAPI. When they subscribe, they get a subscription key that is good for any API in that product. If youcreated the APIM instance, you are an administrator already, so you are subscribed to every product bydefault.
By default, each API Management instance comes with two sample products:
StarterUnlimited
Operations can be called directly from the administrative portal, which provides a convenient way to view and testthe operations of an API.
1. Select the API you created in the previous step.2. Press the Test tab.3. Select some operation.
The page displays fields for query parameters and fields for the headers. One of the headers is "Ocp-Apim-Subscription-Key", for the subscription key of the product that is associated with this API. If you created theAPIM instance, you are an administrator already, so the key is filled in automatically.
4. Press Send.
Backend responds with 200 OK and some data.
Operations can also be called Developer portal to test APIs.
Append other APIs
Related topics
Next steps
1. Select the API you created in the "Import and publish a back-end API" step.
3. Select the API that you created.4. Click the operation you want to test.5. Press Try it.
2. Press Developer portal.
The "Developer portal" site opens up.
6. Press Send.
After an operation is invoked, the developer portal displays the Response status, the Response headers,and any Response content.
An API can be composed of APIs exposed by different services: OpenAPI Specification, SOAP API, API App,Function App, Logic App, Service Fabric.
To append a different API to your existing API, follow the steps below. Once you import another API, theoperations are appended to your current API.
1. Navigate to your APIM instance in the Azure portal.2. Select APIs from under API MANAGEMENT.3. Press ellipsis ". . ." next tp the API that you want to append another API to.4. Select Import from the drop-down menu.5. Select one of services from which you want to import an API.
Import an OpenAPI SpecificationImport a SOAP APIImport a SOAP API and convert to RESTImport an API AppImport a Function AppImport a Logic AppImport a Service Fabric appEdit an API
Transform and protect a published API
Import a SOAP API and convert to REST12/4/2017 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
TIPTIP
Import and publish a back-end API
This article shows how to import a SOAP API and convert it to REST. The article also shows how to test theAPIM API.
In this article, you learn how to:
Import a SOAP API and convert to RESTTest the API in the Azure portalTest the API in the Developer portal
Complete the following quickstart: Create an Azure API Management instance
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select APIs from under API MANAGEMENT.2. Select WSDL from the Add a new API list.
Test the new APIM API in the Azure portal
3. In the WSDL specification, enter the URL to where your SOAP API resides.
6. Add an API URL suffix. The suffix is a name that identifies this specific API in this APIM instance. It has to beunique in this APIM instance.
8. Select Create.
4. Click SOAP to REST radio button. When this option is clicked, APIM attempts to make an automatictransformation between XML and JSON. In this case consumers should be calling the API as a restful API,which returns JSON. APIM is converting each request into a SOAP call.
5. Press tab.
The following fields get filled up with the info from the SOAP API: Display name, Name, Description.
7. Publish the API by associating the API with a product. In this case, the "Unlimited" product is used. If youwant for the API to be published and be available to developers, add it to a product. You can do it duringAPI creation or set it later.
Products are associations of one or more APIs. You can include a number of APIs and offer them todevelopers through the developer portal. Developers must first subscribe to a product to get access to theAPI. When they subscribe, they get a subscription key that is good for any API in that product. If youcreated the APIM instance, you are an administrator already, so you are subscribed to every product bydefault.
By default, each API Management instance comes with two sample products:
StarterUnlimited
Operations can be called directly from the Azure portal, which provides a convenient way to view and test theoperations of an API.
1. Select the API you created in the previous step.2. Press the Test tab.3. Select some operation.
The page displays fields for query parameters and fields for the headers. One of the headers is "Ocp-Apim-Subscription-Key", for the subscription key of the product that is associated with this API. If youcreated the APIM instance, you are an administrator already, so the key is filled in automatically.
4. Press Send.
Backend responds with 200 OK and some data.
Call an operation from the developer portal
Append other APIs
Related topics
Operations can also be called Developer portal to test APIs.
1. Select the API you created in the "Import and publish a back-end API" step.
3. Select the API that you created.4. Click the operation you want to test.5. Press Try it.
2. Press Developer portal.
The "Developer portal" site opens up.
6. Press Send.
After an operation is invoked, the developer portal displays the Response status, the Response headers,and any Response content.
An API can be composed of APIs exposed by different services: OpenAPI Specification, SOAP API, API App,Function App, Logic App, Service Fabric.
To append a different API to your existing API, follow the steps below. Once you import another API, theoperations are appended to your current API.
1. Navigate to your APIM instance in the Azure portal.2. Select APIs from under API MANAGEMENT.3. Press ellipsis ". . ." next tp the API that you want to append another API to.4. Select Import from the drop-down menu.5. Select one of services from which you want to import an API.
Import an OpenAPI SpecificationImport a SOAP APIImport a SOAP API and convert to RESTImport an API AppImport a Function AppImport a Logic AppImport a Service Fabric appEdit an API
Next stepsTransform and protect a published API
Import an API App as an API12/4/2017 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
TIPTIP
Import and publish a back-end API
This article shows how to import an API App as an API. The article also shows how to test the APIM API.
In this article, you learn how to:
Import an API App as an APITest the API in the Azure portalTest the API in the Developer portal
Complete the following quickstart: Create an Azure API Management instanceMake sure there is an API App in your subscription. For more information, see [App Service Documentation][https://docs.microsoft.com/azure/app-service/]
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select APIs from under API MANAGEMENT.2. Select API App from the Add a new API list.
Test the new APIM API in the Azure portal
Call an operation from the developer portal
3. Press Browse to see the list of API Apps in your subscription.
5. Add an API URL suffix. The suffix is a name that identifies this specific API in this APIM instance. It has to beunique in this APIM instance.
7. Select Create.
!(API app)[./media/import-api-app-as-api/api-app.png]
4. Select the app. APIM finds the swagger associated with the selected app, fetches it, and imports it.
In case APIM does not find swagger, it exposes the API as a "pass-through" API.
6. Publish the API by associating the API with a product. In this case, the "Unlimited" product is used. If youwant for the API to be published and be available to developers, add it to a product. You can do it duringAPI creation or set it later.
Products are associations of one or more APIs. You can include a number of APIs and offer them todevelopers through the developer portal. Developers must first subscribe to a product to get access to theAPI. When they subscribe, they get a subscription key that is good for any API in that product. If youcreated the APIM instance, you are an administrator already, so you are subscribed to every product bydefault.
By default, each API Management instance comes with two sample products:
StarterUnlimited
Operations can be called directly from the Azure portal, which provides a convenient way to view and test theoperations of an API.
1. Select the API you created in the previous step.2. Press the Test tab.3. Select some operation.
The page displays fields for query parameters and fields for the headers. One of the headers is "Ocp-Apim-Subscription-Key", for the subscription key of the product that is associated with this API. If youcreated the APIM instance, you are an administrator already, so the key is filled in automatically.
4. Press Send.
Backend responds with 200 OK and some data.
Operations can also be called Developer portal to test APIs.
1. Select the API you created in the "Import and publish a back-end API" step.
3. Select the API that you created.4. Click the operation you want to test.5. Press Try it.
2. Press Developer portal.
The "Developer portal" site opens up.
6. Press Send.
After an operation is invoked, the developer portal displays the Response status, the Response headers,
Append other APIs
Related topics
Next steps
and any Response content.
An API can be composed of APIs exposed by different services: OpenAPI Specification, SOAP API, API App,Function App, Logic App, Service Fabric.
To append a different API to your existing API, follow the steps below. Once you import another API, theoperations are appended to your current API.
1. Navigate to your APIM instance in the Azure portal.2. Select APIs from under API MANAGEMENT.3. Press ellipsis ". . ." next tp the API that you want to append another API to.4. Select Import from the drop-down menu.5. Select one of services from which you want to import an API.
Import an OpenAPI SpecificationImport a SOAP APIImport a SOAP API and convert to RESTImport an API AppImport a Function AppImport a Logic AppImport a Service Fabric appEdit an API
Transform and protect a published API
Import a Function App as an API12/4/2017 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
TIPTIP
Import and publish a back-end API
This article shows how to import a Function App as an API. The article also shows how to test the APIM API.
In this article, you learn how to:
Import a Function App as an APITest the API in the Azure portalTest the API in the Developer portal
Complete the following quickstart: Create an Azure API Management instanceMake sure there is a Function App in your subscription. For more information, see Create a Function App
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select APIs from under API MANAGEMENT.2. Select Function App from the Add a new API list.
Test the new APIM API in the Azure portal
Call an operation from the developer portal
3. Press Browse to see the list of Function Apps in your subscription.4. Select the app. APIM finds the swagger associated with the selected app, fetches it, and imports it.5. Add an API URL suffix. The suffix is a name that identifies this specific API in this APIM instance. It has to be
unique in this APIM instance.
7. Select Create.
6. Publish the API by associating the API with a product. In this case, the "Unlimited" product is used. If youwant for the API to be published and be available to developers, add it to a product. You can do it duringAPI creation or set it later.
Products are associations of one or more APIs. You can include a number of APIs and offer them todevelopers through the developer portal. Developers must first subscribe to a product to get access to theAPI. When they subscribe, they get a subscription key that is good for any API in that product. If youcreated the APIM instance, you are an administrator already, so you are subscribed to every product bydefault.
By default, each API Management instance comes with two sample products:
StarterUnlimited
Operations can be called directly from the Azure portal, which provides a convenient way to view and test theoperations of an API.
1. Select the API you created in the previous step.2. Press the Test tab.3. Select some operation.
The page displays fields for query parameters and fields for the headers. One of the headers is "Ocp-Apim-Subscription-Key", for the subscription key of the product that is associated with this API. If youcreated the APIM instance, you are an administrator already, so the key is filled in automatically.
4. Press Send.
Backend responds with 200 OK and some data.
Operations can also be called Developer portal to test APIs.
1. Select the API you created in the "Import and publish a back-end API" step.
3. Select the API that you created.4. Click the operation you want to test.5. Press Try it.
2. Press Developer portal.
The "Developer portal" site opens up.
Append other APIs
Related topics
Next steps
6. Press Send.
After an operation is invoked, the developer portal displays the Response status, the Response headers,and any Response content.
An API can be composed of APIs exposed by different services: OpenAPI Specification, SOAP API, API App,Function App, Logic App, Service Fabric.
To append a different API to your existing API, follow the steps below. Once you import another API, theoperations are appended to your current API.
1. Navigate to your APIM instance in the Azure portal.2. Select APIs from under API MANAGEMENT.3. Press ellipsis ". . ." next tp the API that you want to append another API to.4. Select Import from the drop-down menu.5. Select one of services from which you want to import an API.
Import an OpenAPI SpecificationImport a SOAP APIImport a SOAP API and convert to RESTImport an API AppImport a Function AppImport a Logic AppImport a Service Fabric appEdit an API
Transform and protect a published API
Import a Logic App as an API1/19/2018 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
TIPTIP
Import and publish a back-end API
This article shows how to import a Logic App as an API. The article also shows how to test the APIM API.
In this article, you learn how to:
Import a Logic App as an APITest the API in the Azure portalTest the API in the Developer portal
Complete the following quickstart: Create an Azure API Management instanceMake sure there is a Logic App in your subscription. For more information, Create your first Logic App
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
1. Select APIs from under API MANAGEMENT.2. Select Logic App from the Add a new API list.
Test the new APIM API in the Azure portal
Call an operation from the developer portal
3. Press Browse to see the list of Logic Apps in your subscription.4. Select the app. APIM finds the swagger associated with the selected app, fetches it, and imports it.5. Add an API URL suffix. The suffix is a name that identifies this specific API in this APIM instance. It has to be
unique in this APIM instance.
7. Select Create.
6. Publish the API by associating the API with a product. In this case, the "Unlimited" product is used. If youwant for the API to be published and be available to developers, add it to a product. You can do it duringAPI creation or set it later.
Products are associations of one or more APIs. You can include a number of APIs and offer them todevelopers through the developer portal. Developers must first subscribe to a product to get access to theAPI. When they subscribe, they get a subscription key that is good for any API in that product. If youcreated the APIM instance, you are an administrator already, so you are subscribed to every product bydefault.
By default, each API Management instance comes with two sample products:
StarterUnlimited
Operations can be called directly from the Azure portal, which provides a convenient way to view and test theoperations of an API.
1. Select the API you created in the previous step.2. Press the Test tab.3. Select some operation.
The page displays fields for query parameters and fields for the headers. One of the headers is "Ocp-Apim-Subscription-Key", for the subscription key of the product that is associated with this API. If youcreated the APIM instance, you are an administrator already, so the key is filled in automatically.
4. Press Send.
Backend responds with 200 OK and some data.
Operations can also be called Developer portal to test APIs.
1. Select the API you created in the "Import and publish a back-end API" step.
3. Select the API that you created.4. Click the operation you want to test.5. Press Try it.
2. Press Developer portal.
The "Developer portal" site opens up.
Append other APIs
NOTENOTE
Related topics
Next steps
6. Press Send.
After an operation is invoked, the developer portal displays the Response status, the Response headers,and any Response content.
An API can be composed of APIs exposed by different services: OpenAPI Specification, SOAP API, API App,Function App, Logic App, Service Fabric.
To append a different API to your existing API, follow the steps below. Once you import another API, theoperations are appended to your current API.
1. Navigate to your APIM instance in the Azure portal.2. Select APIs from under API MANAGEMENT.3. Press ellipsis ". . ." next tp the API that you want to append another API to.4. Select Import from the drop-down menu.5. Select one of services from which you want to import an API.
Every Logic App has manual-invoke operation. If you want to comprise your API of multiple logic apps, in order not tohave collision, you need to rename the function.
Import an OpenAPI SpecificationImport a SOAP APIImport a SOAP API and convert to RESTImport an API AppImport a Function AppImport a Logic AppImport a Service Fabric appEdit an API
Transform and protect a published API
Tutorial: deploy API Management with Service Fabric3/9/2018 • 12 min to read • Edit Online
Prerequisites
Network topology
This tutorial is part four of a series. Deploying Azure API Management with Service Fabric is an advanced scenario.API Management is useful when you need to publish APIs with a rich set of routing rules for your back-end ServiceFabric services. Cloud applications typically need a front-end gateway to provide a single point of ingress for users,devices, or other applications. In Service Fabric, a gateway can be any stateless service designed for traffic ingresssuch as an ASP.NET Core application, Event Hubs, IoT Hub, or Azure API Management.
This tutorial shows you how to set up Azure API Management with Service Fabric to route traffic to a back-endservice in Service Fabric. When you're finished, you have deployed API Management to a VNET, configured an APIoperation to send traffic to back-end stateless services. To learn more about Azure API Management scenarios withService Fabric, see the overview article.
In this tutorial, you learn how to:
Deploy API ManagementConfigure API ManagementCreate an API operationConfigure a backend policyAdd the API to a product
In this tutorial series you learn how to:
Create a secure Windows cluster or Linux cluster on Azure using a templateScale a cluster in or outUpgrade the runtime of a clusterDeploy API Management with Service Fabric
Before you begin this tutorial:
If you don't have an Azure subscription, create a free accountInstall the Azure Powershell module version 4.1 or higher or Azure CLI 2.0.Create a secure Windows cluster or Linux cluster on AzureIf you deploy a Windows cluster, set up a Windows development environment. Install Visual Studio 2017 andthe Azure development, ASP.NET and web development, and .NET Core cross-platform developmentworkloads. Then set up a .NET development environment.If you deploy a Linux cluster, set up a Java development environment on Linux or MacOS. Install the ServiceFabric CLI.
Now that you have a secure Windows cluster or Linux cluster on Azure, deploy API Management to the virtualnetwork (VNET) in the subnet and NSG designated for API Management. For this tutorial, the API ManagementResource Manager template is pre-configured to use the names of the VNET, subnet, and NSG that you set up inthe previous Windows cluster tutorial or Linux cluster tutorial. This tutorial deploys the following topology to Azurein which API Management and Service Fabric are in subnets of the same Virtual Network:
Sign in to Azure and select your subscription
Login-AzureRmAccountGet-AzureRmSubscriptionSet-AzureRmContext -SubscriptionId <guid>
az loginaz account set --subscription <guid>
Deploy a Service Fabric back-end service
Deploy a .NET Service Fabric serviceDeploy a .NET Service Fabric service
Sign in to your Azure account select your subscription before you execute Azure commands.
Before configuring API Management to route traffic to a Service Fabric back-end service, first you need a runningservice to accept requests. If you previously created a Windows cluster, deploy a .NET Service Fabric service. If youpreviously created a Linux cluster, deploy a Java Service Fabric service.
For this tutorial, create a basic stateless ASP.NET Core Reliable Service using the default Web API project template.This creates an HTTP endpoint for your service, which you expose through Azure API Management.
Start Visual Studio as Administrator and create an ASP.NET Core service:
1. In Visual Studio, select File -> New Project.2. Select the Service Fabric Application template under Cloud and name it "ApiApplication".3. Select the stateless ASP.NET Core service template and name the project "WebApiService".4. Select the Web API ASP.NET Core 2.0 project template.5. Once the project is created, open PackageRoot\ServiceManifest.xml and remove the Port attribute from the
endpoint resource configuration:
Create a Java Service Fabric serviceCreate a Java Service Fabric service
<Resources> <Endpoints> <Endpoint Protocol="http" Name="ServiceEndpoint" Type="Input" /> </Endpoints></Resources>
["value1", "value2"]`
Removing the port allows Service Fabric to specify a port dynamically from the application port range,opened through the Network Security Group in the cluster Resource Manager template, allowing traffic toflow to it from API Management.
6. Press F5 in Visual Studio to verify the web API is available locally.
Open Service Fabric Explorer and drill down to a specific instance of the ASP.NET Core service to see thebase address the service is listening on. Add /api/values to the base address and open it in a browser,which invokes the Get method on the ValuesController in the Web API template. It returns the defaultresponse that is provided by the template, a JSON array that contains two strings:
This is the endpoint that you expose through API Management in Azure.
7. Finally, deploy the application to your cluster in Azure. In Visual Studio, right-click the Application projectand select Publish. Provide your cluster endpoint (for example, mycluster.southcentralus.cloudapp.azure.com:19000 ) to deploy the application to your Service Fabric cluster
in Azure.
An ASP.NET Core stateless service named fabric:/ApiApplication/WebApiService should now be running in yourService Fabric cluster in Azure.
For this tutorial deploy a basic web server, which echoes messages back to the user. The echo server sampleapplication contains an HTTP endpoint for your service, which you expose through Azure API Management.
git clone https://github.com/Azure-Samples/service-fabric-java-getting-started.gitcd service-fabric-java-getting-started/reliable-services-actor-sample
<Endpoint Name="WebEndpoint" Protocol="http" Port="8081" />
cd Services/EchoServer/EchoServer1.0/gradle
1. Clone the Java getting started samples.
2. Edit Services/EchoServer/EchoServer1.0/EchoServerApplication/EchoServerPkg/ServiceManifest.xml.Update the endpoint so the service listens on port 8081.
3. Save ServiceManifest.xml, then build the EchoServer1.0 application.
4. Deploy the application to the cluster.
Download and understand the Resource Manager templates
Microsoft.ApiManagement/serviceMicrosoft.ApiManagement/service
Microsoft.ApiManagement/service/certificatesMicrosoft.ApiManagement/service/certificates
Microsoft.ApiManagement/service/backendsMicrosoft.ApiManagement/service/backends
Microsoft.ApiManagement/service/productsMicrosoft.ApiManagement/service/products
cd Scriptssfctl cluster select --endpoint https://mycluster.southcentralus.cloudapp.azure.com:19080 --pem <full_path_to_pem_on_dev_machine> --no-verify./install.sh
A Java stateless service named fabric:/EchoServerApplication/EchoServerService should now be running inyour Service Fabric cluster in Azure.
5. Open a browser and type in http://mycluster.southcentralus.cloudapp.azure.com:8081/getMessage, youshould see "[version 1.0]Hello World!!!" displayed.
Download and save the following Resource Manager templates and parameters file:
network-apim.jsonnetwork-apim.parameters.jsonapim.jsonapim.parameters.json
The network-apim.json template deploys a new subnet and network security group in the virtual network where theService Fabric cluster is deployed.
The following sections describe the resources being defined by the apim.json template. For more information,follow the links to the template reference documentation within each section. The configurable parameters definedin the apim.parameters.json parameters file are set later in this article.
Microsoft.ApiManagement/service describes the API Management service instance: name, SKU or tier, resourcegroup location, publisher information, and virtual network.
Microsoft.ApiManagement/service/certificates configures API Management security. API Management mustauthenticate with your Service Fabric cluster for service discovery using a client certificate that has access to yourcluster. This tutorial uses the same certificate specified previously when creating the Windows cluster or Linuxcluster, which by default can be used to access your cluster.
This tutorial uses the same certificate for client authentication and cluster node-to-node security. You may use aseparate client certificate if you have one configured to access your Service Fabric cluster. Provide the name,password, and data (base-64 encoded string) of the private key file (.pfx) of the cluster certificate that you specifiedwhen creating your Service Fabric cluster.
Microsoft.ApiManagement/service/backends describes the backend service that traffic is forwarded to.
For Service Fabric backends, the Service Fabric cluster is the backend instead of a specific Service Fabric service.This allows a single policy to route to more than one service in the cluster. The url field here is a fully qualifiedservice name of a service in your cluster that all requests are routed to by default if no service name is specified in abackend policy. You may use a fake service name, such as "fabric:/fake/service" if you do not intend to have afallback service. resourceId specifies the cluster management endpoint. clientCertificateThumbprint andserverCertificateThumbprints identify certificates used to authenticate with the cluster.
Microsoft.ApiManagement/service/products creates a product. In Azure API Management, a product contains oneor more APIs as well as a usage quota and the terms of use. Once a product is published, developers can subscribe
Microsoft.ApiManagement/service/apisMicrosoft.ApiManagement/service/apis
Microsoft.ApiManagement/service/apis/operationsMicrosoft.ApiManagement/service/apis/operations
Microsoft.ApiManagement/service/apis/policiesMicrosoft.ApiManagement/service/apis/policies
to the product and begin to use the product's APIs.
Enter a descriptive displayName and description for the product. For this tutorial, a subscription is required butsubscription approval by an admin is not. This product state is "published" and is visible to subscribers.
Microsoft.ApiManagement/service/apis creates an API. An API in API Management represents a set of operationsthat can be invoked by client applications. Once the operations are added, the API is added to a product and can bepublished. Once an API is published, it can be subscribed to and used by developers.
displayName can be any name for your API. For this tutorial, use "Service Fabric App".name provides a unique and descriptive name for the API, such as "service-fabric-app". It is displayed in thedeveloper and publisher portals.serviceUrl references the HTTP service implementing the API. API management forwards requests to thisaddress. For Service Fabric backends, this URL value is not used. You can put any value here. For this tutorial,for example "http://servicefabric".path is appended to the base URL for the API management service. The base URL is common for all APIshosted by an API Management service instance. API Management distinguishes APIs by their suffix andtherefore the suffix must be unique for every API for a given publisher.protocols determine which protocols can be used to access the API. For this tutorial, list http and https.path is a suffix for the API. For this tutorial, use "myapp".
Microsoft.ApiManagement/service/apis/operations Before an API in API Management can be used, operationsmust be added to the API. External clients use an operation to communicate with the ASP.NET Core statelessservice running in the Service Fabric cluster.
To add a front-end API operation, fill out the values:
displayName and description describe the operation. For this tutorial, use "Values".method specifies the HTTP verb. For this tutorial, specify GET.urlTemplate is appended to the base URL of the API and identifies a single HTTP operation. For this tutorial,use /api/values if you added the .NET backend service or getMessage if you added the Java backend service.By default, the URL path specified here is the URL path sent to the backend Service Fabric service. If you use thesame URL path here that your service uses, such as "/api/values", then the operation works without furthermodification. You may also specify a URL path here that is different from the URL path used by your backendService Fabric service, in which case you also need to specify a path rewrite in your operation policy later.
Microsoft.ApiManagement/service/apis/policies creates a backend policy, which ties everything together. This iswhere you configure the backend Service Fabric service to which requests are routed. You can apply this policy toany API operation. For more information, see Policies overview.
The backend configuration for Service Fabric provides the following request routing controls:
Service instance selection by specifying a Service Fabric service instance name, either hardcoded (for example, "fabric:/myapp/myservice" ) or generated from the HTTP request (for example, "fabric:/myapp/users/" + context.Request.MatchedParameters["name"] ).
Partition resolution by generating a partition key using any Service Fabric partitioning scheme.Replica selection for stateful services.Resolution retry conditions that allow you to specify the conditions for re-resolving a service location andresending a request.
policyContent is the Json escaped XML contents of the policy. For this tutorial, create a backend policy to route
<policies> <inbound> <base/> <set-backend-service backend-id="servicefabric" sf-service-instance-name="service-name" sf-resolve-condition="@((int)context.Response.StatusCode != 200)" /> </inbound> <backend> <base/> </backend> <outbound> <base/> </outbound></policies>
Set parameters and deploy API Management
PARAMETER VALUE
apimInstanceName sf-apim
apimPublisherEmail [email protected]
apimSku Developer
serviceFabricCertificateName sfclustertutorialgroup320171031144217
certificatePassword q6D7nN%6ck@6
serviceFabricCertificateThumbprint C4C1E541AD512B8065280292A8BA6079C3F26F10
serviceFabricCertificate <base-64 encoded string>
url_path /api/values
clusterHttpManagementEndpoint https://mysfcluster.southcentralus.cloudapp.azure.com:19080
inbound_policy <XML string>
requests directly to the .NET or Java stateless service deployed earlier. Add a set-backend-service policy underinbound policies. Replace the sf-service-instance-name value with fabric:/ApiApplication/WebApiService if youpreviously deployed the .NET backend service, or fabric:/EchoServerApplication/EchoServerService if you deployedthe Java service. backend-id references a backend resource, in this case the Microsoft.ApiManagement/service/backends resource defined in the apim.json template. backend-id can also
reference another backend resource created using the API Management APIs. For this tutorial, set backend-id tothe value of the service_fabric_backend_name parameter.
For a full set of Service Fabric back-end policy attributes, refer to the API Management back-end documentation
Fill in the following empty parameters in the apim.parameters.json for your deployment.
certificatePassword and serviceFabricCertificateThumbprint must match the cluster certificate used to set up thecluster.
serviceFabricCertificate is the certificate as a base-64 encoded string, which can be generated using the following
$bytes = [System.IO.File]::ReadAllBytes("C:\mycertificates\sfclustertutorialgroup220171109113527.pfx");$b64 = [System.Convert]::ToBase64String($bytes);[System.Io.File]::WriteAllText("C:\mycertificates\sfclustertutorialgroup220171109113527.txt", $b64);
<policies> <inbound> <base/> <set-backend-service backend-id="servicefabric" sf-service-instance-name="service-name" sf-resolve-condition="@((int)context.Response.StatusCode != 200)" /> </inbound> <backend> <base/> </backend> <outbound> <base/> </outbound></policies>
$groupname = "sfclustertutorialgroup"$clusterloc="southcentralus"$templatepath="C:\clustertemplates"
New-AzureRmResourceGroupDeployment -ResourceGroupName $groupname -TemplateFile "$templatepath\network-apim.json" -TemplateParameterFile "$templatepath\network-apim.parameters.json" -Verbose
New-AzureRmResourceGroupDeployment -ResourceGroupName $groupname -TemplateFile "$templatepath\apim.json" -TemplateParameterFile "$templatepath\apim.parameters.json" -Verbose
ResourceGroupName="sfclustertutorialgroup"az group deployment create --name ApiMgmtNetworkDeployment --resource-group $ResourceGroupName --template-file network-apim.json --parameters @network-apim.parameters.json
az group deployment create --name ApiMgmtDeployment --resource-group $ResourceGroupName --template-file apim.json --parameters @apim.parameters.json
Test it
script:
In inbound_policy, replace the sf-service-instance-name value with fabric:/ApiApplication/WebApiService if youpreviously deployed the .NET backend service, or fabric:/EchoServerApplication/EchoServerService if you deployedthe Java service. backend-id references a backend resource, in this case the Microsoft.ApiManagement/service/backends resource defined in the apim.json template. backend-id can also
reference another backend resource created using the API Management APIs. For this tutorial, set backend-id tothe value of the service_fabric_backend_name parameter.
Use the following script to deploy the Resource Manager template and parameter files for API Management:
You can now try sending a request to your back-end service in Service Fabric through API Management directlyfrom the Azure portal.
1. In the API Management service, select API.2. In the Service Fabric App API you created in the previous steps, select the Test tab and then the Values
operation.3. Click the Send button to send a test request to the backend service. You should see an HTTP response
["value1", "value2"]```
Clean up resources
$ResourceGroupName = "sfclustertutorialgroup"Remove-AzureRmResourceGroup -Name $ResourceGroupName -Force
ResourceGroupName="sfclustertutorialgroup"az group delete --name $ResourceGroupName
Next steps
HTTP/1.1 200 OK
Transfer-Encoding: chunked
Content-Type: application/json; charset=utf-8
Vary: Origin
Ocp-Apim-Trace-Location: https://apimgmtstodhwklpry2xgkdj.blob.core.windows.net/apiinspectorcontainer/PWSQOq_FCDjGcaI1rdMn8w2-2?sv=2015-07-08&sr=b&sig=MhQhzk%2FEKzE5odlLXRjyVsgzltWGF8OkNzAKaf0B1P0%3D&se=2018-01-28T01%3A04%3A44Z&sp=r&traceId=9f8f1892121e445ea1ae4d2bc8449ce4
Date: Sat, 27 Jan 2018 01:04:44 GMT
similar to:
A cluster is made up of other Azure resources in addition to the cluster resource itself. The simplest way to deletethe cluster and all the resources it consumes is to delete the resource group.
Log in to Azure and select the subscription ID with which you want to remove the cluster. You can find yoursubscription ID by logging in to the Azure portal. Delete the resource group and all the cluster resources using theRemove-AzureRMResourceGroup cmdlet.
In this tutorial, you learned how to:
Deploy API ManagementConfigure API ManagementCreate an API operationConfigure a backend policyAdd the API to a product
Edit an API12/4/2017 • 1 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
TIPTIP
Edit an API in APIM
The steps in this tutorial show you how to use API Management (APIM) to edit an API.
You can do it by adding, deleting, renaming operations in the APIM instance.You can edit your API's swagger.
Create an Azure API Management instanceImport and publish your first API
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
Update the swagger
1. Click the APIs tab.2. Select one of the APIs that you previously imported.3. Select the Design tab.4. Select an operation, which you want to edit.5. To rename the operation, select a pencil in the Frontend window.
You can update your backbend API from the Azure portal by following these steps:
1. Select All operations2. Click pencil in the Frontend window.
Your API's swagger appears.
Related topics
Next steps
4. Press Save.
3. Update the swagger.
Import an OpenAPI SpecificationImport a SOAP APIImport a SOAP API and convert to RESTImport an API AppImport a Function AppImport a Logic AppImport a Service Fabric appEdit an API
APIM policy samples Transform and protect a published API
Upgrade and scale an API Management instance12/12/2017 • 4 min to read • Edit Online
NOTENOTE
Prerequisites
How to plan for capacity?
Use the Azure portal to examine metricsUse the Azure portal to examine metrics
Customers can scale an API Management (APIM) instance by adding and removing units. A unit is composed ofdedicated Azure resources and has a certain load-bearing capacity expressed as a number of API calls per month.This number does not represent a call limit, but rather a maximum throughput value to allow for rough capacityplanning. Actual throughput and latency vary broadly depending on factors such as number and rate ofconcurrent connections, the kind and number of configured policies, request and response sizes, and backendlatency.
Capacity and price of each unit depends on the tier in which the unit exists. You can choose between four tiers:Developer, Basic, Standard, Premium. If you need to increase capacity for a service within a tier, you should adda unit. If the tier that is currently selected in your APIM instance does not allow adding more units, you need toupgrade to a higher-level tier.
The price of each unit and the available features (for example, multi-region deployment) depends on the tier thatyou chose for your APIM instance. The pricing details article, explains the price per unit and features you get ineach tier.
The pricing details article shows approximate numbers of unit capacity in each tier. To get more accurate numbers, you needto look at a realistic scenario for your APIs. See the "How to plan for capacity" section that follows.
To perform the steps described in this article, you must have:
An active Azure subscription.
If you don't have an Azure subscription, create a free account before you begin.
An APIM instance. For more information, see Create an Azure API Management instance.
To find out if you have enough units to handle your traffic, test on workloads that you expect.
As mentioned above, the number of requests per second an APIM unit can process depends on many variables.For example, the connection pattern, the size of the request and response, policies that are configured on each API,number of clients that are sending requests.
Use Metrics (uses Azure Monitor capabilities) to understand how much capacity is used at any given time.
1. Navigate to your APIM instance in the Azure portal.2. Select Metrics.3. Select Capacity metric from Available metrics.
The capacity metric gives you some idea of how much of the available compute capacity is being used inyour tenant. Its value is derived from the compute resources used by your tenant such as memory, CPU,and network queue lengths. It is not a direct measure of the number of requests being processed. You can
Upgrade and scale
NOTENOTE
Use the Azure portal to upgrade and scaleUse the Azure portal to upgrade and scale
Next steps
TIPTIP
test by increasing the request load on your tenant and monitoring what value of the capacity metriccorresponds to your peak load. You can set a metric alert to let you know when something unexpected ishappening. For example, your APIM instance has exceeded its expected peak capacity for over 10 minutes.
You can configure alerts to let you know when your service is running low on capacity or call into a logic app thatautomatically scale by adding a unit.
As mentioned previously, you can choose between four tiers: Developer, Basic, Standard and Premium. TheDeveloper tier should be used to evaluate the service; it should not be used for production. The Developer tierdoes not have SL A and you cannot scale this tier (add/remove units).
Basic, Standard and Premium are production tiers that have SL A and can be scaled. The Basic tier is thecheapest tier which has SL A and it can be scaled upto 2 units, Standard tier can be scaled to up to four units. Youcan add any number of units to the Premium tier.
The Premium tier enables you to distribute a single API management instance across any number of desiredAzure regions. When you initially create an API Management service, the instance contains only one unit andresides in a single Azure region. The initial region is designated as the primary region. Additional regions can beeasily added. When adding a region, you specify the number of units you want to allocate. For example, you canhave one unit in the primary region and five units in some other region. You can tailor the number of units to thetraffic you have in each region. For more information, see How to deploy an Azure API Management serviceinstance to multiple Azure regions.
You can upgrade and downgrade to and from any tier. Note that upgrading or downgrading can remove somefeatures - for example, VNETs or multi-region deployment, when downgrading to Standard or Basic from thePremium tier.
The upgrade or scale process can take from 15 to 45 minutes to apply. You get notification when it is done.
1. Navigate to your APIM instance in the Azure portal.2. Select Scale and pricing.3. Pick the desired tier.4. Specify the number of units you want to add. You can either use the slider or type the number of units.
If you choose the Premium tier, you first need to select a region.5. Press Save
How to deploy an Azure API Management service instance to multiple Azure regions
Configure a custom domain name2/13/2018 • 3 min to read • Edit Online
WARNINGWARNING
Prerequisites
Use the Azure portal to set a custom domain name
When you create an API Management (APIM) instance, Azure assigns it to a subdomain of azure-api.net (forexample, apim-service-name.azure-api.net ). However, you can expose your APIM endpoints using your owndomain name, such as contoso.com. This tutorial shows you how to map an existing custom DNS name toendpoints exposed by an Azure API Management instance.
Customers who wish to use certificate pinning to improve the security of their applications must use a custom domain name> and certificate which they manage, not the default certificate. Customers that pin the default certificate instead will be >taking a hard dependency on the properties of the certificate they don't control, which is not a recommended practice.
To perform the steps described in this article, you must have:
A custom domain name that is owned by you. The custom domain name you want to use, must be procuredseparately and hosted on a DNS server. This topic does not give instructions on how to host a custom domainname.You must have a valid certificate with a public and private key (.PFX). Subject or subject alternative name (SAN)has to match the domain name (this enables APIM to securely expose URLs over SSL).
An active Azure subscription.
If you don't have an Azure subscription, create a free account before you begin.
An APIM instance. For more information, see Create an Azure API Management instance.
1. Navigate to your APIM instance in the Azure portal.2. Select Custom domains and SSL.
There is a number of endpoints to which you can assign a custom domain name. Currently, the followingendpoints are available:
Proxy (default is: <apim-service-name>.azure-api.net ),Portal (default is: <apim-service-name>.portal.azure-api.net ),Management (default is: <apim-service-name>.management.azure-api.net ),
NOTENOTE
SCM (default is: <apim-service-name>.scm.azure-api.net ).
You can update all of the endpoints or some of them. Commonly, customers update Proxy (this URL is usedto call the API exposed through API Management) and Portal (the developer portal URL). Management andSCM endpoints are used internally by APIM customers and thus are less frequently assigned a customdomain name.
How APIM Proxy Server responds with SSL certificates in the TLShandshakeClients calling with SNI headerClients calling with SNI header
Clients calling without SNI headerClients calling without SNI header
Support for PUT/POST request with large payload
Next steps
3. Select the endpoint that you want to update.
NOTENOTE
4. In the window on the right, click Custom.
In the Custom domain name, specify the name you want to use. For example, api.contoso.com . Wildcard domain names (for example, *.domain.com) are also supported.In the Certificate, specify a valid .PFX file that you want to upload.If the certificate has a password, enter it in the Password field.
5. Click Apply.
The process of assigning the certificate may take 15 minutes or more depending on size of deployment. DeveloperSKU has downtime, Basic and higher SKU's do not have downtime.
If the customer has one or multiple custom domains configured for Proxy, APIM can respond to HTTPS requestsfrom the custom domain(s) (for example, contoso.com) as well as default domain (for example, apim-service-name.azure-api.net). Based on the information in the Server Name Indication (SNI) header, APIM responds withappropriate server certificate.
If the customer is using a client, which does not send the SNI header, APIM creates responses based on thefollowing logic:
If the service has just one custom domain configured for Proxy, the Default Certificate is the certificate that wasissued to the Proxy custom domain.If the service has configured multiple custom domains for Proxy (only supported in the Premium tier), thecustomer can designate which certificate should be the default certificate. To set the default certificate, thedefaultSslBinding property should be set to true ("defaultSslBinding":"true"). If the customer does not set theproperty, the default certificate is the certificate issued to default Proxy domain hosted at *.azure-api.net.
APIM Proxy server supports request with large payload when using client-side certificates in HTTPS (for example,payload > 40 KB). To prevent the server's request from freezing, customers can set the property"negotiateClientCertificate": "true" on the Proxy hostname. If the property is set to true, the client certificate isrequested at SSL/TLS connection time, before any HTTP request exchange. Since the setting applies at the ProxyHostname level, all connection requests ask for the client certificate. Customers can configure up to 20 customdomains for Proxy (only supported in the Premium tier) and work around this limitation.
Upgrade and scale your service
Add caching to improve performance in Azure APIManagement12/4/2017 • 1 min to read • Edit Online
Prerequisites
Add the caching policies
Operations in API Management can be configured for response caching. Response caching can significantly reduceAPI latency, bandwidth consumption, and web service load for data that does not change frequently.
For more detailed information about caching, see API Management caching policies and Custom caching in AzureAPI Management.
What you'll learn:
Add response caching for your APIVerify caching in action
To complete this tutorial:
Create an Azure API Management instanceImport and publish an API
With caching policies shown in this example, the first request to the GetSpeakers operation returns a responsefrom the backend service. This response is cached, keyed by the specified headers and query string parameters.Subsequent calls to the operation, with matching parameters, will have the cached response returned, until thecache duration interval has expired.
Call an operation and test the caching
1. Sign in to the Azure portal at https://portal.azure.com.2. Browse to your APIM instance.3. Select the API tab.4. Click Demo Conference API from your API list.5. Select GetSpeakers.6. On the top of the screen, select Design tab.
8. Select Code editor.
<cache-lookup vary-by-developer="false" vary-by-developer-groups="false"> <vary-by-header>Accept</vary-by-header> <vary-by-header>Accept-Charset</vary-by-header> <vary-by-header>Authorization</vary-by-header> </cache-lookup>
<cache-store caching-mode="cache-on" duration="20" />
7. In the Inbound processing window, click the triangle (next to the pencil).
9. In the inbound element, add the following policy:
10. In the outbound element, add the following policy:
Duration specifies the expiration interval of the cached responses. In this example, the interval is 20seconds.
To see the caching in action, call the operation from the developer portal.
Next steps
1. In the Azure portal, browse to your APIM instance.2. Select the APIs tab.3. Select the API to which you added caching policies.4. Select the GetSpeakers operation.5. Click the Test tab in the top right menu.6. Press Send.
For more information about caching policies, see Caching policies in the API Management policy reference.For information on caching items by key using policy expressions, see Custom caching in Azure APIManagement.
Protect an API by using OAuth 2.0 with Azure ActiveDirectory and API Management4/9/2018 • 6 min to read • Edit Online
Prerequisites
Overview
Register an application in Azure AD to represent the API
Register another application in Azure AD to represent a clientapplication
This guide shows you how to configure your Azure API Management instance to protect an API, by using theOAuth 2.0 protocol with Azure Active Directory (Azure AD).
To follow the steps in this article, you must have:
An API Management instanceAn API being published that uses the API Management instanceAn Azure AD tenant
Here is a quick overview of the steps:
1. Register an application (backend-app) in Azure AD to represent the API.2. Register another application (client-app) in Azure AD to represent a client application that needs to call the API.3. In Azure AD, grant permissions to allow the client-app to call the backend-app.4. Configure the Developer Console to use OAuth 2.0 user authorization.5. Add the validate-jwt policy to validate the OAuth token for every incoming request.
To protect an API with Azure AD, the first step is to register an application in Azure AD that represents the API.
1. Browse to your Azure AD tenant, and then browse to App registrations.
2. Select New application registration.
3. Provide a name of the application. (For this example, the name is backend-app .)
4. Choose Web app / API as the Application type.
5. For Sign-on URL, you can use https://localhost as a placeholder.
6. Select Create.
When the application is created, make a note of the Application ID , for use in a subsequent step.
Every client application that calls the API needs to be registered as an application in Azure AD as well. For thisexample, the sample client application is the Developer Console in the API Management developer portal. Here'show to register another application in Azure AD to represent the Developer Console.
1. Select New application registration.
Grant permissions in Azure AD
NOTENOTE
Enable OAuth 2.0 user authorization in the Developer Console
2. Provide a name of the application. (For this example, the name is client-app .)
3. Choose Web app / API as the Application type.
4. For Sign-on URL, you can use https://localhost as a placeholder, or use the sign-in URL of your APIManagement instance. (For this example, the URL is https://contoso5.portal.azure-api.net/signin .)
5. Select Create.
When the application is created, make a note of the Application ID , for use in a subsequent step.
Now, create a client secret for this application, for use in a subsequent step.
1. Select Settings again, and go to Keys.
2. Under Passwords, provide a Key description. Choose when the key should expire, and select Save.
Make a note of the key value.
Now that you have registered two applications to represent the API and the Developer Console, you need to grantpermissions to allow the client-app to call the backend-app.
1. Browse to Application registrations.
2. Select client-app , and go to Settings.
3. Select Required permissions > Add.
4. Select Select an API, and search for backend-app .
5. Under Delegated Permissions, select Access backend-app .
6. Select Select, and then select Done.
If Azure Active Directory is not listed under permissions to other applications, select Add to add it from the list.
At this point, you have created your applications in Azure AD, and have granted proper permissions to allow theclient-app to call the backend-app.
In this example, the Developer Console is the client-app. The following steps describe how to enable OAuth 2.0user authorization in the Developer Console.
1. Browse to your API Management instance.
2. Select OAuth 2.0 > Add.
3. Provide a Display name and Description.
4. For the Client registration page URL, enter a placeholder value, such as http://localhost . The Clientregistration page URL points to the page that users can use to create and configure their own accounts forOAuth 2.0 providers that support this. In this example, users do not create and configure their ownaccounts, so you use a placeholder instead.
5. For Authorization grant types, select Authorization code.
Successfully call the API from the developer portal
6. Specify the Authorization endpoint URL and Token endpoint URL. Retrieve these values from theEndpoints page in your Azure AD tenant. Browse to the App registrations page again, and selectEndpoints.
7. Copy the OAuth 2.0 Authorization Endpoint, and paste it into the Authorization endpoint URL textbox.
8. Copy the OAuth 2.0 Token Endpoint, and paste it into the Token endpoint URL text box. In addition topasting in the token endpoint, add a body parameter named resource. For the value of this parameter, usethe Application ID for the back-end app.
9. Next, specify the client credentials. These are the credentials for the client-app.
10. For Client ID , use the Application ID for the client-app.
11. For Client secret, use the key you created for the client-app earlier.
12. Immediately following the client secret is the redirect_url for the authorization code grant type. Make anote of this URL.
13. Select Create.
14. Go back to the Settings page of your client-app.
15. Select Reply URLs, and paste the redirect_url in the first row. In this example, you replaced https://localhost with the URL in the first row.
Now that you have configured an OAuth 2.0 authorization server, the Developer Console can obtain access tokensfrom Azure AD.
The next step is to enable OAuth 2.0 user authorization for your API. This enables the Developer Console to knowthat it needs to obtain an access token on behalf of the user, before making calls to your API.
1. Browse to your API Management instance, and go to APIs.
2. Select the API you want to protect. In this example, you use the Echo API .
3. Go to Settings.
4. Under Security, choose OAuth 2.0, and select the OAuth 2.0 server you configured earlier.
5. Select Save.
Now that the OAuth 2.0 user authorization is enabled on the Echo API , the Developer Console obtains an accesstoken on behalf of the user, before calling the API.
1. Browse to any operation under the Echo API in the developer portal, and select Try it. This brings you tothe Developer Console.
2. Note a new item in the Authorization section, corresponding to the authorization server you just added.
3. Select Authorization code from the authorization drop-down list, and you are prompted to sign in to theAzure AD tenant. If you are already signed in with the account, you might not be prompted.
4. After successful sign-in, an Authorization header is added to the request, with an access token from AzureAD. The following is a sample token (Base64 encoded):
Configure a JWT validation policy to pre-authorize requests
<validate-jwt header-name="Authorization" failed-validation-httpcode="401" failed-validation-error-message="Unauthorized. Access token is missing or invalid."> <openid-config url="https://login.microsoftonline.com/{aad-tenant}/.well-known/openid-configuration" /> <required-claims> <claim name="aud"> <value>{Application ID of backend-app}</value> </claim> </required-claims></validate-jwt>
Build an application to call the API
Next steps
Authorization: Bearer eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6IlNTUWRoSTFjS3ZoUUVEU0p4RTJnR1lzNDBRMCIsImtpZCI6IlNTUWRoSTFjS3ZoUUVEU0p4RTJnR1lzNDBRMCJ9.eyJhdWQiOiIxYzg2ZWVmNC1jMjZkLTRiNGUtODEzNy0wYjBiZTEyM2NhMGMiLCJpc3MiOiJodHRwczovL3N0cy53aW5kb3dzLm5ldC80NDc4ODkyMC05Yjk3LTRmOGItODIwYS0yMTFiMTMzZDk1MzgvIiwiaWF0IjoxNTIxMTUyNjMzLCJuYmYiOjE1MjExNTI2MzMsImV4cCI6MTUyMTE1NjUzMywiYWNyIjoiMSIsImFpbyI6IkFWUUFxLzhHQUFBQUptVzkzTFd6dVArcGF4ZzJPeGE1cGp2V1NXV1ZSVnd1ZXZ5QU5yMlNkc0tkQmFWNnNjcHZsbUpmT1dDOThscUJJMDhXdlB6cDdlenpJdzJLai9MdWdXWWdydHhkM1lmaDlYSGpXeFVaWk9JPSIsImFtciI6WyJyc2EiXSwiYXBwaWQiOiJhYTY5ODM1OC0yMWEzLTRhYTQtYjI3OC1mMzI2NTMzMDUzZTkiLCJhcHBpZGFjciI6IjEiLCJlbWFpbCI6Im1pamlhbmdAbWljcm9zb2Z0LmNvbSIsImZhbWlseV9uYW1lIjoiSmlhbmciLCJnaXZlbl9uYW1lIjoiTWlhbyIsImlkcCI6Imh0dHBzOi8vc3RzLndpbmRvd3MubmV0LzcyZjk4OGJmLTg2ZjEtNDFhZi05MWFiLTJkN2NkMDExZGI0Ny8iLCJpcGFkZHIiOiIxMzEuMTA3LjE3NC4xNDAiLCJuYW1lIjoiTWlhbyBKaWFuZyIsIm9pZCI6IjhiMTU4ZDEwLWVmZGItNDUxMS1iOTQzLTczOWZkYjMxNzAyZSIsInNjcCI6InVzZXJfaW1wZXJzb25hdGlvbiIsInN1YiI6IkFGaWtvWFk1TEV1LTNkbk1pa3Z3MUJzQUx4SGIybV9IaVJjaHVfSEM1aGciLCJ0aWQiOiI0NDc4ODkyMC05Yjk3LTRmOGItODIwYS0yMTFiMTMzZDk1MzgiLCJ1bmlxdWVfbmFtZSI6Im1pamlhbmdAbWljcm9zb2Z0LmNvbSIsInV0aSI6ImFQaTJxOVZ6ODBXdHNsYjRBMzBCQUEiLCJ2ZXIiOiIxLjAifQ.agGfaegYRnGj6DM_-N_eYulnQdXHhrsus45QDuApirETDR2P2aMRxRioOCR2YVwn8pmpQ1LoAhddcYMWisrw_qhaQr0AYsDPWRtJ6x0hDk5teUgbix3gazb7F-TVcC1gXpc9y7j77Ujxcq9z0r5lF65Y9bpNSefn9Te6GZYG7BgKEixqC4W6LqjtcjuOuW-ouy6LSSox71Fj4Ni3zkGfxX1T_jiOvQTd6BBltSrShDm0bTMefoyX8oqfMEA2ziKjwvBFrOjO0uK4rJLgLYH4qvkR0bdF9etdstqKMo5gecarWHNzWi_tghQu9aE3Z3EZdYNI_ZGM-Bbe3pkCfvEOyA
5. Select Send, and you can call the API successfully.
At this point, when a user tries to make a call from the Developer Console, the user is prompted to sign in. TheDeveloper Console obtains an access token on behalf of the user.
But what if someone calls your API without a token or with an invalid token? For example, you can still call the APIeven if you delete the Authorization header. The reason is that API Management does not validate the accesstoken at this point. It simply passes the Authorization header to the back-end API.
You can use the Validate JWT policy to pre-authorize requests in API Management, by validating the access tokensof each incoming request. If a request does not have a valid token, API Management blocks it. For example, youcan add the following policy to the <inbound> policy section of the Echo API . It checks the audience claim in anaccess token, and returns an error message if the token is not valid. For information on how to configure policies,see Set or edit policies.
In this guide, you used the Developer Console in API Management as the sample client application to call the Echo API protected by OAuth 2.0. To learn more about how to build an application and implement OAuth 2.0, see
Azure Active Directory code samples.
Learn more about Azure Active Directory and OAuth2.0.Check out more videos about API Management.For other ways to secure your back-end service, see Mutual Certificate authentication.
Create an API Management service instance.
Manage your first API.
How to use Azure API Management with virtualnetworks4/9/2018 • 10 min to read • Edit Online
NOTENOTE
Prerequisites
Enable VNET connectionEnable VNET connectivity using the Azure portalEnable VNET connectivity using the Azure portal
Azure Virtual Networks (VNETs) allow you to place any of your Azure resources in a non-internet routeablenetwork that you control access to. These networks can then be connected to your on-premises networks usingvarious VPN technologies. To learn more about Azure Virtual Networks start with the information here: AzureVirtual Network Overview.
Azure API Management can be deployed inside the virtual network (VNET), so it can access backend serviceswithin the network. The developer portal and API gateway, can be configured to be accessible either from theInternet or only within the virtual network.
Azure API Management supports both classic and Azure Resource Manager VNets.
To perform the steps described in this article, you must have:
VNET connectivity is available in the Premium and Developer tiers only. Switch to one of these tiers byfollowing the directions in the upgrade and scale topic.
An active Azure subscription.
If you don't have an Azure subscription, create a free account before you begin.
An APIM instance. For more information, see Create an Azure API Management instance.
1. Navigate to your APIM instance in the Azure portal.2. Select Virtual Network.3. Configure the API Management instance to be deployed inside a Virtual network.
4. Select the desired access type:
External: the API Management gateway and developer portal are accessible from the public internetvia an external load balancer. The gateway can access resources within the virtual network.
Internal: the API Management gateway and developer portal are accessible only from within thevirtual network via an internal load balancer. The gateway can access resources within the virtualnetwork.
NOTENOTE
IMPORTANTIMPORTANT
`
You will now see a list of all regions where your API Management service is provisioned. Select aVNET and subnet for every region. The list is populated with both classic and Resource Managervirtual networks available in your Azure subscriptions that are setup in the region you areconfiguring.
Service Endpoint in the above diagram includes Gateway/Proxy, the Azure portal, the Developer portal, GIT,and the Direct Management Endpoint. Management Endpoint in the above diagram is the endpoint hostedon the service to manage configuration via Azure portal and Powershell. Also, note, that, even though, thediagram shows IP Addresses for its various endpoints, API Management service only responds on itsconfigured Hostnames.
When deploying an Azure API Management instance to a Resource Manager VNET, the service must be in adedicated subnet that contains no other resources except for Azure API Management instances. If an attemptis made to deploy an Azure API Management instance to a Resource Manager VNET subnet that containsother resources, the deployment will fail.
5. Click Save at the top of the screen.
NOTENOTE
IMPORTANTIMPORTANT
Enable VNET connection using PowerShell cmdlets
Connect to a web service hosted within a virtual Network
Common Network Configuration Issues
The VIP address of the API Management instance will change each time VNET is enabled or disabled.The VIP address will also change when API Management is moved from External to Internal or vice-versa
If you remove API Management from a VNET or change the one it is deployed in, the previously used VNET can remainlocked for up to two hours. During this period it will not be possible to delete the VNET or deploy a new resource to it.
You can also enable VNET connectivity using the PowerShell cmdlets
Create an API Management service inside a VNET: Use the cmdlet New-AzureRmApiManagement tocreate an Azure API Management service inside a VNET.
Deploy an existing API Management service inside a VNET: Use the cmdlet Update-AzureRmApiManagementDeployment to move an existing Azure API Management service inside a VirtualNetwork.
After your API Management service is connected to the VNET, accessing backend services within it is no differentthan accessing public services. Just type in the local IP address or the host name (if a DNS server is configured forthe VNET) of your web service into the Web service URL field when creating a new API or editing an existingone.
Following is a list of common misconfiguration issues that can occur while deploying API Management serviceinto a Virtual Network.
Custom DNS server setup: The API Management service depends on several Azure services. When APIManagement is hosted in a VNET with a custom DNS server, it needs to resolve the hostnames of those Azureservices. Please follow this guidance on custom DNS setup. See the ports table below and other networkrequirements for reference.
IMPORTANTIMPORTANT
SOURCE /DESTINATIONPORT(S) DIRECTION
TRANSPORTPROTOCOL
SOURCE /DESTINATION PURPOSE (*)
VIRTUALNETWORK TYPE
* / 80, 443 Inbound TCP INTERNET /VIRTUAL_NETWORK
Clientcommunicationto APIManagement
External
* / 3443 Inbound TCP INTERNET /VIRTUAL_NETWORK
Managementendpoint forAzure portal andPowershell
Internal
* / 80, 443 Outbound TCP VIRTUAL_NETWORK / INTERNET
Dependency onAzure Storage,Azure ServiceBus, and AzureActive Directory(whereapplicable).
External &Internal
* / 1433 Outbound TCP VIRTUAL_NETWORK / INTERNET
Access to AzureSQL endpoints
External &Internal
* / 5672 Outbound TCP VIRTUAL_NETWORK / INTERNET
Dependency forLog to Event Hubpolicy andmonitoring agent
External &Internal
* / 445 Outbound TCP VIRTUAL_NETWORK / INTERNET
Dependency onAzure File Sharefor GIT
External &Internal
* / 1886 Outbound TCP VIRTUAL_NETWORK / INTERNET
Needed topublish Healthstatus toResource Health
External &Internal
* / 25028 Outbound TCP VIRTUAL_NETWORK / INTERNET
Connect to SMTPRelay for sendingEmails
External &Internal
If you plan to use a Custom DNS Server(s) for the VNET, you should set it up before deploying an API Management serviceinto it. Otherwise you need to update the API Management service each time you change the DNS Server(s) by running theApply Network Configuration Operation
Ports required for API Management: Inbound and Outbound traffic into the Subnet in which APIManagement is deployed can be controlled using Network Security Group. If any of these ports are unavailable,API Management may not operate properly and may become inaccessible. Having one or more of these portsblocked is another common misconfiguration issue when using API Management with a VNET.
When an API Management service instance is hosted in a VNET, the ports in the following table are used.
* / 6381 - 6383 Inbound &Outbound
TCP VIRTUAL_NETWORK /VIRTUAL_NETWORK
Access RedisCache InstancesbetweenRoleInstances
External &Internal
* / * Inbound TCP AZURE_LOAD_BALANCER /VIRTUAL_NETWORK
AzureInfrastructureLoad Balancer
External &Internal
SOURCE /DESTINATIONPORT(S) DIRECTION
TRANSPORTPROTOCOL
SOURCE /DESTINATION PURPOSE (*)
VIRTUALNETWORK TYPE
IMPORTANTIMPORTANTThe Ports for which the Purpose is bold are required for API Management service to be deployed successfully. Blocking theother ports however will cause degradation in the ability to use and monitor the running service.
SSL functionality: To enable SSL certificate chain building and validation the API Management serviceneeds Outbound network connectivity to ocsp.msocsp.com, mscrl.microsoft.com and crl.microsoft.com. Thisdependency is not required, if any certificate you upload to API Management contain the full chain to theCA root.
DNS Access: Outbound access on port 53 is required for communication with DNS servers. If a customDNS server exists on the other end of a VPN gateway, the DNS server must be reachable from the subnethosting API Management.
Metrics and Health Monitoring: Outbound network connectivity to Azure Monitoring endpoints, whichresolve under the following domains: global.metrics.nsatc.net, shoebox2.metrics.nsatc.net,prod3.metrics.nsatc.net, prod.warmpath.msftcloudes.com, prod3-black.prod3.metrics.nsatc.net and prod3-red.prod3.metrics.nsatc.net.
Express Route Setup: A common customer configuration is to define their own default route (0.0.0.0/0)which forces outbound Internet traffic to instead flow on-premises. This traffic flow invariably breaksconnectivity with Azure API Management because the outbound traffic is either blocked on-premises, orNAT'd to an unrecognizable set of addresses that no longer work with various Azure endpoints. Thesolution is to define one (or more) user-defined routes (UDRs) on the subnet that contains the Azure APIManagement. A UDR defines subnet-specific routes that will be honored instead of the default route. Ifpossible, it is recommended to use the following configuration:
The ExpressRoute configuration advertises 0.0.0.0/0 and by default force tunnels all outbound traffic on-premises.The UDR applied to the subnet containing the Azure API Management defines 0.0.0.0/0 with a next hoptype of Internet. The combined effect of these steps is that the subnet level UDR takes precedence overthe ExpressRoute forced tunneling, thus ensuring outbound Internet access from the Azure APIManagement.
Routing through network virtual appliances: Configurations that use a UDR with a default route(0.0.0.0/0) to route internet destined traffic from the API Management subnet through a network virtualappliance running in Azure will block management traffic coming from Internet to the API Managementservice instance deployed inside the virtual network subnet. This configuration is not supported.
WARNINGWARNING
Troubleshooting
Subnet Size Requirement
Routing
Azure API Management is not supported with ExpressRoute configurations that incorrectly cross-advertise routes fromthe public peering path to the private peering path. ExpressRoute configurations that have public peering configured, willreceive route advertisements from Microsoft for a large set of Microsoft Azure IP address ranges. If these address ranges areincorrectly cross-advertised on the private peering path, the end result is that all outbound network packets from the AzureAPI Management instance's subnet are incorrectly force-tunneled to a customer's on-premises network infrastructure. Thisnetwork flow breaks Azure API Management. The solution to this problem is to stop cross-advertising routes from the publicpeering path to the private peering path.
IMPORTANTIMPORTANT
Initial Setup: When the initial deployment of API Management service into a subnet does not succeed, it isadvised to first deploy a virtual machine into the same subnet. Next remote desktop into the virtual machineand validate that there is connectivity to one of each resource below in your azure subscription
Azure Storage blobAzure SQL Database
After you have validated the connectivity, make sure to remove all the resources deployed in the subnet, beforedeploying API Management into the subnet.
Incremental Updates: When making changes to your network, refer to NetworkStatus API, to verify thatthe API Management service has not lost access to any of the critical resources which it depends upon. Theconnectivity status should be updated every 15 minutes.
Resource Navigation Links: When deploying into Resource Manager style vnet subnet, API Managementreserves the subnet, by creating a resource navigation Link. If the subnet already contains a resource from adifferent provider, deployment will fail. Similarly, when you move an API Management service to a differentsubnet or delete it, we will remove that resource navigation link.
Azure reserves some IP addresses within each subnet, and these addresses can't be used. The first and last IPaddresses of the subnets are reserved for protocol conformance, along with three more addresses used for Azureservices. For more information, see Are there any restrictions on using IP addresses within these subnets?
In addition to the IP addresses used by the Azure VNET infrastructure, each Api Management instance in thesubnet uses two IP addresses per unit of Premium SKU or one IP address for the Developer SKU. Each instancereserves an additional IP address for the external load balancer. When deploying into Internal vnet, it requires anadditional IP address for the internal load balancer.
Given the calculation above the minimum size of the subnet, in which API Management can be deployed is /29which gives 3 IP addresses.
A load balanced public IP address (VIP) will be reserved to provide access to all service endpoints.An IP address from a subnet IP range (DIP) will be used to access resources within the vnet and a public IPaddress (VIP) will be used to access resources outside the vnet.Load balanced public IP address can be found on the Overview/Essentials blade in the Azure portal.
Limitations
Related content
A subnet containing API Management instances cannot contain any other Azure resource types.The subnet and the API Management service must be in the same subscription.A subnet containing API Management instances cannot be moved across subscriptions.For multi-region API Management deployments configured in Internal virtual network mode, users areresponsible for managing the load balancing across multiple regions, as they own the routing.
Connecting a Virtual Network to backend using Vpn GatewayConnecting a Virtual Network from different deployment modelsHow to use the API Inspector to trace calls in Azure API ManagementVirtual Network Faq
Using Azure API Management service with aninternal virtual network4/9/2018 • 3 min to read • Edit Online
Prerequisites
Creating an API Management in an internal virtual network
Enable a virtual network connection using the Azure portalEnable a virtual network connection using the Azure portal
With Azure Virtual Networks, Azure API Management can manage APIs not accessible on the internet. A numberof VPN technologies are available to make the connection. API Management can be deployed in two main modesinside a virtual network:
ExternalInternal
When API Management deploys in internal virtual network mode, all the service endpoints (gateway, theDeveloper portal, the Azure portal, direct management, and Git) are only visible inside a virtual network that youcontrol the access to. None of the service endpoints are registered on the public DNS server.
Using API Management in internal mode, you can achieve the following scenarios:
Make APIs hosted in your private datacenter securely accessible by third parties outside of it by using site-to-site or Azure ExpressRoute VPN connections.Enable hybrid cloud scenarios by exposing your cloud-based APIs and on-premises APIs through a commongateway.Manage your APIs hosted in multiple geographic locations by using a single gateway endpoint.
To perform the steps described in this article, you must have:
An active Azure subscription.
If you don't have an Azure subscription, create a free account before you begin.
An Azure API Management instance. For more information, see Create an Azure API Managementinstance.
The API Management service in an internal virtual network is hosted behind an internal load balancer (ILB).
1. Browse to your Azure API Management instance in the Azure portal.2. Select Virtual network.3. Configure the API Management instance to be deployed inside the virtual network.
Enable a virtual network connection by using PowerShell cmdletsEnable a virtual network connection by using PowerShell cmdlets
DNS configuration
4. Select Save.
After the deployment succeeds, you should see the internal virtual IP address of your service on the dashboard.
You can also enable virtual network connectivity by using PowerShell cmdlets.
Create an API Management service inside a virtual network: Use the cmdlet New-AzureRmApiManagement to create an Azure API Management service inside a virtual network andconfigure it to use the internal virtual network type.
Deploy an existing API Management service inside a virtual network: Use the cmdlet Update-AzureRmApiManagementDeployment to move an existing API Management service inside a virtualnetwork and configure it to use the internal virtual network type.
When API Management is in external virtual network mode, the DNS is managed by Azure. For internal virtualnetwork mode, you have to manage your own routing.
NOTENOTE
Access on default host namesAccess on default host names
Access on custom domain namesAccess on custom domain names
Routing
API Management service does not listen to requests coming from IP addresses. It only responds to requests to the hostname configured on its service endpoints. These endpoints include gateway, the Azure portal and the Developer portal, directmanagement endpoint, and Git.
When you create an API Management service, named "contoso" for example, the following service endpoints areconfigured by default:
Gateway or proxy: contoso.azure-api.net
The Azure portal and the Developer portal: contoso.portal.azure-api.net
Direct management endpoint: contoso.management.azure-api.net
Git: contoso.scm.azure-api.net
To access these API Management service endpoints, you can create a virtual machine in a subnet connected to thevirtual network in which API Management is deployed. Assuming the internal virtual IP address for your service is10.0.0.5, you can map the hosts file, %SystemDrive%\drivers\etc\hosts, as follows:
10.0.0.5 contoso.azure-api.net
10.0.0.5 contoso.portal.azure-api.net
10.0.0.5 contoso.management.azure-api.net
10.0.0.5 contoso.scm.azure-api.net
You can then access all the service endpoints from the virtual machine you created. If you use a custom DNSserver in a virtual network, you can also create A DNS records and access these endpoints from anywhere in yourvirtual network.
1. If you don’t want to access the API Management service with the default host names, you can set upcustom domain names for all your service endpoints as shown in the following image:
2. Then you can create records in your DNS server to access the endpoints that are only accessible from withinyour virtual network.
Related content
A load balanced private virtual IP address from the subnet range will be reserved and used to access the APIManagement service endpoints from within the vnet.A load balanced public IP address (VIP) will also be reserved to provide access to the management serviceendpoint only over port 3443.An IP address from a subnet IP range (DIP) will be used to access resources within the vnet and a public IPaddress (VIP) will be used to access resources outside the vnet.Load balanced public and private IP addresses can be found on the Overview/Essentials blade in the Azureportal.
To learn more, see the following articles:
Common network configuration problems while setting up Azure API Management in a virtual networkVirtual network FAQsCreating a record in DNS
Integrate API Management in an internal VNET withApplication Gateway12/7/2017 • 11 min to read • Edit Online
Overview
Prerequisites
Scenario
The API Management service can be configured in a Virtual Network in internal mode which makes it accessibleonly from within the Virtual Network. Azure Application Gateway is a PAAS Service which provides a Layer-7 loadbalancer. It acts as a reverse-proxy service and provides among its offering a Web Application Firewall (WAF).
Combining API Management provisioned in an internal VNET with the Application Gateway frontend enables thefollowing scenarios:
Use the same API Management resource for consumption by both internal consumers and external consumers.Use a single API Management resource and have a subset of APIs defined in API Management available forexternal consumers.Provide a turn-key way to switch access to API Management from the public Internet on and off.
To perform the steps described in this article, you must have:
An active Azure subscription.
If you don't have an Azure subscription, create a free account before you begin.
An APIM instance. For more information, see Create an Azure API Management instance.
This article covers how to use a single API Management service for both internal and external consumers andmake it act as a single frontend for both on-prem and cloud APIs. You will also see how to expose only a subset ofyour APIs (in the example they are highlighted in green) for External Consumption using the PathBasedRoutingfunctionality available in Application Gateway.
In the first setup example all your APIs are managed only from within your Virtual Network. Internal consumers(highlighted in orange) can access all your internal and external APIs. Traffic never goes out to Internet a highperformance is delivered via Express Route circuits.
Before you begin
What is required to create an integration between API Managementand Application Gateway?
Steps required for integrating API Management and ApplicationGateway
1. Install the latest version of the Azure PowerShell cmdlets by using the Web Platform Installer. You candownload and install the latest version from the Windows PowerShell section of the Downloads page.
2. Create a Virtual Network and create separate subnets for API Management and Application Gateway.3. If you intend to create a custom DNS server for the Virtual Network, do so before starting the deployment.
Double check it works by ensuring a virtual machine created in a new subnet in the Virtual Network can resolveand access all Azure service endpoints.
Back-end server pool: This is the internal virtual IP address of the API Management service.Back-end server pool settings: Every pool has settings like port, protocol, and cookie-based affinity. Thesesettings are applied to all servers within the pool.Front-end port: This is the public port that is opened on the application gateway. Traffic hitting it getsredirected to one of the back-end servers.Listener: The listener has a front-end port, a protocol (Http or Https, these values are case-sensitive), and theSSL certificate name (if configuring SSL offload).Rule: The rule binds a listener to a back-end server pool.Custom Health Probe: Application Gateway, by default, uses IP address based probes to figure out whichservers in the BackendAddressPool are active. The API Management service only responds to requests whichhave the correct host header, hence the default probes fail. A custom health probe needs to be defined to helpapplication gateway determine that the service is alive and it should forward requests.Custom domain certificate: To access API Management from the internet you need to create a CNAMEmapping of its hostname to the Application Gateway front-end DNS name. This ensures that the hostnameheader and certificate sent to Application Gateway that is forwarded to API Management is one APIM canrecognize as valid.
1. Create a resource group for Resource Manager.2. Create a Virtual Network, subnet, and public IP for the Application Gateway. Create another subnet for API
Create a resource group for Resource Manager
Step 1Step 1
Login-AzureRmAccount
Step 2Step 2
Get-AzureRmSubscription -Subscriptionid "GUID of subscription" | Select-AzureRmSubscription
Step 3Step 3
New-AzureRmResourceGroup -Name "apim-appGw-RG" -Location "West US"
Create a Virtual Network and a subnet for the application gateway
Step 1Step 1
$appgatewaysubnet = New-AzureRmVirtualNetworkSubnetConfig -Name "apim01" -AddressPrefix "10.0.0.0/24"
Step 2Step 2
Management.3. Create an API Management service inside the VNET subnet created above and ensure you use the Internal
mode.4. Setup the custom domain name in the API Management service.5. Create an Application Gateway configuration object.6. Create an Application Gateway resource.7. Create a CNAME from the public DNS name of the Application Gateway to the API Management proxy
hostname.
Make sure that you are using the latest version of Azure PowerShell. More info is available at Using WindowsPowerShell with Resource Manager.
Log in to Azure
Authenticate with your credentials.
Check the subscriptions for the account and select it.
Create a resource group (skip this step if you're using an existing resource group).
Azure Resource Manager requires that all resource groups specify a location. This is used as the default location forresources in that resource group. Make sure that all commands to create an application gateway use the sameresource group.
The following example shows how to create a Virtual Network using the resource manager.
Assign the address range 10.0.0.0/24 to the subnet variable to be used for Application Gateway while creating aVirtual Network.
Assign the address range 10.0.1.0/24 to the subnet variable to be used for API Management while creating aVirtual Network.
$apimsubnet = New-AzureRmVirtualNetworkSubnetConfig -Name "apim02" -AddressPrefix "10.0.1.0/24"
Step 3Step 3
$vnet = New-AzureRmVirtualNetwork -Name "appgwvnet" -ResourceGroupName "apim-appGw-RG" -Location "West US" -AddressPrefix "10.0.0.0/16" -Subnet $appgatewaysubnet,$apimsubnet
Step 4Step 4
$appgatewaysubnetdata=$vnet.Subnets[0]$apimsubnetdata=$vnet.Subnets[1]
Create an API Management service inside a VNET configured ininternal mode
Step 1Step 1
$apimVirtualNetwork = New-AzureRmApiManagementVirtualNetwork -Location "West US" -SubnetResourceId $apimsubnetdata.Id
Step 2Step 2
$apimService = New-AzureRmApiManagement -ResourceGroupName "apim-appGw-RG" -Location "West US" -Name "ContosoApi" -Organization "Contoso" -AdminEmail "[email protected]" -VirtualNetwork $apimVirtualNetwork -VpnType "Internal" -Sku "Developer"
Set-up a custom domain name in API ManagementStep 1Step 1
$certUploadResult = Import-AzureRmApiManagementHostnameCertificate -ResourceGroupName "apim-appGw-RG" -Name "ContosoApi" -HostnameType "Proxy" -PfxPath <full path to .pfx file> -PfxPassword <password for certificate file> -PassThru
Step 2Step 2
Create a Virtual Network named appgwvnet in resource group apim-appGw-RG for the West US region usingthe prefix 10.0.0.0/16 with subnets 10.0.0.0/24 and 10.0.1.0/24.
Assign a subnet variable for the next steps
The following example shows how to create an API Management service in a VNET configured for internal accessonly.
Create an API Management Virtual Network object using the subnet $apimsubnetdata created above.
Create an API Management service inside the Virtual Network.
After the above command succeeds refer to DNS Configuration required to access internal VNET APIManagement service to access it.
Upload the certificate with private key for the domain. For this example it will be *.contoso.net .
Once the certificate is uploaded, create a hostname configuration object for the proxy with a hostname of api.contoso.net , as the example certificate provides authority for the *.contoso.net domain.
$proxyHostnameConfig = New-AzureRmApiManagementHostnameConfiguration -CertificateThumbprint $certUploadResult.Thumbprint -Hostname "api.contoso.net"$result = Set-AzureRmApiManagementHostnames -Name "ContosoApi" -ResourceGroupName "apim-appGw-RG" -ProxyHostnameConfiguration $proxyHostnameConfig
Create a public IP address for the front-end configuration
$publicip = New-AzureRmPublicIpAddress -ResourceGroupName "apim-appGw-RG" -name "publicIP01" -location "West US" -AllocationMethod Dynamic
Create application gateway configuration
Step 1Step 1
$gipconfig = New-AzureRmApplicationGatewayIPConfiguration -Name "gatewayIP01" -Subnet $appgatewaysubnetdata
Step 2Step 2
$fp01 = New-AzureRmApplicationGatewayFrontendPort -Name "port01" -Port 443
Step 3Step 3
$fipconfig01 = New-AzureRmApplicationGatewayFrontendIPConfig -Name "frontend1" -PublicIPAddress $publicip
Step 4Step 4
$cert = New-AzureRmApplicationGatewaySslCertificate -Name "cert01" -CertificateFile <full path to .pfx file> -Password <password for certificate file>
Step 5Step 5
$listener = New-AzureRmApplicationGatewayHttpListener -Name "listener01" -Protocol "Https" -FrontendIPConfiguration $fipconfig01 -FrontendPort $fp01 -SslCertificate $cert
Create a public IP resource publicIP01 in resource group apim-appGw-RG for the West US region.
An IP address is assigned to the application gateway when the service starts.
All configuration items must be set up before creating the application gateway. The following steps create theconfiguration items that are needed for an application gateway resource.
Create an application gateway IP configuration named gatewayIP01. When Application Gateway starts, it picksup an IP address from the subnet configured and route network traffic to the IP addresses in the back-end IP pool.Keep in mind that each instance takes one IP address.
Configure the front-end IP port for the public IP endpoint. This port is the port that end users connect to.
Configure the front-end IP with public IP endpoint.
Configure the certificate for the Application Gateway, used to decrypt and re-encrypt the traffic passing through.
Create the HTTP listener for the Application Gateway. Assign the front-end IP configuration, port, and ssl certificateto it.
Step 6Step 6
NOTENOTE
$apimprobe = New-AzureRmApplicationGatewayProbeConfig -Name "apimproxyprobe" -Protocol "Https" -HostName "api.contoso.net" -Path "/status-0123456789abcdef" -Interval 30 -Timeout 120 -UnhealthyThreshold 8
Step 7Step 7
$authcert = New-AzureRmApplicationGatewayAuthenticationCertificate -Name "whitelistcert1" -CertificateFile <full path to .cer file>
Step 8Step 8
$apimPoolSetting = New-AzureRmApplicationGatewayBackendHttpSettings -Name "apimPoolSetting" -Port 443 -Protocol "Https" -CookieBasedAffinity "Disabled" -Probe $apimprobe -AuthenticationCertificates $authcert -RequestTimeout 180
Step 9Step 9
$apimProxyBackendPool = New-AzureRmApplicationGatewayBackendAddressPool -Name "apimbackend" -BackendIPAddresses $apimService.StaticIPs[0]
Step 10Step 10
$dummyBackendSetting = New-AzureRmApplicationGatewayBackendHttpSettings -Name "dummySetting01" -Port 80 -Protocol Http -CookieBasedAffinity Disabled
$dummyBackendPool = New-AzureRmApplicationGatewayBackendAddressPool -Name "dummyBackendPool" -BackendFqdns "dummybackend.com"
Create a custom probe to the API Management service ContosoApi proxy domain endpoint. The path /status-0123456789abcdef is a default health endpoint hosted on all the API Management services. Set api.contoso.net as a custom probe hostname to secure it with SSL certificate.
The hostname contosoapi.azure-api.net is the default proxy hostname configured when a service named contosoapi iscreated in public Azure.
Upload the certificate to be used on the SSL-enabled backend pool resources. This is the same certificate whichyou provided in Step 4 above.
Configure HTTP backend settings for the Application Gateway. This includes setting a time-out limit for backendrequest after which they are cancelled. This value is different from the probe time-out.
Configure a back-end IP address pool named apimbackend with the internal virtual IP address of the APIManagement service created above.
Create settings for a dummy (non-existent) backend. Requests to API paths that we do not want to expose fromAPI Management via Application Gateway will hit this backend and return 404.
Configure HTTP settings for the dummy backend.
Configure a dummy backend dummyBackendPool, which points to a FQDN address dummybackend.com.This FQDN address does not exist in the virtual network.
$dummyPathRule = New-AzureRmApplicationGatewayPathRuleConfig -Name "nonexistentapis" -Paths "/*" -BackendAddressPool $dummyBackendPool -BackendHttpSettings $dummyBackendSetting
Step 11Step 11
$echoapiRule = New-AzureRmApplicationGatewayPathRuleConfig -Name "externalapis" -Paths "/echo/*" -BackendAddressPool $apimProxyBackendPool -BackendHttpSettings $apimPoolSetting
$urlPathMap = New-AzureRmApplicationGatewayUrlPathMapConfig -Name "urlpathmap" -PathRules $echoapiRule, $dummyPathRule -DefaultBackendAddressPool $dummyBackendPool -DefaultBackendHttpSettings $dummyBackendSetting
Step 12Step 12
$rule01 = New-AzureRmApplicationGatewayRequestRoutingRule -Name "rule1" -RuleType PathBasedRouting -HttpListener $listener -UrlPathMap $urlPathMap
Step 13Step 13
$sku = New-AzureRmApplicationGatewaySku -Name "WAF_Medium" -Tier "WAF" -Capacity 2
Step 14Step 14
$config = New-AzureRmApplicationGatewayWebApplicationFirewallConfiguration -Enabled $true -FirewallMode "Prevention"
Create Application Gateway
Create a rule setting that the Application Gateway will use by default which points to the non-existent backenddummybackend.com in the Virtual Network.
Configure URL rule paths for the back-end pools. This enables selecting only some of the APIs from APIManagement for being exposed to the public. For example, if there are Echo API (/echo/), Calculator API (/calc/)etc. make only Echo API accessible from Internet).
The following example creates a simple rule for the "/echo/" path routing traffic to the back-end"apimProxyBackendPool".
If the path doesn't match the path rules we want to enable from API Management, the rule path map configurationalso configures a default back-end address pool named dummyBackendPool. For example,http://api.contoso.net/calc/* goes to dummyBackendPool as it is defined as the default pool for un-matchedtraffic.
The above step ensures that only requests for the path "/echo" are allowed through the Application Gateway.Requests to other APIs configured in API Management will throw 404 errors from Application Gateway whenaccessed from the Internet.
Create a rule setting for the Application Gateway to use URL path-based routing.
Configure the number of instances and size for the Application Gateway. Here we are using the WAF SKU forincreased security of the API Management resource.
Configure WAF to be in "Prevention" mode.
Create an Application Gateway with all the configuration objects from the preceding steps.
$appgw = New-AzureRmApplicationGateway -Name $applicationGatewayName -ResourceGroupName $resourceGroupName -Location $location -BackendAddressPools $apimProxyBackendPool, $dummyBackendPool -BackendHttpSettingsCollection $apimPoolSetting, $dummyBackendSetting -FrontendIpConfigurations $fipconfig01 -GatewayIpConfigurations $gipconfig -FrontendPorts $fp01 -HttpListeners $listener -UrlPathMaps $urlPathMap -RequestRoutingRules $rule01 -Sku $sku -WebApplicationFirewallConfig $config -SslCertificates $cert -AuthenticationCertificates $authcert -Probes $apimprobe
CNAME the API Management proxy hostname to the public DNSname of the Application Gateway resource
Get-AzureRmPublicIpAddress -ResourceGroupName "apim-appGw-RG" -Name "publicIP01"
Summary
Next steps
Once the gateway is created, the next step is to configure the front end for communication. When using a public IP,Application Gateway requires a dynamically assigned DNS name, which may not be easy to use.
The Application Gateway's DNS name should be used to create a CNAME record which points the APIM proxyhost name (e.g. api.contoso.net in the examples above) to this DNS name. To configure the frontend IP CNAMErecord, retrieve the details of the Application Gateway and its associated IP/DNS name using the PublicIPAddresselement. The use of A-records is not recommended since the VIP may change on restart of gateway.
Azure API Management configured in a VNET provides a single gateway interface for all configured APIs, whetherthey are hosted on-prem or in the cloud. Integrating Application Gateway with API Management provides theflexibility of selectively enabling particular APIs to be accessible on the Internet, as well as providing a WebApplication Firewall as a frontend to your API Management instance.
Learn more about Azure Application Gateway
Learn more about API Management and VNETs
Application Gateway OverviewApplication Gateway Web Application FirewallApplication Gateway using Path-based Routing
Using API Management available only within the VNETUsing API Management in VNET
How to secure back-end services using clientcertificate authentication in Azure API Management2/28/2018 • 3 min to read • Edit Online
Prerequisites
Upload a client certificate
API Management provides the capability to secure access to the back-end service of an API using clientcertificates. This guide shows how to manage certificates in the API publisher portal, and how to configure an APIto use a certificate to access its back-end service.
For information about managing certificates using the API Management REST API, see Azure API ManagementREST API Certificate entity.
This guide shows you how to configure your API Management service instance to use client certificateauthentication to access the back-end service for an API. Before following the steps in this topic, you should haveyour back-end service configured for client certificate authentication (to configure certificate authentication inAzure WebSites refer to this article), and have access to the certificate and the password for the certificate foruploading in the API Management publisher portal.
To get started, click Publisher portal in the Azure Portal for your API Management service. This takes you to theAPI Management publisher portal.
If you have not yet created an API Management service instance, see Create an API Management serviceinstance.
Click Security from the API Management menu on the left, and click Client certificates.
To upload a new certificate, click Upload certificate.
Browse to your certificate, and then enter the password for the certificate.
The certificate must be in .pfx format. Self-signed certificates are allowed.
Click Upload to upload the certificate.
The certificate password is validated at this time. If it is incorrect an error message is displayed.
Once the certificate is uploaded, it appears on the Client certificates tab. If you have multiple certificates, make anote of the subject, or the last four characters of the thumbprint, which are used to select the certificate whenconfiguring an API to use certificates, as covered in the following Configure an API to use a client certificate forgateway authentication section.
To turn off certificate chain validation when using, for example, a self-signed certificate, follow the stepsdescribed in this FAQ item.
Delete a client certificate
Configure an API to use a client certificate for gateway authentication
To delete a certificate, click Delete beside the desired certificate.
Click Yes, delete it to confirm.
If the certificate is in use by an API, then a warning screen is displayed. To delete the certificate you must firstremove the certificate from any APIs that are configured to use it.
Click APIs from the API Management menu on the left, click the name of the desired API, and click the Securitytab.
Select Client certificates from the With credentials drop-down list.
Select the desired certificate from the Client certificate drop-down list. If there are multiple certificates you canlook at the subject or the last four characters of the thumbprint as noted in the previous section to determine thecorrect certificate.
Click Save to save the configuration change to the API.
This change is effective immediately, and calls to operations of that API will use the certificate to authenticateon the back-end server.
When a certificate is specified for gateway authentication for the back-end service of an API, it becomes part ofthe policy for that API, and can be viewed in the policy editor.
Self-signed certificates
$context = New-AzureRmApiManagementContext -resourcegroup 'ContosoResourceGroup' -servicename 'ContosoAPIMService'New-AzureRmApiManagementBackend -Context $context -Url 'https://contoso.com/myapi' -Protocol http -SkipCertificateChainValidation $true
If you are using self-signed certificates, you will need to disable certificate chain validation in order for APIManagement to communicate with the backend system, otherwise it will return a 500 error code. To configure this,you can use the New-AzureRmApiManagementBackend (for new back end) or Set-AzureRmApiManagementBackend (forexisting back end) PowerShell cmdlets and set the -SkipCertificateChainValidation parameter to True .
Modify the content and layout of pages on thedeveloper portal in Azure API Management2/14/2018 • 1 min to read • Edit Online
Structure of developer portal pages
Modifying the contents of a layout widget
There are three fundamental ways to customize the developer portal in Azure API Management:
Edit the contents of static pages and page layout elements (explained in this guide)Update the styles used for page elements across the developer portalModify the templates used for pages generated by the portal (for example, API docs, products, userauthentication, etc.)
The developer portal is based on a content management system. The layout of every page is built based on set ofsmall page elements known as widgets:
All widgets are editable.
The core contents specific to each individual page reside in the "Contents" widget. Editing a page means editingthe contents of this widget.All page layout elements are contained with the remaining widgets. Changes made to these widgets are appliedto all pages. They are referred to as "layout widgets."
In day-to-day page editing one would often modify just the Content widget, which will have different content foreach individual page.
The Developer portal is accessible from the Azure Portal.
Next steps
1. Click Developer Portal from the toolbar of your API Management instance.2. To edit the contents of widgets, click the icon comprised of two paint brushes from the Developer portal menu
on the left.
4. Once you are ready to publish your changes, click Publish at the bottom of the page.
3. To modify the contents of the header, scroll to the Header section in the list on the left.
The widgets are editable from within the fields.
Now you should be able to see the new header on every page within the developer portal.
Update the styles used for page elements across the developer portalModify the templates used for pages generated by the portal (for example, API docs, products, userauthentication, etc.)
How to customize the Azure API Managementdeveloper portal using templates2/6/2018 • 4 min to read • Edit Online
Developer portal templates overview
There are three fundamental ways to customize the developer portal in Azure API Management:
Edit the contents of static pages and page layout elementsUpdate the styles used for page elements across the developer portalModify the templates used for pages generated by the portal (explained in this guide)
Templates are used to customize the content of system-generated developer portal pages (for example, APIdocs, products, user authentication, etc.). Using DotLiquid syntax, and a provided set of localized stringresources, icons, and page controls, you have great flexibility to configure the content of the pages as you see fit.
Editing templates is done from the Developer portal while being logged in as an administrator. To get therefirst open the Azure Portal and click Developer portal from the service toolbar of your API Managementinstance.
To access the developer portal templates, click the customize icon on the left to display the customization menu,and click Templates.
The templates list displays several categories of templates covering the different pages in the developer portal.Each template is different, but the steps to edit them and publish the changes are the same. To edit a template,click the name of the template.
Clicking a template takes you to the developer portal page that is customizable by that template. In this example,the Product list template is displayed. The Product list template controls the area of the screen indicated bythe red rectangle.
Some templates, like the User Profile templates, customize different parts of the same page.
The editor for each developer portal template has two sections displayed at the bottom of the page. The left-hand side displays the editing pane for the template, and the right-hand side displays the data model for thetemplate.
The template editing pane contains the markup that controls the appearance and behavior of the correspondingpage in the developer portal. The markup in the template uses the DotLiquid syntax. One popular editor forDotLiquid is DotLiquid for Designers. Any changes made to the template during editing are displayed in real-time in the browser, but are not visible to your customers until you save and publish the template.
The Template data pane provides a guide to the data model for the entities that are available for use in aparticular template. It provides this guide by displaying the live data that are currently displayed in the developerportal. You can expand the template panes by clicking the rectangle in the upper-right corner of the Templatedata pane.
In the previous example, there are two products displayed in the developer portal that were retrieved from thedata displayed in the Template data pane, as shown in the following example:
{ "Paging": { "Page": 1, "PageSize": 10, "TotalItemCount": 2, "ShowAll": false, "PageCount": 1 }, "Filtering": { "Pattern": null, "Placeholder": "Search products" }, "Products": [ { "Id": "56ec64c380ed850042060001", "Title": "Starter", "Description": "Subscribers will be able to run 5 calls/minute up to a maximum of 100 calls/week.", "Terms": "", "ProductState": 1, "AllowMultipleSubscriptions": false, "MultipleSubscriptionsCount": 1 }, { "Id": "56ec64c380ed850042060002", "Title": "Unlimited", "Description": "Subscribers have completely unlimited access to the API. Administrator approval is required.", "Terms": null, "ProductState": 1, "AllowMultipleSubscriptions": false, "MultipleSubscriptionsCount": 1 } ]}
The markup in the Product list template processes the data to provide the desired output by iterating throughthe collection of products to display information and a link to each individual product. Note the <search-control> and <page-control> elements in the markup. These control the display of the searching and
paging controls on the page. ProductsStrings|PageTitleProducts is a localized string reference that contains the h2 header text for the page. For a list of string resources, page controls, and icons available for use in developer
portal templates, see API Management developer portal templates reference.
<search-control></search-control><div class="row"> <div class="col-md-9"> <h2>{% localized "ProductsStrings|PageTitleProducts" %}</h2> </div></div><div class="row"> <div class="col-md-12"> {% if products.size > 0 %} <ul class="list-unstyled"> {% for product in products %} <li> <h3><a href="/products/{{product.id}}">{{product.title}}</a></h3> {{product.description}} </li> {% endfor %} </ul> <paging-control></paging-control> {% else %} {% localized "CommonResources|NoItemsToDisplay" %} {% endif %} </div></div>
To save a template
To publish a template
To save a template, click save in the template editor.
Saved changes are not live in the developer portal until they are published.
Saved templates can be published either individually, or all together. To publish an individual template, clickpublish in the template editor.
To revert a template to the previous version
Click Yes to confirm and make the template live on the developer portal.
To publish all currently unpublished template versions, click Publish in the templates list. Unpublishedtemplates are designated by an asterisk following the template name. In this example, the Product list andProduct templates are being published.
Click Publish customizations to confirm.
Newly published templates are effective immediately in the developer portal.
To revert a template to the previous published version, click revert in the template editor.
To restore a template to the default version
Click Yes to confirm.
The previously published version of a template is live in the developer portal once the revert operation iscomplete.
Restoring templates to their default version is a two-step process. First the templates must be restored, and thenthe restored versions must be published.
To restore a single template to the default version click restore in the template editor.
Click Yes to confirm.
Next steps
To restore all templates to their default versions, click Restore default templates on the template list.
The restored templates must then be published individually or all at once by following the steps in To publish atemplate.
For reference information for developer portal templates, string resources, icons, and page controls, see APIManagement developer portal templates reference.
Authorize developer accounts by using Azure ActiveDirectory in Azure API Management4/9/2018 • 4 min to read • Edit Online
NOTENOTE
Prerequisites
Authorize developer accounts by using Azure AD
This article shows you how to enable access to the developer portal for users from Azure Active Directory (AzureAD). This guide also shows you how to manage groups of Azure AD users by adding external groups that containthe users.
Azure AD integration is available in the Developer, Standard, and Premium tiers only.
Complete the following quickstart: Create an Azure API Management instance.Import and publish an Azure API Management instance. For more information, see Import and publish.
1. Sign in to the Azure portal.
2. Select .3. Type api in the search box.4. Select API Management services.5. Select your API Management service instance.6. Under SECURITY , select Identities.
7. Select +Add from the top.
The Add identity provider pane appears on the right.
8. Under Provider type, select Azure Active Directory.
Controls that enable you to enter other necessary information appear in the pane. The controls includeClient ID and Client secret. (You get information about these controls later in the article.)
9. Make a note of the contents of Redirect URL.
10. In your browser, open a different tab.11. Go to the Azure portal.
12. Select .13. Type active. The Azure Active Directory pane appears.14. Select Azure Active Directory.15. Under MANAGE , select App registrations.
17. Enter a name for the application.18. For the application type, select Web app/API.19. For the sign-in URL, enter the sign-in URL of your developer portal. In this example, the sign-in URL is
https://apimwithaad.portal.azure-api.net/signin.20. Select Create to create the application.
16. Select New application registration.
The Create pane appears on the right. That's where you enter the Azure AD app-relevant information.
21. To find your app, select App registrations and search by name.
22. After the application is registered, go to Reply URL and make sure Redirect URL is set to the value that yougot from step 9.
24. Set application permissions by selecting Required permissions.
23. If you want to configure your application (for example, change App ID URL), select Properties.
If multiple Azure AD instances will be used for this application, select Yes for Multi-tenanted. The defaultis No.
25. Select your application, and then select the Read directory data and Sign in and read user profile checkboxes.
28. Switch back to the Azure AD configuration, and select Keys.29. Create a new key by specifying a name and duration.
NOTENOTE
For more information about application permissions and delegated permissions, see Accessing the GraphAPI.
26. In the left pane, copy the Application ID value.
27. Switch back to your API Management application.
In the Add identity provider window, paste the Application ID value in the Client ID box.
30. Select Save. The key is generated.
Copy the key to the clipboard.
Make a note of this key. After you close the Azure AD configuration pane, the key cannot be displayed again.
31. Switch back to your API Management application.
In the Add identity provider window, paste the key in the Client secret text box.
32. The Add identity provider window also contains the Allowed Tenants text box. There, specify thedomains of the Azure AD instances to which you want to grant access to the APIs of the API Managementservice instance. You can separate multiple domains with newlines, spaces, or commas.
You can specify multiple domains in the Allowed Tenants section. Before any user can sign in from adifferent domain than the original domain where the application was registered, a global administrator ofthe different domain must grant permission for the application to access directory data. To grantpermission, the global administrator should:
a. Go to https://<URL of your developer portal>/aadadminconsent (for example, https://contoso.portal.azure-api.net/aadadminconsent).
b. Type in the domain name of the Azure AD tenant that they want to give access to.
c. Select Submit.
In the following example, a global administrator from miaoaad.onmicrosoft.com is trying to give permissionto this particular developer portal.
33. After you specify the desired configuration, select Add.
After the changes are saved, users in the specified Azure AD instance can sign in to the developer portal byfollowing the steps in Sign in to the developer portal by using an Azure AD account.
On the next screen, the global administrator is prompted to confirm giving the permission.
Add an external Azure AD group
Sign in to the developer portal by using an Azure AD account
If a non-global administrator tries to sign in before a global administrator grants permissions, the sign-in attemptfails and an error screen is displayed.
After you enable access for users in an Azure AD instance, you can add Azure AD groups in API Management.Then, you can more easily manage the association of the developers in the group with the desired products.
To configure an external Azure AD group, you must first configure the Azure AD instance on the Identities tab byfollowing the procedure in the previous section.
You add external Azure AD groups from the Groups tab of your API Management instance.
1. Select the Groups tab.2. Select the Add AAD group button.
3. Select the group that you want to add.4. Press the Select button.
After you add an external Azure AD group, you can review and configure its properties. Select the name of thegroup from the Groups tab. From here, you can edit Name and Description information for the group.
Users from the configured Azure AD instance can now sign in to the developer portal. They can view andsubscribe to any groups for which they have visibility.
To sign in to the developer portal by using an Azure AD account that you configured in the previous sections:
1. Open a new browser window by using the sign-in URL from the Active Directory application configuration,
and select Azure Active Directory.
2. Enter the credentials of one of the users in Azure AD, and select Sign in.
3. You might be prompted with a registration form if any additional information is required. Complete theregistration form, and select Sign up.
Your user is now signed in to the developer portal for your API Management service instance.
4/9/2018 • 3 min to read • Edit Online
WARNINGWARNING
How to authorize developer accounts by using Azure ActiveDirectory B2C in Azure API ManagementOverview
NOTENOTE
Authorize developer accounts by using Azure Active Directory B2C
Azure Active Directory B2C integration is available in the Developer and Premium tiers only.
Azure Active Directory B2C is a cloud identity management solution for consumer-facing web and mobileapplications. You can use it to manage access to your developer portal. This guide shows you the configurationthat's required in your API Management service to integrate with Azure Active Directory B2C. For informationabout enabling access to the developer portal by using classic Azure Active Directory, see How to authorizedeveloper accounts using Azure Active Directory.
To complete the steps in this guide, you must first have an Azure Active Directory B2C tenant to create an application in.Also, you need to have signup and signin policies ready. For more information, see Azure Active Directory B2C overview.
NOTENOTE
1. To get started, click Publisher portal in the Azure portal for your API Management service. This takes youto the API Management publisher portal.
If you haven't yet created an API Management service instance, see Create an API Management service instance inthe Get started with Azure API Management tutorial.
2. On the API Management menu, click Security. On the Identities tab, choose Azure Active DirectoryB2C.
3. Make a note of the Redirect URL and switch over to Azure Active Directory B2C in the Azure portal.
4. Click the Applications button.
5. Click the Add button to create a new Azure Active Directory B2C application.
6. In the New application blade, enter a name for the application. Choose Yes under Web App/Web API,and choose Yes under Allow implicit flow. Then copy the Redirect URL from the Azure ActiveDirectory B2C section of the Identities tab in the publisher portal, and paste it into the Reply URL textbox.
7. Click the Create button. When the application is created, it appears in the Applications blade. Click the
application name to see its details.
8. From the Properties blade, copy the Application ID to the clipboard.
9. Switch back to the publisher portal and paste the ID into the Client Id text box.
10. Switch back to the Azure portal, click the Keys button, and then click Generate key. Click Save to save theconfiguration and display the App key. Copy the key to the clipboard.
11. Switch back to the publisher portal and paste the key into the Client Secret text box.
12. Specify the domain name of the Azure Active Directory B2C tenant in Allowed Tenant.
Sign up for a developer account by using Azure Active Directory B2C
NOTENOTE
13. Specify the Signup Policy and Signin Policy. Optionally, you can also provide the Profile Editing Policyand Password Reset Policy.
For more information on policies, see Azure Active Directory B2C: Extensible policy framework.
14. After you've specified the desired configuration, click Save.
After the changes are saved, developers will be able to create new accounts and sign in to the developerportal by using Azure Active Directory B2C.
1. To sign up for a developer account by using Azure Active Directory B2C, open a new browser window andgo to the developer portal. Click the Sign up button.
Next steps
NOTENOTE
2. Choose to sign up with Azure Active Directory B2C.
3. You're redirected to the signup policy that you configured in the previous section. Choose to sign up byusing your email address or one of your existing social accounts.
If Azure Active Directory B2C is the only option that's enabled on the Identities tab in the publisher portal, you'll beredirected to the signup policy directly.
When the signup is complete, you're redirected back to the developer portal. You're now signed in to thedeveloper portal for your API Management service instance.
Azure Active Directory B2C overviewAzure Active Directory B2C: Extensible policy frameworkUse a Microsoft account as an identity provider in Azure Active Directory B2CUse a Google account as an identity provider in Azure Active Directory B2CUse a LinkedIn account as an identity provider in Azure Active Directory B2CUse a Facebook account as an identity provider in Azure Active Directory B2C
How to delegate user registration and productsubscription4/9/2018 • 5 min to read • Edit Online
Delegating developer sign in and sign-up
Delegation allows you to use your existing website for handling developer sign-in/sign-up and subscription toproducts as opposed to using the built-in functionality in the developer portal. This enables your website to ownthe user data and perform the validation of these steps in a custom way.
To delegate developer sign-in and sign-up to your existing website, you will need to create a special delegationendpoint on your site that acts as the entry-point for any such request initiated from the API Managementdeveloper portal.
The final workflow will be as follows:
1. Developer clicks on the sign-in or sign-up link at the API Management developer portal2. Browser is redirected to the delegation endpoint3. Delegation endpoint in return redirects to or presents UI asking user to sign in or sign-up4. On success, the user is redirected back to the API Management developer portal page they started from
To begin, let's first set-up API Management to route requests via your delegation endpoint. In the API Managementpublisher portal, click on Security and then click the Delegation tab. Click the checkbox to enable 'Delegate sign-in & sign-up'.
Decide what the URL of your special delegation endpoint will be and enter it in the Delegation endpoint URLfield.Within the Delegation authentication key field, enter a secret that will be used to compute a signature providedto you for verification to ensure that the request is indeed coming from Azure API Management. You can clickthe generate button to have API Management randomly generate a key for you.
Delegating product subscription
Now you need to create the delegation endpoint. It has to perform a number of actions:
3. Verify that you are receiving a request for sign-in/sign-up: the operation query parameter will be set to"SignIn".
4. Present the user with UI to sign in or sign-up5. If the user is signing-up you have to create a corresponding account for them in API Management. Create a
user with the API Management REST API. When doing so, ensure that you set the user ID to the same it is inyour user store or to an ID that you can keep track of.
1. Receive a request in the following form:
http://www.yourwebsite.com/apimdelegation?operation=SignIn&returnUrl={URL of sourcepage}&salt={string}&sig={string}
Query parameters for the sign-in / sign up case:
operation: identifies what type of delegation request it is - it can only be SignIn in this casereturnUrl: the URL of the page where the user clicked on a sign-in or sign-up linksalt: a special salt string used for computing a security hashsig: a computed security hash to be used for comparison to your own computed hash
2. Verify that the request is coming from Azure API Management (optional, but highly recommended forsecurity)
Compare the above-computed hash to the value of the sig query parameter. If the two hashes match,move on to the next step, otherwise deny the request.
Compute an HMAC-SHA512 hash of a string based on the returnUrl and salt query parameters(example code provided below):
HMAC(salt + '\n' + returnUrl)
6. When the user is successfully authenticated:
request a single-sign-on (SSO) token via the API Management REST API
redirect the user to the above produced URL
append a returnUrl query parameter to the SSO URL you have received from the API call above:
for example, https://customer.portal.azure-api.net/signin-sso?token&returnUrl=/return/url
In addition to the SignIn operation, you can also perform account management by following the previous stepsand using one of the following operations:
ChangePasswordChangeProfileCloseAccount
You must pass the following query parameters for account management operations.
operation: identifies what type of delegation request it is (ChangePassword, ChangeProfile, or CloseAccount)userId: the user id of the account to managesalt: a special salt string used for computing a security hashsig: a computed security hash to be used for comparison to your own computed hash
Example Code
Delegating product subscription works similarly to delegating user sign-in/-up. The final workflow would be asfollows:
1. Developer selects a product in the API Management developer portal and clicks on the Subscribe button2. Browser is redirected to the delegation endpoint3. Delegation endpoint performs required product subscription steps - this is up to you and may entail redirecting
to another page to request billing information, asking additional questions, or simply storing the informationand not requiring any user action
To enable the functionality, on the Delegation page click Delegate product subscription.
Then ensure the delegation endpoint performs the following actions:
3. Perform any product subscription processing based on the type of operation requested in operation - forexample, billing, further questions, etc.
4. On successfully subscribing the user to the product on your side, subscribe the user to the API Managementproduct by calling the REST API for product subscription.
1. Receive a request in the following form:
http://www.yourwebsite.com/apimdelegation?operation={operation}&productId={product to subscribeto}&userId={user making request}&salt={string}&sig={string}
Query parameters for the product subscription case:
operation: identifies what type of delegation request it is. For product subscription requests the validoptions are:
productId: the ID of the product the user requested to subscribe touserId: the ID of the user for whom the request is madesalt: a special salt string used for computing a security hashsig: a computed security hash to be used for comparison to your own computed hash
"Subscribe": a request to subscribe the user to a given product with provided ID (see below)"Unsubscribe": a request to unsubscribe a user from a product"Renew": a request to renew a subscription (for example, that may be expiring)
2. Verify that the request is coming from Azure API Management (optional, but highly recommended forsecurity)
Compare the above-computed hash to the value of the sig query parameter. If the two hashes match,move on to the next step, otherwise deny the request.
Compute an HMAC-SHA512 of a string based on the productId, userId, and **salt queryparameters:
HMAC(salt + '\n' + productId + '\n' + userId)
These code samples show how to take the delegation validation key, which is set in the Delegation screen of thepublisher portal, to create a HMAC, which is then used to validate the signature, proving the validity of the passedreturnUrl. The same code works for the productId and userId with slight modification.
C# code to generate hash of returnUrl
using System.Security.Cryptography;
string key = "delegation validation key";string returnUrl = "returnUrl query parameter";string salt = "salt query parameter";string signature;using (var encoder = new HMACSHA512(Convert.FromBase64String(key))){ signature = Convert.ToBase64String(encoder.ComputeHash(Encoding.UTF8.GetBytes(salt + "\n" + returnUrl))); // change to (salt + "\n" + productId + "\n" + userId) when delegating product subscription // compare signature to sig query parameter}
var crypto = require('crypto');
var key = 'delegation validation key'; var returnUrl = 'returnUrl query parameter';var salt = 'salt query parameter';
var hmac = crypto.createHmac('sha512', new Buffer(key, 'base64'));var digest = hmac.update(salt + '\n' + returnUrl).digest();// change to (salt + "\n" + productId + "\n" + userId) when delegating product subscription// compare signature to sig query parameter
var signature = digest.toString('base64');
Next steps
NodeJS code to generate hash of returnUrl
For more information on delegation, see the following video:
How to configure notifications and email templates inAzure API Management2/6/2018 • 2 min to read • Edit Online
Prerequisites
Configure notifications
API Management provides the ability to configure notifications for specific events, and to configure the emailtemplates that are used to communicate with the administrators and developers of an API Management instance.This article shows how to configure notifications for the available events, and provides an overview of configuringthe email templates used for these events.
If you do not have an API Management service instance, complete the following quickstart: Create an Azure APIManagement instance.
1. Select your API MANAGEMENT instance.2. Click Notifications to view the available notifications.
The following list of events can be configured for notifications.
Subscription requests (requiring approval) - The specified email recipients and users will receiveemail notifications about subscription requests for API products requiring approval.New subscriptions - The specified email recipients and users will receive email notifications about newAPI product subscriptions.Application gallery requests - The specified email recipients and users will receive email notificationswhen new applications are submitted to the application gallery.BCC - The specified email recipients and users will receive email blind carbon copies of all emails sent todevelopers.New issue or comment - The specified email recipients and users will receive email notifications whena new issue or comment is submitted on the developer portal.
Configure notification templates
4. Press Add.
Close account message - The specified email recipients and users will receive email notifications whenan account is closed.Approaching subscription quota limit - The following email recipients and users will receiveemail notifications when subscription usage gets close to usage quota.
For each event, you can specify email recipients using the email address text box or you can selectusers from a list.
3. To specify the email addresses to be notified, enter them in the email address text box. If you have multipleemail addresses, separate them using commas.
API Management provides notification templates for the email messages that are sent in the course ofadministering and using the service. The following email templates are provided.
Application gallery submission approvedDeveloper farewell letterDeveloper quota limit approaching notificationInvite userNew comment added to an issueNew issue receivedNew subscription activatedSubscription renewed confirmationSubscription request declinesSubscription request received
These templates can be modified as desired.
To view and configure the email templates for your API Management instance, click Notifications templates.
NOTENOTE
Each email template has a subject in plain text, and a body definition in HTML format. Each item can be customizedas desired.
The Parameters list contains a list of parameters, which when inserted into the subject or body, will be replacedthe designated value when the email is sent. To insert a parameter, place the cursor where you wish the parameterto go, and click the arrow to the left of the parameter name.
The parameters are not replaced with actual values when previewing or sending a test.
To save the changes to the email template, click Save, or to cancel the changes click Discard.
How to authorize developer accounts using OAuth2.0 in Azure API Management2/28/2018 • 4 min to read • Edit Online
Prerequisites
NOTENOTE
Configure an OAuth 2.0 authorization server in API Management
NOTENOTE
Many APIs support OAuth 2.0 to secure the API and ensure that only valid users have access, and they can onlyaccess resources to which they're entitled. In order to use Azure API Management's interactive Developer Consolewith such APIs, the service allows you to configure your service instance to work with your OAuth 2.0 enabled API.
This guide shows you how to configure your API Management service instance to use OAuth 2.0 authorization fordeveloper accounts, but does not show you how to configure an OAuth 2.0 provider. The configuration for eachOAuth 2.0 provider is different, although the steps are similar, and the required pieces of information used inconfiguring OAuth 2.0 in your API Management service instance are the same. This topic shows examples usingAzure Active Directory as an OAuth 2.0 provider.
For more information on configuring OAuth 2.0 using Azure Active Directory, see the WebApp-GraphAPI-DotNet sample.
To get started, click Publisher portal in the Azure Portal for your API Management service.
If you have not yet created an API Management service instance, see Create an API Management service instance.
Click Security from the API Management menu on the left, click OAuth 2.0, and then click Add authorizationserver.
NOTENOTE
After clicking Add authorization server, the new authorization server form is displayed.
Enter a name and an optional description in the Name and Description fields.
These fields are used to identify the OAuth 2.0 authorization server within the current API Management service instance andtheir values do not come from the OAuth 2.0 server.
Enter the Client registration page URL. This page is where users can create and manage their accounts, andvaries depending on the OAuth 2.0 provider used. The Client registration page URL points to the page thatusers can use to create and configure their own accounts for OAuth 2.0 providers that support user managementof accounts. Some organizations do not configure or use this functionality even if the OAuth 2.0 provider supportsit. If your OAuth 2.0 provider does not have user management of accounts configured, enter a placeholder URLhere such as the URL of your company, or a URL such as https://placeholder.contoso.com .
The next section of the form contains the Authorization code grant types, Authorization endpoint URL, andAuthorization request method settings.
Specify the Authorization code grant types by checking the desired types. Authorization code is specified bydefault.
Enter the Authorization endpoint URL. For Azure Active Directory, this URL will be similar to the following URL,where <client_id> is replaced with the client id that identifies your application to the OAuth 2.0 server.
https://login.microsoftonline.com/<client_id>/oauth2/authorize
The Authorization request method specifies how the authorization request is sent to the OAuth 2.0 server. Bydefault GET is selected.
The next section is where the Token endpoint URL, Client authentication methods, Access token sendingmethod, and Default scope are specified.
For an Azure Active Directory OAuth 2.0 server, the Token endpoint URL will have the following format, where <APPID> has the format of yourapp.onmicrosoft.com .
https://login.microsoftonline.com/<APPID>/oauth2/token
The default setting for Client authentication methods is Basic, and Access token sending method isAuthorization header. These values are configured on this section of the form, along with the Default scope.
The Client credentials section contains the Client ID and Client secret, which are obtained during the creationand configuration process of your OAuth 2.0 server. Once the Client ID and Client secret are specified, theredirect_uri for the authorization code is generated. This URI is used to configure the reply URL in your OAuth2.0 server configuration.
Configure an API to use OAuth 2.0 user authorization
If Authorization code grant types is set to Resource owner password, the Resource owner passwordcredentials section is used to specify those credentials; otherwise you can leave it blank.
Once the form is complete, click Save to save the API Management OAuth 2.0 authorization server configuration.Once the server configuration is saved, you can configure APIs to use this configuration, as shown in the nextsection.
Click APIs from the API Management menu on the left, click the name of the desired API, click Security, andthen check the box for OAuth 2.0.
Select the desired Authorization server from the drop-down list, and click Save.
Test the OAuth 2.0 user authorization in the Developer Portal
NOTENOTE
Once you have configured your OAuth 2.0 authorization server and configured your API to use that server, youcan test it by going to the Developer Portal and calling an API. Click Developer portal in the top right menu.
Click APIs in the top menu and select Echo API.
If you have only one API configured or visible to your account, then clicking APIs takes you directly to the operations for thatAPI.
Select the GET Resource operation, click Open Console, and then select Authorization code from the drop-down.
NOTENOTE
When Authorization code is selected, a pop-up window is displayed with the sign-in form of the OAuth 2.0provider. In this example the sign-in form is provided by Azure Active Directory.
If you have pop-ups disabled you will be prompted to enable them by the browser. After you enable them, selectAuthorization code again and the sign-in form will be displayed.
Once you have signed in, the Request headers are populated with an Authorization : Bearer header thatauthorizes the request.
Next steps
At this point you can configure the desired values for the remaining parameters, and submit the request.
For more information about using OAuth 2.0 and API Management, see the following video and accompanyingarticle.
How to set or edit Azure API Management policies12/4/2017 • 2 min to read • Edit Online
Set or edit a policy
Configure scope
The policy definition is an XML document that describes a sequence of inbound and outbound statements. TheXML can be edited directly in the definition window. You can also select a predefined policy from the list that isprovided to the right of the policy window. The statements applicable to the current scope are enabled andhighlighted. Clicking an enabled statement adds the appropriate XML at the location of the cursor in the definitionview.
For detailed information about policies, see Policies in Azure API Management.
To set or edit a policy, follow the following steps:
1. Sign in to the Azure portal at https://portal.azure.com.2. Browse to your APIM instance.3. Click the APIs tab.4. Select one of the APIs that you previously imported.5. Select the Design tab.6. Select an operation to which you want to apply the policy. If you want to apply the policy to all operations,
select All operations.7. Click the triangle next to the inbound or outbound pencils.
<policies> <inbound> <base /> </inbound> <backend> <base /> </backend> <outbound> <base /> </outbound> <on-error> <base /> </on-error> </policies>
8. Select the Code editor item.
9. Paste the desired policy code into one of the appropriate blocks.
Policies can be configured globally or at the scope of a Product, API, or Operation. To begin configuring a policy,
Global scopeGlobal scope
Product scopeProduct scope
you must first select the scope at which the policy should apply.
Policy scopes are evaluated in the following order :
1. Global scope2. Product scope3. API scope4. Operation scope
The statements within policies are evaluated according to the placement of the base element, if it is present.Global policy has no parent policy and using the <base> element in it has no effect.
To see the policies in the current scope in the policy editor, click Recalculate effective policy for selected scope.
Global scope is configured for All APIs in your APIM instance.
1. Sign in to the Azure portal and navigate to your APIM instance.
4. Select Code editor.5. Add or edit policies.
2. Click All APIs.
3. Click the triangle icon.
6. Press Save.
The changes are propagated to the API Management gateway immediately.
Product scope is configured for the selected product.
1. Click Products.
2. Select the product to which you want to apply policies.
API scopeAPI scope
Operation scopeOperation scope
Next steps
3. Click Policies.4. Add or edit policies.5. Press Save.
API scope is configured for All Operations of the selected API.
3. Click the triangle icon.4. Select Code editor.5. Add or edit policies.6. Press Save.
1. Select the API you want to apply policies to.
2. Select All operations
Operation scope is configured for the selected operation.
1. Select an API.
4. Select Code editor.5. Add or edit policies.6. Press Save.
2. Select the operation you want to apply policies to.
3. Click the triangle icon.
See the following related topics:
Transform APIsPolicy Reference for a full list of policy statements and their settingsPolicy samples
API Management policy expressions3/14/2018 • 7 min to read • Edit Online
Syntax
Examples@(true)
@((1+1).ToString())
@("Hi There".Length)
@(Regex.Match(context.Response.Headers.GetValueOrDefault("Cache-Control",""), @"max-age=(?<maxAge>\d+)").Groups["maxAge"]?.Value)
@(context.Variables.ContainsKey("maxAge") ? int.Parse((string)context.Variables["maxAge"]) : 3600)
@{ string value; if (context.Request.Headers.TryGetValue("Authorization", out value)) { return Encoding.UTF8.GetString(Convert.FromBase64String(value)); } else { return null; } }
Usage
This article discusses policy expressions syntax is C# 7. Each expression has access to the implicitly providedcontext variable and an allowed subset of .NET Framework types.
For more information:
See how to supply context information to your backend service. Use the Set query string parameter and SetHTTP header policies to supply this information.See how to use the Validate JWT policy to pre-authorize access to operations based on token claims.See how to use an API Inspector trace to see how policies are evaluated and the results of those evaluations.See how to use expressions with the Get from cache and Store to cache policies to configure APIManagement response caching. Set a duration that matches the response caching of the backend service asspecified by the backed service's Cache-Control directive.See how to perform content filtering. Remove data elements from the response received from the backendusing the Control flow and Set body policies.To download the policy statements, see the api-management-samples/policies github repo.
Single statement expressions are enclosed in @(expression) , where expression is a well-formed C# expressionstatement.
Multi-statement expressions are enclosed in @{expression} . All code paths within multi-statement expressionsmust end with a return statement.
IMPORTANTIMPORTANT
.NET Framework types allowed in policy expressions
CLR TYPE SUPPORTED METHODS
Newtonsoft.Json.Linq.Extensions All methods are supported
Newtonsoft.Json.Linq.JArray All methods are supported
Newtonsoft.Json.Linq.JConstructor All methods are supported
Newtonsoft.Json.Linq.JContainer All methods are supported
Newtonsoft.Json.Linq.JObject All methods are supported
Newtonsoft.Json.Linq.JProperty All methods are supported
Newtonsoft.Json.Linq.JRaw All methods are supported
Newtonsoft.Json.Linq.JToken All methods are supported
Newtonsoft.Json.Linq.JTokenType All methods are supported
Newtonsoft.Json.Linq.JValue All methods are supported
System.Collections.Generic.IReadOnlyCollection<T> All
System.Collections.Generic.IReadOnlyDictionary<TKey,TValue>
All
System.Collections.Generic.ISet<TKey, TValue> All
System.Collections.Generic.KeyValuePair<TKey, TValue> Key, Value
System.Collections.Generic.List<TKey, TValue> All
System.Collections.Generic.Queue<TKey, TValue> All
System.Collections.Generic.Stack<TKey, TValue> All
System.Convert All
Expressions can be used as attribute values or text values in any API Management policies (unless the policyreference specifies otherwise).
When you use policy expressions, there is only limited verification of the policy expressions when the policy is defined.Expressions are executed by the gateway at run-time, any exceptions generated by policy expressions result in a runtimeerror.
The following table lists the .NET Framework types and their members that are allowed in policy expressions.
System.DateTime All
System.DateTimeKind Utc
System.DateTimeOffset All
System.Decimal All
System.Double All
System.Guid All
System.IEnumerable<T> All
System.IEnumerator<T> All
System.Int16 All
System.Int32 All
System.Int64 All
System.Linq.Enumerable<T> All methods are supported
System.Math All
System.MidpointRounding All
System.Nullable<T> All
System.Random All
System.SByte All
System.Security.Cryptography. HMACSHA384 All
System.Security.Cryptography. HMACSHA512 All
System.Security.Cryptography.HashAlgorithm All
System.Security.Cryptography.HMAC All
System.Security.Cryptography.HMACMD5 All
System.Security.Cryptography.HMACSHA1 All
System.Security.Cryptography.HMACSHA256 All
System.Security.Cryptography.KeyedHashAlgorithm All
CLR TYPE SUPPORTED METHODS
System.Security.Cryptography.MD5 All
System.Security.Cryptography.RNGCryptoServiceProvider All
System.Security.Cryptography.SHA1 All
System.Security.Cryptography.SHA1Managed All
System.Security.Cryptography.SHA256 All
System.Security.Cryptography.SHA256Managed All
System.Security.Cryptography.SHA384 All
System.Security.Cryptography.SHA384Managed All
System.Security.Cryptography.SHA512 All
System.Security.Cryptography.SHA512Managed All
System.Single All
System.String All
System.StringSplitOptions All
System.Text.Encoding All
System.Text.RegularExpressions.Capture Index, Length, Value
System.Text.RegularExpressions.CaptureCollection Count, Item
System.Text.RegularExpressions.Group Captures, Success
System.Text.RegularExpressions.GroupCollection Count, Item
System.Text.RegularExpressions.Match Empty, Groups, Result
System.Text.RegularExpressions.Regex (Constructor),IsMatch, Match, Matches, Replace
System.Text.RegularExpressions.RegexOptions Compiled, IgnoreCase, IgnorePatternWhitespace, Multiline,None, RightToLeft, Singleline
System.TimeSpan All
System.Tuple All
System.UInt16 All
System.UInt32 All
CLR TYPE SUPPORTED METHODS
System.UInt64 All
System.Uri All
System.Xml.Linq.Extensions All methods are supported
System.Xml.Linq.XAttribute All methods are supported
System.Xml.Linq.XCData All methods are supported
System.Xml.Linq.XComment All methods are supported
System.Xml.Linq.XContainer All methods are supported
System.Xml.Linq.XDeclaration All methods are supported
System.Xml.Linq.XDocument All methods are supported
System.Xml.Linq.XDocumentType All methods are supported
System.Xml.Linq.XElement All methods are supported
System.Xml.Linq.XName All methods are supported
System.Xml.Linq.XNamespace All methods are supported
System.Xml.Linq.XNode All methods are supported
System.Xml.Linq.XNodeDocumentOrderComparer All methods are supported
System.Xml.Linq.XNodeEqualityComparer All methods are supported
System.Xml.Linq.XObject All methods are supported
System.Xml.Linq.XProcessingInstruction All methods are supported
System.Xml.Linq.XText All methods are supported
System.Xml.XmlNodeType All
CLR TYPE SUPPORTED METHODS
Context variable
CONTEX T VARIABLE ALLOWED METHODS, PROPERTIES, AND PARAMETER VALUES
A variable named context is implicitly available in every policy expression. Its members provide informationpertinent to the \request . All of the context members are read-only.
context Api: IApi
Deployment
Elapsed: TimeSpan - time interval between the value ofTimestamp and current time
LastError
Operation
Product
Request
RequestId: Guid - unique request identifier
Response
Subscription
Timestamp: DateTime - point in time when request wasreceived
Tracing: bool - indicates if tracing is on or off
User
Variables: IReadOnlyDictionary<string, object>
void Trace(message: string)
context.Api Id: string
IsRevisionCurrent: bool
Name: string
Path: string
Revision: string
ServiceUrl: IUrl
Version: string
context.Deployment Region: string
ServiceName: string
Certificates: IReadOnlyDictionary<string, X509Certificate2>
CONTEX T VARIABLE ALLOWED METHODS, PROPERTIES, AND PARAMETER VALUES
context.LastError Source: string
Reason: string
Message: string
Scope: string
Section: string
Path: string
PolicyId: string
For more information about context.LastError, see Errorhandling.
context.Operation Id: string
Method: string
Name: string
UrlTemplate: string
context.Product Apis: IEnumerable<IApi>
ApprovalRequired: bool
Groups: IEnumerable<IGroup>
Id: string
Name: string
State: enum ProductState {NotPublished, Published}
SubscriptionLimit: int?
SubscriptionRequired: bool
context.Request Body: IMessageBody
Certificate:System.Security.Cryptography.X509Certificates.X509Certificate2
Headers: IReadOnlyDictionary<string, string[]>
IpAddress: string
MatchedParameters: IReadOnlyDictionary<string, string>
Method: string
OriginalUrl:IUrl
Url: IUrl
CONTEX T VARIABLE ALLOWED METHODS, PROPERTIES, AND PARAMETER VALUES
stringcontext.Request.Headers.GetValueOrDefault(headerName:string, defaultValue: string)
headerName: string
defaultValue: string
Returns comma-separated request header values or defaultValue if the header is not found.
context.Response Body: IMessageBody
Headers: IReadOnlyDictionary<string, string[]>
StatusCode: int
StatusReason: string
stringcontext.Response.Headers.GetValueOrDefault(headerName:string, defaultValue: string)
headerName: string
defaultValue: string
Returns comma-separated response header values or defaultValue if the header is not found.
context.Subscription CreatedTime: DateTime
EndDate: DateTime?
Id: string
Key: string
Name: string
PrimaryKey: string
SecondaryKey: string
StartDate: DateTime?
context.User Email: string
FirstName: string
Groups: IEnumerable<IGroup>
Id: string
Identities: IEnumerable<IUserIdentity>
LastName: string
Note: string
RegistrationDate: DateTime
CONTEX T VARIABLE ALLOWED METHODS, PROPERTIES, AND PARAMETER VALUES
IApi Id: string
Name: string
Path: string
Protocols: IEnumerable<string>
ServiceUrl: IUrl
SubscriptionKeyParameterNames:ISubscriptionKeyParameterNames
IGroup Id: string
Name: string
IMessageBody As<T>(preserveContent: bool = false): Where T: string,JObject, JToken, JArray, XNode, XElement, XDocument
The context.Request.Body.As<T> and context.Response.Body.As<T> methods are used to read a
request and response message bodies in a specified type T .By default the method uses the original message bodystream and renders it unavailable after it returns. To avoidthat by having the method operate on a copy of the bodystream, set the preserveContent parameter to true . Gohere to see an example.
IUrl Host: string
Path: string
Port: int
Query: IReadOnlyDictionary<string, string[]>
QueryString: string
Scheme: string
IUserIdentity Id: string
Provider: string
ISubscriptionKeyParameterNames Header: string
Query: string
string IUrl.Query.GetValueOrDefault(queryParameterName:string, defaultValue: string)
queryParameterName: string
defaultValue: string
Returns comma-separated query parameter values or defaultValue if the parameter is not found.
CONTEX T VARIABLE ALLOWED METHODS, PROPERTIES, AND PARAMETER VALUES
T context.Variables.GetValueOrDefault<T>(variableName:string, defaultValue: T)
variableName: string
defaultValue: T
Returns variable value cast to type T or defaultValue ifthe variable is not found.
This method throws an exception if the specified type doesnot match the actual type of the returned variable.
BasicAuthCredentials AsBasic(input: this string) input: string
If the input parameter contains a valid HTTP BasicAuthentication authorization request header value, themethod returns an object of type BasicAuthCredentials ;otherwise the method returns null.
bool TryParseBasic(input: this string, result: outBasicAuthCredentials)
input: string
result: out BasicAuthCredentials
If the input parameter contains a valid HTTP BasicAuthentication authorization value in the request header themethod returns true and the result parameter contains avalue of type BasicAuthCredentials ; otherwise themethod returns false .
BasicAuthCredentials Password: string
UserId: string
Jwt AsJwt(input: this string) input: string
If the input parameter contains a valid JWT token value, themethod returns an object of type Jwt ; otherwise themethod returns null .
bool TryParseJwt(input: this string, result: out Jwt) input: string
result: out Jwt
If the input parameter contains a valid JWT token value, themethod returns true and the result parameter contains avalue of type Jwt ; otherwise the method returns false .
CONTEX T VARIABLE ALLOWED METHODS, PROPERTIES, AND PARAMETER VALUES
Jwt Algorithm: string
Audience: IEnumerable<string>
Claims: IReadOnlyDictionary<string, string[]>
ExpirationTime: DateTime?
Id: string
Issuer: string
NotBefore: DateTime?
Subject: string
Type: string
string Jwt.Claims.GetValueOrDefault(claimName: string,defaultValue: string)
claimName: string
defaultValue: string
Returns comma-separated claim values or defaultValue ifthe header is not found.
byte[] Encrypt(input: this byte[], alg: string, key:byte[],iv:byte[])
input - plaintext to be encrypted
alg - name of a symmetric encryption algorithm
key - encryption key
iv - initialization vector
Returns encrypted plaintext.
byte[] Encrypt(input: this byte[], alg:System.Security.Cryptography.SymmetricAlgorithm)
input - plaintext to be encrypted
alg - encryption algorithm
Returns encrypted plaintext.
byte[] Encrypt(input: this byte[], alg:System.Security.Cryptography.SymmetricAlgorithm,key:byte[], iv:byte[])
input - plaintext to be encrypted
alg - encryption algorithm
key - encryption key
iv - initialization vector
Returns encrypted plaintext.
CONTEX T VARIABLE ALLOWED METHODS, PROPERTIES, AND PARAMETER VALUES
byte[] Decrypt(input: this byte[], alg: string, key:byte[],iv:byte[])
input - cypher text to be decrypted
alg - name of a symmetric encryption algorithm
key - encryption key
iv - initialization vector
Returns plaintext.
byte[] Decrypt(input: this byte[], alg:System.Security.Cryptography.SymmetricAlgorithm)
input - cypher text to be decrypted
alg - encryption algorithm
Returns plaintext.
byte[] Decrypt(input: this byte[], alg:System.Security.Cryptography.SymmetricAlgorithm,key:byte[], iv:byte[])
input - input - cypher text to be decrypted
alg - encryption algorithm
key - encryption key
iv - initialization vector
Returns plaintext.
CONTEX T VARIABLE ALLOWED METHODS, PROPERTIES, AND PARAMETER VALUES
Next stepsFor more information working with policies, see:
Policies in API ManagementTransform APIsPolicy Reference for a full list of policy statements and their settingsPolicy samples
Custom caching in Azure API Management2/14/2018 • 8 min to read • Edit Online
Architecture
Fragment caching
{ "airline" : "Air Canada", "flightno" : "871", "status" : "ontime", "gate" : "B40", "terminal" : "2A", "userprofile" : "$userprofile$"}
{ "username" : "Bob Smith", "Status" : "Gold" }
Azure API Management service has built-in support for HTTP response caching using the resource URL as thekey. The key can be modified by request headers using the vary-by properties. This is useful for caching entireHTTP responses (aka representations), but sometimes it is useful to just cache a portion of a representation. Thenew cache-lookup-value and cache-store-value policies provide the ability to store and retrieve arbitrary pieces ofdata from within policy definitions. This ability also adds value to the previously introduced send-request policybecause you can now cache responses from external services.
API Management service uses a shared per-tenant data cache so that, as you scale up to multiple units you still getaccess to the same cached data. However, when working with a multi-region deployment there are independentcaches within each of the regions. It is important to not treat the cache as a data store, where it is the only sourceof some piece of information. If you did, and later decided to take advantage of the multi-region deployment, thencustomers with users that travel may lose access to that cached data.
There are certain cases where responses being returned contain some portion of data that is expensive todetermine and yet remains fresh for a reasonable amount of time. As an example, consider a service built by anairline that provides information relating flight reservations, flight status, etc. If the user is a member of the airlinespoints program, they would also have information relating to their current status and accumulated mileage. Thisuser-related information might be stored in a different system, but it may be desirable to include it in responsesreturned about flight status and reservations. This can be done using a process called fragment caching. Theprimary representation can be returned from the origin server using some kind of token to indicate where theuser-related information is to be inserted.
Consider the following JSON response from a backend API.
And secondary resource at /userprofile/{userid} that looks like,
To determine the appropriate user information to include, API Management needs to identify who the end user is.This mechanism is implementation-dependent. As an example, I am using the Subject claim of a JWT token.
<set-variable name="enduserid" value="@(context.Request.Headers.GetValueOrDefault("Authorization","").Split(' ')[1].AsJwt()?.Subject)" />
<cache-lookup-valuekey="@("userprofile-" + context.Variables["enduserid"])"variable-name="userprofile" />
<choose> <when condition="@(!context.Variables.ContainsKey("userprofile"))"> <!-- If the userprofile context variable doesn’t exist, make an HTTP request to retrieve it. --> </when></choose>
<send-request mode="new" response-variable-name="userprofileresponse" timeout="10" ignore-error="true">
<!-- Build a URL that points to the profile for the current end-user --> <set-url>@(new Uri(new Uri("https://apimairlineapi.azurewebsites.net/UserProfile/"), (string)context.Variables["enduserid"]).AbsoluteUri) </set-url> <set-method>GET</set-method></send-request>
<set-variable name="userprofile" value="@(((IResponse)context.Variables["userprofileresponse"]).Body.As<string>())" />
<cache-store-value key="@("userprofile-" + context.Variables["enduserid"])" value="@((string)context.Variables["userprofile"])" duration="100000" />
API Management stores the enduserid value in a context variable for later use. The next step is to determine if aprevious request has already retrieved the user information and stored it in the cache. For this, API Managementuses the cache-lookup-value policy.
If there is no entry in the cache that corresponds to the key value, then no userprofile context variable is created.API Management checks the success of the lookup using the choose control flow policy.
If the userprofile context variable doesn’t exist, then API Management is going to have to make an HTTP requestto retrieve it.
API Management uses the enduserid to construct the URL to the user profile resource. Once API Managementhas the response, it pulls the body text out of the response and stores it back into a context variable.
To avoid API Management from making this HTTP request again, when the same user makes another request, youcan specify to store the user profile in the cache.
API Management stores the value in the cache using the exact same key that API Management originallyattempted to retrieve it with. The duration that API Management chooses to store the value should be based onhow often the information changes and how tolerant users are to out-of-date information.
<!-- Update response body with user profile--><find-and-replace from='"$userprofile$"' to="@((string)context.Variables["userprofile"])" />
It is important to realize that retrieving from the cache is still an out-of-process, network request and potentiallycan still add tens of milliseconds to the request. The benefits come when determining the user profile informationtakes longer than that due to needing to do database queries or aggregate information from multiple back-ends.
The final step in the process is to update the returned response with the user profile information.
You can chose to include the quotation marks as part of the token so that even when the replace doesn’t occur, theresponse is still a valid JSON.
Once you combine all these steps together, the end result is a policy that looks like the following one.
<policies> <inbound> <!-- How you determine user identity is application dependent --> <set-variable name="enduserid" value="@(context.Request.Headers.GetValueOrDefault("Authorization","").Split(' ')[1].AsJwt()?.Subject)" />
<!--Look for userprofile for this user in the cache --> <cache-lookup-value key="@("userprofile-" + context.Variables["enduserid"])" variable-name="userprofile" />
<!-- If API Management doesn’t find it in the cache, make a request for it and store it --> <choose> <when condition="@(!context.Variables.ContainsKey("userprofile"))"> <!-- Make HTTP request to get user profile --> <send-request mode="new" response-variable-name="userprofileresponse" timeout="10" ignore-error="true">
<!-- Build a URL that points to the profile for the current end-user --> <set-url>@(new Uri(new Uri("https://apimairlineapi.azurewebsites.net/UserProfile/"),(string)context.Variables["enduserid"]).AbsoluteUri)</set-url> <set-method>GET</set-method> </send-request>
<!-- Store response body in context variable --> <set-variable name="userprofile" value="@(((IResponse)context.Variables["userprofileresponse"]).Body.As<string>())" />
<!-- Store result in cache --> <cache-store-value key="@("userprofile-" + context.Variables["enduserid"])" value="@((string)context.Variables["userprofile"])" duration="100000" /> </when> </choose> <base /> </inbound> <outbound> <!-- Update response body with user profile--> <find-and-replace from='"$userprofile$"' to="@((string)context.Variables["userprofile"])" /> <base /> </outbound></policies>
Transparent versioning
This caching approach is primarily used in web sites where HTML is composed on the server side so that it can berendered as a single page. It can also be useful in APIs where clients cannot do client-side HTTP caching or it isdesirable not to put that responsibility on the client.
This same kind of fragment caching can also be done on the backend web servers using a Redis caching server,however, using the API Management service to perform this work is useful when the cached fragments arecoming from different back-ends than the primary responses.
It is common practice for multiple different implementation versions of an API to be supported at any one time.For example, to support different environments (dev, test, production, etc.) or to support older versions of the API
<set-variable name="clientid" value="@(context.Subscription.Key)" />
<cache-lookup-valuekey="@("clientversion-" + context.Variables["clientid"])"variable-name="clientversion" />
<choose> <when condition="@(!context.Variables.ContainsKey("clientversion"))">
<send-request mode="new" response-variable-name="clientconfiguresponse" timeout="10" ignore-error="true"> <set-url>@(new Uri(new Uri(context.Api.ServiceUrl.ToString() + "api/ClientConfig/"),(string)context.Variables["clientid"]).AbsoluteUri)</set-url> <set-method>GET</set-method></send-request>
<set-variable name="clientversion" value="@(((IResponse)context.Variables["clientconfiguresponse"]).Body.As<string>())" />
<cache-store-value key="@("clientversion-" + context.Variables["clientid"])" value="@((string)context.Variables["clientversion"])" duration="100000" />
<set-backend-service base-url="@(context.Api.ServiceUrl.ToString() + "api/" + (string)context.Variables["clientversion"] + "/")" />
to give time for API consumers to migrate to newer versions.
One approach to handling this, instead of requiring client developers to change the URLs from /v1/customers to /v2/customers is to store in the consumer’s profile data which version of the API they currently wish to use and
call the appropriate backend URL. To determine the correct backend URL to call for a particular client, it isnecessary to query some configuration data. By caching this configuration data, API Management can minimizethe performance penalty of doing this lookup.
The first step is to determine the identifier used to configure the desired version. In this example, I chose toassociate the version to the product subscription key.
API Management then does a cache lookup to see whether it already retrieved the desired client version.
Then, API Management checks to see if it did not find it in the cache.
If API Management didn’t find it, API Management retrieves it.
Extract the response body text from the response.
Store it back in the cache for future use.
And finally update the back-end URL to select the version of the service desired by the client.
<inbound> <base /> <set-variable name="clientid" value="@(context.Subscription.Key)" /> <cache-lookup-value key="@("clientversion-" + context.Variables["clientid"])" variable-name="clientversion" />
<!-- If API Management doesn’t find it in the cache, make a request for it and store it --> <choose> <when condition="@(!context.Variables.ContainsKey("clientversion"))"> <send-request mode="new" response-variable-name="clientconfiguresponse" timeout="10" ignore-error="true"> <set-url>@(new Uri(new Uri(context.Api.ServiceUrl.ToString() + "api/ClientConfig/"),(string)context.Variables["clientid"]).AbsoluteUri)</set-url> <set-method>GET</set-method> </send-request> <!-- Store response body in context variable --> <set-variable name="clientversion" value="@(((IResponse)context.Variables["clientconfiguresponse"]).Body.As<string>())" /> <!-- Store result in cache --> <cache-store-value key="@("clientversion-" + context.Variables["clientid"])" value="@((string)context.Variables["clientversion"])" duration="100000" /> </when> </choose> <set-backend-service base-url="@(context.Api.ServiceUrl.ToString() + "api/" + (string)context.Variables["clientversion"] + "/")" /></inbound>
Tenant Isolation
Summary
The complete policy is as follows:
Enabling API consumers to transparently control which backend version is being accessed by clients withouthaving to update and redeploy clients is an elegant solution that addresses many API versioning concerns.
In larger, multi-tenant deployments some companies create separate groups of tenants on distinct deployments ofbackend hardware. This minimizes the number of customers who are impacted by a hardware issue on thebackend. It also enables new software versions to be rolled out in stages. Ideally this backend architecture shouldbe transparent to API consumers. This can be achieved in a similar way to transparent versioning because it isbased on the same technique of manipulating the backend URL using configuration state per API key.
Instead of returning a preferred version of the API for each subscription key, you would return an identifier thatrelates a tenant to the assigned hardware group. That identifier can be used to construct the appropriate backendURL.
The freedom to use the Azure API management cache for storing any kind of data enables efficient access toconfiguration data that can affect the way an inbound request is processed. It can also be used to store datafragments that can augment responses, returned from a backend API.
Monitor your APIs with Azure API Management,Event Hubs, and Runscope2/5/2018 • 13 min to read • Edit Online
Why Send From API Management Service?
Why send to an Azure Event Hub?
The API Management service provides many capabilities to enhance the processing of HTTP requests sent to yourHTTP API. However, the existence of the requests and responses is transient. The request is made and it flowsthrough the API Management service to your backend API. Your API processes the request and a response flowsback through to the API consumer. The API Management service keeps some important statistics about the APIsfor display in the Azure portal dashboard, but beyond that, the details are gone.
By using the log-to-eventhub policy in the API Management service, you can send any details from the requestand response to an Azure Event Hub. There are a variety of reasons why you may want to generate events fromHTTP messages being sent to your APIs. Some examples include audit trail of updates, usage analytics, exceptionalerting, and third-party integrations.
This article demonstrates how to capture the entire HTTP request and response message, send it to an Event Huband then relay that message to a third-party service that provides HTTP logging and monitoring services.
It is possible to write HTTP middleware that can plug into HTTP API frameworks to capture HTTP requests andresponses and feed them into logging and monitoring systems. The downside to this approach is the HTTPmiddleware needs to be integrated into the backend API and must match the platform of the API. If there aremultiple APIs, then each one must deploy the middleware. Often there are reasons why backend APIs cannot beupdated.
Using the Azure API Management service to integrate with logging infrastructure provides a centralized andplatform-independent solution. It is also scalable, in part due to the geo-replication capabilities of Azure APIManagement.
It is a reasonable to ask, why create a policy that is specific to Azure Event Hubs? There are many different placeswhere I might want to log my requests. Why not just send the requests directly to the final destination? That is anoption. However, when making logging requests from an API management service, it is necessary to consider howlogging messages impact the performance of the API. Gradual increases in load can be handled by increasingavailable instances of system components or by taking advantage of geo-replication. However, short spikes intraffic can cause requests to be delayed if requests to logging infrastructure start to slow under load.
The Azure Event Hubs is designed to ingress huge volumes of data, with capacity for dealing with a far highernumber of events than the number of HTTP requests most APIs process. The Event Hub acts as a kind ofsophisticated buffer between your API management service and the infrastructure that stores and processes themessages. This ensures that your API performance will not suffer due to the logging infrastructure.
Once the data has been passed to an Event Hub, it is persisted and will wait for Event Hub consumers to process it.The Event Hub does not care how it is processed, it just cares about making sure the message will be successfullydelivered.
Event Hubs has the ability to stream events to multiple consumer groups. This allows events to be processed bydifferent systems. This enables supporting many integration scenarios without putting addition delays on theprocessing of the API request within the API Management service as only one event needs to be generated.
A policy to send application/http messages
<log-to-eventhub logger-id="conferencelogger" partition-id="0">@{ var requestLine = string.Format("{0} {1} HTTP/1.1\r\n", context.Request.Method, context.Request.Url.Path + context.Request.Url.QueryString);
var body = context.Request.Body?.As<string>(true); if (body != null && body.Length > 1024) { body = body.Substring(0, 1024); }
var headers = context.Request.Headers .Where(h => h.Key != "Authorization" && h.Key != "Ocp-Apim-Subscription-Key") .Select(h => string.Format("{0}: {1}", h.Key, String.Join(", ", h.Value))) .ToArray<string>();
var headerString = (headers.Any()) ? string.Join("\r\n", headers) + "\r\n" : string.Empty;
return "request:" + context.Variables["message-id"] + "\n" + requestLine + headerString + "\r\n" + body;}</log-to-eventhub>
Policy declarationPolicy declaration
PartitionsPartitions
An Event Hub accepts event data as a simple string. The contents of that string are up to you. To be able to packageup an HTTP request and send it off to Event Hubs, we need to format the string with the request or responseinformation. In situations like this, if there is an existing format we can reuse, then we may not have to write ourown parsing code. Initially I considered using the HAR for sending HTTP requests and responses. However, thisformat is optimized for storing a sequence of HTTP requests in a JSON-based format. It contained a number ofmandatory elements that added unnecessary complexity for the scenario of passing the HTTP message over thewire.
An alternative option was to use the application/http media type as described in the HTTP specification RFC7230. This media type uses the exact same format that is used to actually send HTTP messages over the wire, butthe entire message can be put in the body of another HTTP request. In our case, we are just going to use the bodyas our message to send to Event Hubs. Conveniently, there is a parser that exists in Microsoft ASP.NET Web API2.2 Client libraries that can parse this format and convert it into the native HttpRequestMessage and HttpResponseMessage objects.
To be able to create this message, we need to take advantage of C# based Policy expressions in Azure APIManagement. Here is the policy, which sends an HTTP request message to Azure Event Hubs.
There a few particular things worth mentioning about this policy expression. The log-to-eventhub policy has anattribute called logger-id, which refers to the name of logger that has been created within the API Managementservice. The details of how to set up an Event Hub logger in the API Management service can be found in thedocument How to log events to Azure Event Hubs in Azure API Management. The second attribute is an optionalparameter that instructs Event Hubs which partition to store the message in. Event Hubs uses partitions to enablescalability and require a minimum of two. The ordered delivery of messages is only guaranteed within a partition.If we do not instruct Event Hub in which partition to place the message, it uses a round-robin algorithm todistribute the load. However, that may cause some of our messages to be processed out of order.
To ensure our messages are delivered to consumers in order and take advantage of the load distribution capabilityof partitions, I chose to send HTTP request messages to one partition and HTTP response messages to a secondpartition. This ensures an even load distribution and we can guarantee that all requests will be consumed in order
HTTP payloadsHTTP payloads
HTTP headersHTTP headers
Message MetadataMessage Metadata
<set-variable name="message-id" value="@(Guid.NewGuid())" />
and all responses are consumed in order. It is possible for a response to be consumed before the correspondingrequest, but as that is not a problem as we have a different mechanism for correlating requests to responses andwe know that requests always come before responses.
After building the requestLine , we check to see if the request body should be truncated. The request body istruncated to only 1024. This could be increased, however individual Event Hub messages are limited to 256 KB, soit is likely that some HTTP message bodies will not fit in a single message. When doing logging and analytics asignificant amount of information can be derived from just the HTTP request line and headers. Also, many APIsrequest only return small bodies and so the loss of information value by truncating large bodies is fairly minimal incomparison to the reduction in transfer, processing, and storage costs to keep all body contents. One final noteabout processing the body is that we need to pass true to the As() method because we are reading the bodycontents, but was also wanted the backend API to be able to read the body. By passing true to this method, wecause the body to be buffered so that it can be read a second time. This is important to be aware of if you have anAPI that does uploading of large files or uses long polling. In these cases, it would be best to avoid reading thebody at all.
HTTP Headers can be transferred over into the message format in a simple key/value pair format. We have chosento strip out certain security sensitive fields, to avoid unnecessarily leaking credential information. It is unlikely thatAPI keys and other credentials would be used for analytics purposes. If we wish to do analysis on the user and theparticular product they are using, then we could get that from the context object and add that to the message.
When building the complete message to send to the event hub, the first line is not actually part of the application/http message. The first line is additional metadata consisting of whether the message is a request or
response message and a message ID, which is used to correlate requests to responses. The message ID is createdby using another policy that looks like this:
We could have created the request message, stored that in a variable until the response was returned and thensent the request and response as a single message. However, by sending the request and response independentlyand using a message id to correlate the two, we get a bit more flexibility in the message size, the ability to takeadvantage of multiple partitions whilst maintaining message order and the request will appear in our loggingdashboard sooner. There also may be some scenarios where a valid response is never sent to the event hub,possibly due to a fatal request error in the API Management service, but we still have a record of the request.
The policy to send the response HTTP message looks similar to the request and so the complete policyconfiguration looks like this:
<policies> <inbound> <set-variable name="message-id" value="@(Guid.NewGuid())" /> <log-to-eventhub logger-id="conferencelogger" partition-id="0"> @{ var requestLine = string.Format("{0} {1} HTTP/1.1\r\n", context.Request.Method, context.Request.Url.Path + context.Request.Url.QueryString);
var body = context.Request.Body?.As<string>(true); if (body != null && body.Length > 1024) { body = body.Substring(0, 1024); }
var headers = context.Request.Headers .Where(h => h.Key != "Authorization" && h.Key != "Ocp-Apim-Subscription-Key") .Select(h => string.Format("{0}: {1}", h.Key, String.Join(", ", h.Value))) .ToArray<string>();
var headerString = (headers.Any()) ? string.Join("\r\n", headers) + "\r\n" : string.Empty;
return "request:" + context.Variables["message-id"] + "\n" + requestLine + headerString + "\r\n" + body; } </log-to-eventhub> </inbound> <backend> <forward-request follow-redirects="true" /> </backend> <outbound> <log-to-eventhub logger-id="conferencelogger" partition-id="1"> @{ var statusLine = string.Format("HTTP/1.1 {0} {1}\r\n", context.Response.StatusCode, context.Response.StatusReason);
var body = context.Response.Body?.As<string>(true); if (body != null && body.Length > 1024) { body = body.Substring(0, 1024); }
var headers = context.Response.Headers .Select(h => string.Format("{0}: {1}", h.Key, String.Join(", ", h.Value))) .ToArray<string>();
var headerString = (headers.Any()) ? string.Join("\r\n", headers) + "\r\n" : string.Empty;
return "response:" + context.Variables["message-id"] + "\n" + statusLine + headerString + "\r\n" + body; } </log-to-eventhub> </outbound></policies>
Receiving events from Event Hubs
The set-variable policy creates a value that is accessible by both the log-to-eventhub policy in the <inbound>
section and the <outbound> section.
Events from Azure Event Hub are received using the AMQP protocol. The Microsoft Service Bus team have madeclient libraries available to make the consuming events easier. There are two different approaches supported, one is
EventProcessorHostEventProcessorHost
IEventProcessorIEventProcessor
async Task IEventProcessor.ProcessEventsAsync(PartitionContext context, IEnumerable<EventData> messages){
foreach (EventData eventData in messages) { _Logger.LogInfo(string.Format("Event received from partition: {0} - {1}", context.Lease.PartitionId,eventData.PartitionKey));
try { var httpMessage = HttpMessage.Parse(eventData.GetBodyStream()); await _MessageContentProcessor.ProcessHttpMessage(httpMessage); } catch (Exception ex) { _Logger.LogError(ex.Message); } } ... checkpointing code snipped ...}
HttpMessageHttpMessage
public class HttpMessage{ public Guid MessageId { get; set; } public bool IsRequest { get; set; } public HttpRequestMessage HttpRequestMessage { get; set; } public HttpResponseMessage HttpResponseMessage { get; set; }
... parsing code snipped ...
}
being a Direct Consumer and the other is using the EventProcessorHost class. Examples of these two approachescan be found in the Event Hubs Programming Guide. The short version of the differences is, Direct Consumer
gives you complete control and the EventProcessorHost does some of the plumbing work for you but makescertain assumptions about how you process those events.
In this sample, we use the EventProcessorHost for simplicity, however it may not the best choice for this particularscenario. EventProcessorHost does the hard work of making sure you don't have to worry about threading issueswithin a particular event processor class. However, in our scenario, we are simply converting the message toanother format and passing it along to another service using an async method. There is no need for updatingshared state and therefore no risk of threading issues. For most scenarios, EventProcessorHost is probably the bestchoice and it is certainly the easier option.
The central concept when using EventProcessorHost is to create an implementation of the IEventProcessor
interface, which contains the method ProcessEventAsync . The essence of that method is shown here:
A list of EventData objects are passed into the method and we iterate over that list. The bytes of each method areparsed into an HttpMessage object and that object is passed to an instance of IHttpMessageProcessor.
The HttpMessage instance contains three pieces of data:
The HttpMessage instance contains a MessageId GUID that allows us to connect the HTTP request to thecorresponding HTTP response and a boolean value that identifies if the object contains an instance of aHttpRequestMessage and HttpResponseMessage. By using the built-in HTTP classes from System.Net.Http , I was
IHttpMessageProcessorIHttpMessageProcessor
Forwarding the HTTP message
public class RunscopeHttpMessageProcessor : IHttpMessageProcessor{ private HttpClient _HttpClient; private ILogger _Logger; private string _BucketKey; public RunscopeHttpMessageProcessor(HttpClient httpClient, ILogger logger) { _HttpClient = httpClient; var key = Environment.GetEnvironmentVariable("APIMEVENTS-RUNSCOPE-KEY", EnvironmentVariableTarget.User); _HttpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("bearer", key); _HttpClient.BaseAddress = new Uri("https://api.runscope.com"); _BucketKey = Environment.GetEnvironmentVariable("APIMEVENTS-RUNSCOPE-BUCKET", EnvironmentVariableTarget.User); _Logger = logger; }
public async Task ProcessHttpMessage(HttpMessage message) { var runscopeMessage = new RunscopeMessage() { UniqueIdentifier = message.MessageId };
if (message.IsRequest) { _Logger.LogInfo("Sending HTTP request " + message.MessageId.ToString()); runscopeMessage.Request = await RunscopeRequest.CreateFromAsync(message.HttpRequestMessage); } else { _Logger.LogInfo("Sending HTTP response " + message.MessageId.ToString()); runscopeMessage.Response = await RunscopeResponse.CreateFromAsync(message.HttpResponseMessage); }
var messagesLink = new MessagesLink() { Method = HttpMethod.Post }; messagesLink.BucketKey = _BucketKey; messagesLink.RunscopeMessage = runscopeMessage; var runscopeResponse = await _HttpClient.SendAsync(messagesLink.CreateRequest()); _Logger.LogDebug("Request sent to Runscope"); }}
able to take advantage of the application/http parsing code that is included in System.Net.Http.Formatting .
The HttpMessage instance is then forwarded to implementation of IHttpMessageProcessor , which is an interface Icreated to decouple the receiving and interpretation of the event from Azure Event Hub and the actual processingof it.
For this sample, I decided it would be interesting to push the HTTP Request over to Runscope. Runscope is acloud-based service that specializes in HTTP debugging, logging and monitoring. They have a free tier, so it is easyto try and it allows us to see the HTTP requests in real time flowing through our API Management service.
The IHttpMessageProcessor implementation looks like this,
I was able to take advantage of an existing client library for Runscope that makes it easy to push HttpRequestMessage and HttpResponseMessage instances up into their service. In order to access the Runscope API,
you need an account and an API Key. Instructions for getting an API key can be found in the Creating Applicationsto Access Runscope API screencast.
Complete sample
Summary
Next steps
The source code and tests for the sample are on GitHub. You need an API Management Service, a connected EventHub, and a Storage Account to run the sample for yourself.
The sample is just a simple Console application that listens for events coming from Event Hub, converts them intoa HttpRequestMessage and HttpResponseMessage objects and then forwards them on to the Runscope API.
In the following animated image, you can see a request being made to an API in the Developer Portal, the Consoleapplication showing the message being received, processed, and forwarded and then the request and responseshowing up in the Runscope Traffic inspector.
Azure API Management service provides an ideal place to capture the HTTP traffic traveling to and from yourAPIs. Azure Event Hubs is a highly scalable, low-cost solution for capturing that traffic and feeding it intosecondary processing systems for logging, monitoring, and other sophisticated analytics. Connecting to third-partytraffic monitoring systems like Runscope is as simple as a few dozen lines of code.
Learn more about Azure Event Hubs
Learn more about API Management and Event Hubs integration
Get started with Azure Event HubsReceive messages with EventProcessorHostEvent Hubs programming guide
How to log events to Azure Event Hubs in Azure API ManagementLogger entity referencelog-to-eventhub policy reference
Advanced request throttling with Azure APIManagement3/6/2018 • 3 min to read • Edit Online
Product-based throttling
Custom key based throttling
IP Address throttling
<rate-limit-by-key calls="10" renewal-period="60" counter-key="@(context.Request.IpAddress)" />
<quota-by-key calls="1000000" bandwidth="10000" renewal-period="2629800" counter-key="@(context.Request.IpAddress)" />
User identity throttling
<rate-limit-by-key calls="10" renewal-period="60" counter-key="@(context.Request.Headers.GetValueOrDefault("Authorization","").AsJwt()?.Subject)" />
Being able to throttle incoming requests is a key role of Azure API Management. Either by controlling the rate ofrequests or the total requests/data transferred, API Management allows API providers to protect their APIs fromabuse and create value for different API product tiers.
To date, the rate throttling capabilities have been limited to being scoped to a particular Product subscription,defined in the Azure portal. This is useful for the API provider to apply limits on the developers who have signedup to use their API, however, it does not help, for example, in throttling individual end users of the API. It is possiblethat for single user of the developer's application to consume the entire quota and then prevent other customers ofthe developer from being able to use the application. Also, several customers who might generate a high volume ofrequests may limit access to occasional users.
The new rate-limit-by-key and quota-by-key policies provide a more flexible solution to traffic control. These newpolicies allow you to define expressions to identify the keys that are used to track traffic usage. The way this worksis easiest illustrated with an example.
The following policies restrict a single client IP address to only 10 calls every minute, with a total of 1,000,000 callsand 10,000 kilobytes of bandwidth per month.
If all clients on the Internet used a unique IP address, this might be an effective way of limiting usage by user.However, it is likely that multiple users are sharing a single public IP address due to them accessing the Internet viaa NAT device. Despite this, for APIs that allow unauthenticated access the IpAddress might be the best option.
If an end user is authenticated, then a throttling key can be generated based on information that uniquely identifiesthat user.
Combined policies
Client driven throttling
<rate-limit-by-key calls="100" renewal-period="60" counter-key="@(request.Headers.GetValueOrDefault("Rate-Key",""))"/>
Summary
Next steps
This example shows how to extract the Authorization header, convert it to JWT object and use the subject of thetoken to identify the user and use that as the rate limiting key. If the user identity is stored in the JWT as one of theother claims, then that value could be used in its place.
Although the new throttling policies provide more control than the existing throttling policies, there is still valuecombining both capabilities. Throttling by product subscription key (Limit call rate by subscription and Set usagequota by subscription) is a great way to enable monetizing of an API by charging based on usage levels. The finergrained control of being able to throttle by user is complementary and prevents one user's behavior fromdegrading the experience of another.
When the throttling key is defined using a policy expression, then it is the API provider that is choosing how thethrottling is scoped. However, a developer might want to control how they rate limit their own customers. Thiscould be enabled by the API provider by introducing a custom header to allow the developer's client application tocommunicate the key to the API.
This enables the developer's client application to choose how they want to create the rate limiting key. The clientdevelopers could create their own rate tiers by allocating sets of keys to users and rotating the key usage.
Azure API Management provides rate and quote throttling to both protect and add value to your API service. Thenew throttling policies with custom scoping rules allow you finer grained control over those policies to enable yourcustomers to build even better applications. The examples in this article demonstrate the use of these new policiesby manufacturing rate limiting keys with client IP addresses, user identity, and client generated values. However,there are many other parts of the message that could be used such as user agent, URL path fragments, messagesize.
Please give us your feedback in the Disqus thread for this topic. It would be great to hear about other potential keyvalues that have been a logical choice in your scenarios.
Using external services from the Azure APIManagement service2/28/2018 • 8 min to read • Edit Online
Send-One-Way-Request
Alerting with SlackAlerting with Slack
<choose> <when condition="@(context.Response.StatusCode >= 500)"> <send-one-way-request mode="new"> <set-url>https://hooks.slack.com/services/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</set-url> <set-method>POST</set-method> <set-body>@{ return new JObject( new JProperty("username","APIM Alert"), new JProperty("icon_emoji", ":ghost:"), new JProperty("text", String.Format("{0} {1}\nHost: {2}\n{3} {4}\n User: {5}", context.Request.Method, context.Request.Url.Path + context.Request.Url.QueryString, context.Request.Url.Host, context.Response.StatusCode, context.Response.StatusReason, context.User.Email )) ).ToString(); }</set-body> </send-one-way-request> </when></choose>
The policies available in Azure API Management service can do a wide range of useful work based purely on theincoming request, the outgoing response, and basic configuration information. However, being able to interact withexternal services from API Management policies opens up many more opportunities.
You have previously seen how to interact with the Azure Event Hub service for logging, monitoring, and analytics.This article demonstrates policies that allow you to interact with any external HTTP-based service. These policiescan be used for triggering remote events or for retrieving information that is used to manipulate the originalrequest and response in some way.
Possibly the simplest external interaction is the fire-and-forget style of request that allows an external service to benotified of some kind of important event. The control flow policy choose can be used to detect any kind ofcondition that you are interested in. If the condition is satisfied, you can make an external HTTP request using thesend-one-way-request policy. This could be a request to a messaging system like Hipchat or Slack, or a mail APIlike SendGrid or MailChimp, or for critical support incidents something like PagerDuty. All of these messagingsystems have simple HTTP APIs that can be invoked.
The following example demonstrates how to send a message to a Slack chat room if the HTTP response statuscode is greater than or equal to 500. A 500 range error indicates a problem with the backend API that the client ofthe API cannot resolve themselves. It usually requires some kind of intervention on API Management part.
Slack has the notion of inbound web hooks. When configuring an inbound web hook, Slack generates a specialURL, which allows you to do a simple POST request and to pass a message into the Slack channel. The JSON bodythat you create is based on a format defined by Slack.
Is fire and forget good enough?Is fire and forget good enough?
Send-Request
Authorizing reference tokensAuthorizing reference tokens
Standardized introspectionStandardized introspection
Extracting the tokenExtracting the token
<set-variable name="token" value="@(context.Request.Headers.GetValueOrDefault("Authorization","scheme param").Split(' ').Last())" />
Making the validation requestMaking the validation request
There are certain tradeoffs when using a fire-and-forget style of request. If for some reason, the request fails, thenthe failure is not be reported. In this particular situation, the complexity of having a secondary failure reportingsystem and the additional performance cost of waiting for the response is not warranted. For scenarios where it isessential to check the response, then the send-request policy is a better option.
The send-request policy enables using an external service to perform complex processing functions and returndata to the API management service that can be used for further policy processing.
A major function of API Management is protecting backend resources. If the authorization server used by your APIcreates JWT tokens as part of its OAuth2 flow, as Azure Active Directory does, then you can use the validate-jwt
policy to verify the validity of the token. Some authorization servers create what are called reference tokens thatcannot be verified without making a callback to the authorization server.
In the past, there has been no standardized way of verifying a reference token with an authorization server.However a recently proposed standard RFC 7662 was published by the IETF that defines how a resource servercan verify the validity of a token.
The first step is to extract the token from the Authorization header. The header value should be formatted with the Bearer authorization scheme, a single space, and then the authorization token as per RFC 6750. Unfortunately
there are cases where the authorization scheme is omitted. To account for this when parsing, API Managementsplits the header value on a space and selects the last string from the returned array of strings. This provides aworkaround for badly formatted authorization headers.
Once API Management has the authorization token, API Management can make the request to validate the token.RFC 7662 calls this process introspection and requires that you POST an HTML form to the introspection resource.The HTML form must at least contain a key/value pair with the key token . This request to the authorization servermust also be authenticated, to ensure that malicious clients cannot go trawling for valid tokens.
<send-request mode="new" response-variable-name="tokenstate" timeout="20" ignore-error="true"> <set-url>https://microsoft-apiappec990ad4c76641c6aea22f566efc5a4e.azurewebsites.net/introspection</set-url> <set-method>POST</set-method> <set-header name="Authorization" exists-action="override"> <value>basic dXNlcm5hbWU6cGFzc3dvcmQ=</value> </set-header> <set-header name="Content-Type" exists-action="override"> <value>application/x-www-form-urlencoded</value> </set-header> <set-body>@($"token={(string)context.Variables["token"]}")</set-body></send-request>
Checking the responseChecking the response
Reporting failureReporting failure
<choose> <when condition="@((bool)((IResponse)context.Variables["tokenstate"]).Body.As<JObject>()["active"] == false)"> <return-response response-variable-name="existing response variable"> <set-status code="401" reason="Unauthorized" /> <set-header name="WWW-Authenticate" exists-action="override"> <value>Bearer error="invalid_token"</value> </set-header> </return-response> </when></choose>
Final solutionFinal solution
The response-variable-name attribute is used to give access the returned response. The name defined in thisproperty can be used as a key into the context.Variables dictionary to access the IResponse object.
From the response object, you can retrieve the body and RFC 7622 tells API Management that the response mustbe a JSON object and must contain at least a property called active that is a boolean value. When active is truethen the token is considered valid.
You can use a <choose> policy to detect if the token is invalid and if so, return a 401 response.
As per RFC 6750 which describes how bearer tokens should be used, API Management also returns a WWW-Authenticate header with the 401 response. The WWW-Authenticate is intended to instruct a client on how to
construct a properly authorized request. Due to the wide variety of approaches possible with the OAuth2framework, it is difficult to communicate all the needed information. Fortunately there are efforts underway to helpclients discover how to properly authorize requests to a resource server.
At the end, you get the following policy:
<inbound> <!-- Extract Token from Authorization header parameter --> <set-variable name="token" value="@(context.Request.Headers.GetValueOrDefault("Authorization","scheme param").Split(' ').Last())" />
<!-- Send request to Token Server to validate token (see RFC 7662) --> <send-request mode="new" response-variable-name="tokenstate" timeout="20" ignore-error="true"> <set-url>https://microsoft-apiappec990ad4c76641c6aea22f566efc5a4e.azurewebsites.net/introspection</set-url> <set-method>POST</set-method> <set-header name="Authorization" exists-action="override"> <value>basic dXNlcm5hbWU6cGFzc3dvcmQ=</value> </set-header> <set-header name="Content-Type" exists-action="override"> <value>application/x-www-form-urlencoded</value> </set-header> <set-body>@($"token={(string)context.Variables["token"]}")</set-body> </send-request>
<choose> <!-- Check active property in response --> <when condition="@((bool)((IResponse)context.Variables["tokenstate"]).Body.As<JObject>()["active"] == false)"> <!-- Return 401 Unauthorized with http-problem payload --> <return-response response-variable-name="existing response variable"> <set-status code="401" reason="Unauthorized" /> <set-header name="WWW-Authenticate" exists-action="override"> <value>Bearer error="invalid_token"</value> </set-header> </return-response> </when> </choose> <base /></inbound>
Response Composition
Building a dashboardBuilding a dashboard
Faking the resourceFaking the resource
This is only one of many examples of how the send-request policy can be used to integrate useful external servicesinto the process of requests and responses flowing through the API Management service.
The send-request policy can be used for enhancing a primary request to a backend system, as you saw in theprevious example, or it can be used as a complete replace for of the backend call. Using this technique you caneasily create composite resources that are aggregated from multiple different systems.
Sometimes you want to be able to expose information that exists in multiple backend systems, for example, to drivea dashboard. The KPIs come from all different back-ends, but you would prefer not to provide direct access to themand it would be nice if all the information could be retrieved in a single request. Perhaps some of the backendinformation needs some slicing and dicing and a little sanitizing first! Being able to cache that composite resourcewould be a useful to reduce the backend load as you know users have a habit of hammering the F5 key in order tosee if their underperforming metrics might change.
The first step to building the dashboard resource is to configure a new operation in the Azure portal. This is aplaceholder operation used to configure a composition policy to build the dynamic resource.
Making the requestsMaking the requests
<set-variable name="fromDate" value="@(context.Request.Url.Query["fromDate"].Last())"><set-variable name="toDate" value="@(context.Request.Url.Query["toDate"].Last())">
Once the operation has been created, you can configure a policy specifically for that operation.
The first step is to extract any query parameters from the incoming request, so that you can forward them to thebackend. In this example, the dashboard is showing information based on a period of time and therefore has a fromDate and toDate parameter. You can use the set-variable policy to extract the information from the request
URL.
Once you have this information, you can make requests to all the backend systems. Each request constructs a newURL with the parameter information and calls its respective server and stores the response in a context variable.
<send-request mode="new" response-variable-name="revenuedata" timeout="20" ignore-error="true"> <set-url>@($"https://accounting.acme.com/salesdata?from={(string)context.Variables["fromDate"]}&to={(string)context.Variables["fromDate"]}")"</set-url> <set-method>GET</set-method></send-request>
<send-request mode="new" response-variable-name="materialdata" timeout="20" ignore-error="true"> <set-url>@($"https://inventory.acme.com/materiallevels?from={(string)context.Variables["fromDate"]}&to={(string)context.Variables["fromDate"]}")"</set-url> <set-method>GET</set-method></send-request>
<send-request mode="new" response-variable-name="throughputdata" timeout="20" ignore-error="true"><set-url>@($"https://production.acme.com/throughput?from={(string)context.Variables["fromDate"]}&to={(string)context.Variables["fromDate"]}")"</set-url> <set-method>GET</set-method></send-request>
<send-request mode="new" response-variable-name="accidentdata" timeout="20" ignore-error="true"><set-url>@($"https://production.acme.com/throughput?from={(string)context.Variables["fromDate"]}&to={(string)context.Variables["fromDate"]}")"</set-url> <set-method>GET</set-method></send-request>
RespondingResponding
<return-response response-variable-name="existing response variable"> <set-status code="200" reason="OK" /> <set-header name="Content-Type" exists-action="override"> <value>application/json</value> </set-header> <set-body> @(new JObject(new JProperty("revenuedata",((IResponse)context.Variables["revenuedata"]).Body.As<JObject>()), new JProperty("materialdata",((IResponse)context.Variables["materialdata"]).Body.As<JObject>()), new JProperty("throughputdata",((IResponse)context.Variables["throughputdata"]).Body.As<JObject>()), new JProperty("accidentdata",((IResponse)context.Variables["accidentdata"]).Body.As<JObject>()) ).ToString()) </set-body></return-response>
These requests execute in sequence, which is not ideal.
To construct the composite response, you can use the return-response policy. The set-body element can use anexpression to construct a new JObject with all the component representations embedded as properties.
The complete policy looks as follows:
<policies> <inbound>
<set-variable name="fromDate" value="@(context.Request.Url.Query["fromDate"].Last())"> <set-variable name="toDate" value="@(context.Request.Url.Query["toDate"].Last())">
<send-request mode="new" response-variable-name="revenuedata" timeout="20" ignore-error="true"> <set-url>@($"https://accounting.acme.com/salesdata?from={(string)context.Variables["fromDate"]}&to={(string)context.Variables["fromDate"]}")"</set-url> <set-method>GET</set-method> </send-request>
<send-request mode="new" response-variable-name="materialdata" timeout="20" ignore-error="true"> <set-url>@($"https://inventory.acme.com/materiallevels?from={(string)context.Variables["fromDate"]}&to={(string)context.Variables["fromDate"]}")"</set-url> <set-method>GET</set-method> </send-request>
<send-request mode="new" response-variable-name="throughputdata" timeout="20" ignore-error="true"> <set-url>@($"https://production.acme.com/throughput?from={(string)context.Variables["fromDate"]}&to={(string)context.Variables["fromDate"]}")"</set-url> <set-method>GET</set-method> </send-request>
<send-request mode="new" response-variable-name="accidentdata" timeout="20" ignore-error="true"> <set-url>@($"https://production.acme.com/throughput?from={(string)context.Variables["fromDate"]}&to={(string)context.Variables["fromDate"]}")"</set-url> <set-method>GET</set-method> </send-request>
<return-response response-variable-name="existing response variable"> <set-status code="200" reason="OK" /> <set-header name="Content-Type" exists-action="override"> <value>application/json</value> </set-header> <set-body> @(new JObject(new JProperty("revenuedata",((IResponse)context.Variables["revenuedata"]).Body.As<JObject>()), new JProperty("materialdata",((IResponse)context.Variables["materialdata"]).Body.As<JObject>()), new JProperty("throughputdata",((IResponse)context.Variables["throughputdata"]).Body.As<JObject>()), new JProperty("accidentdata",((IResponse)context.Variables["accidentdata"]).Body.As<JObject>()) ).ToString()) </set-body> </return-response> </inbound> <backend> <base /> </backend> <outbound> <base /> </outbound></policies>
Summary
In the configuration of the placeholder operation, you can configure the dashboard resource to be cached for atleast an hour.
Azure API Management service provides flexible policies that can be selectively applied to HTTP traffic and enablescomposition of backend services. Whether you want to enhance your API gateway with alerting functions,verification, validation capabilities or create new composite resources based on multiple backend services, the
send-request and related policies open a world of possibilities.
How to use properties in Azure API Managementpolicies1/26/2018 • 4 min to read • Edit Online
ATTRIBUTE TYPE DESCRIPTION
Display name string Alphanumeric string used forreferencing the property in the policies.
Value string The value of the property. It may not beempty or consist only of whitespace.
Secret boolean Determines whether the value is asecret and should be encrypted or not.
Tags array of string Optional tags that when provided canbe used to filter the property list.
API Management policies are a powerful capability of the system that allow the Azure portal to change thebehavior of the API through configuration. Policies are a collection of statements that are executed sequentially onthe request or response of an API. Policy statements can be constructed using literal text values, policy expressions,and properties.
Each API Management service instance has a properties collection of key/value pairs that are global to the serviceinstance. These properties can be used to manage constant string values across all API configuration and policies.Each property can have the following attributes:
Property values can contain literal strings and policy expressions. For example, the value of ExpressionProperty isa policy expression that returns a string containing the current date and time. The property ContosoHeaderValue ismarked as a secret, so its value is not displayed.
NAME VALUE SECRET TAGS
ContosoHeader TrackingId False Contoso
ContosoHeaderValue •••••••••••••••••••••• True Contoso
ExpressionProperty @(DateTime.Now.ToString()) False
To add and edit a property
To delete a property
IMPORTANTIMPORTANT
To search and filter properties
1. Select APIs from under API MANAGEMENT.2. Select Named values.
4. Click Create.
3. Press +Add.
Name and Value are required values. If this property value is a secret, check the This is a secret checkbox.Enter one or more optional tags to help with organizing your properties, and click Save.
Once the property is created, you can edit it by clicking on the property. If you change the property name, anypolicies that reference that property are automatically updated to use the new name.
For information on editing a property using the REST API, see Edit a property using the REST API.
To delete a property, click Delete beside the property to delete.
If the property is referenced by any policies, you will be unable to successfully delete it until you remove the property from allpolicies that use it.
For information on deleting a property using the REST API, see Delete a property using the REST API.
To use a property
<set-header name="{{ContosoHeader}}" exists-action="override"> <value>{{ContosoHeaderValue}}</value></set-header>
<set-header name="CustomHeader" exists-action="override"> <value>{{ExpressionProperty}}</value></set-header>
The Named values tab includes searching and filtering capabilities to help you manage your properties. To filterthe property list by property name, enter a search term in the Search property textbox. To display all properties,clear the Search property textbox and press enter.
To filter the property list by tag values, enter one or more tags into the Filter by tags textbox. To display allproperties, clear the Filter by tags textbox and press enter.
To use a property in a policy, place the property name inside a double pair of braces like {{ContosoHeader}} , asshown in the following example:
In this example, ContosoHeader is used as the name of a header in a set-header policy, and ContosoHeaderValue isused as the value of that header. When this policy is evaluated during a request or response to the APIManagement gateway, {{ContosoHeader}} and {{ContosoHeaderValue}} are replaced with their respective propertyvalues.
Properties can be used as complete attribute or element values as shown in the previous example, but they canalso be inserted into or combined with part of a literal text expression as shown in the following example: <set-header name = "CustomHeader{{ContosoHeader}}" ...>
Properties can also contain policy expressions. In the following example, the ExpressionProperty is used.
When this policy is evaluated, {{ExpressionProperty}} is replaced with its value: @(DateTime.Now.ToString()) . Sincethe value is a policy expression, the expression is evaluated and the policy proceeds with its execution.
You can test this out in the developer portal by calling an operation that has a policy with properties in scope. Inthe following example, an operation is called with the two previous example set-header policies with properties.Note that the response contains two custom headers that were configured using policies with properties.
If you look at the API Inspector trace for a call that includes the two previous sample policies with properties, youcan see the two set-header policies with the property values inserted as well as the policy expression evaluation
Next steps
for the property that contained the policy expression.
While property values can contain policy expressions, property values can't contain other properties. If textcontaining a property reference is used for a property value, such as Property value text {{MyProperty}} , thatproperty reference won't be replaced and will be included as part of the property value.
Learn more about working with policiesPolicies in API ManagementPolicy referencePolicy expressions
How to secure APIs using client certificateauthentication in API Management12/7/2017 • 1 min to read • Edit Online
Checking the expiration date
<choose> <when condition="@(context.Request.Certificate == null || context.Request.Certificate.NotAfter < DateTime.Now)" > <return-response> <set-status code="403" reason="Invalid client certificate" /> </return-response> </when></choose>
Checking the issuer and subject
<choose> <when condition="@(context.Request.Certificate == null || context.Request.Certificate.Issuer != "trusted-issuer" || context.Request.Certificate.SubjectName != "expected-subject-name")" > <return-response> <set-status code="403" reason="Invalid client certificate" /> </return-response> </when></choose>
Checking the thumbprint
<choose> <when condition="@(context.Request.Certificate == null || context.Request.Certificate.Thumbprint != "desired-thumbprint")" > <return-response> <set-status code="403" reason="Invalid client certificate" /> </return-response> </when></choose>
API Management provides the capability to secure access to APIs (i.e., client to API Management) using clientcertificates. Currently, you can check the thumbprint of a client certificate against a desired value. You can alsocheck the thumbprint against existing certificates uploaded to API Management.
For information about securing access to the back-end service of an API using client certificates (i.e., APIManagement to back-end), see How to secure back-end services using client certificate authentication
Below policies can be configured to check if the certificate is expired:
Below policies can be configured to check the issuer and subject of a client certificate:
Below policies can be configured to check the thumbprint of a client certificate:
Checking a thumbprint against certificates uploaded to APIManagement
<choose> <when condition="@(context.Request.Certificate == null || !context.Deployment.Certificates.Any(c => c.Value.Thumbprint == context.Request.Certificate.Thumbprint))" > <return-response> <set-status code="403" reason="Invalid client certificate" /> </return-response> </when></choose>
Next step
The following example shows how to check the thumbprint of a client certificate against certificates uploaded toAPI Management:
How to secure back-end services using client certificate authenticationHow to upload certificates
API Management access restriction policies2/16/2018 • 13 min to read • Edit Online
Access restriction policies
Check HTTP header
Policy statementPolicy statement
<check-header name="header name" failed-check-httpcode="code" failed-check-error-message="message" ignore-case="True"> <value>Value1</value> <value>Value2</value> </check-header>
ExampleExample
<check-header name="Authorization" failed-check-httpcode="401" failed-check-error-message="Not authorized" ignore-case="false"> <value>f6dc69a089844cf6b2019bae6d36fac8</value> </check-header>
ElementsElements
NAME DESCRIPTION REQUIRED
check-header Root element. Yes
value Allowed HTTP header value. Whenmultiple value elements are specified,the check is considered a success if anyone of the values is a match.
No
This topic provides a reference for the following API Management policies. For information on adding andconfiguring policies, see Policies in API Management.
Check HTTP header - Enforces existence and/or value of a HTTP Header.Limit call rate by subscription - Prevents API usage spikes by limiting call rate, on a per subscription basis.Limit call rate by key - Prevents API usage spikes by limiting call rate, on a per key basis.Restrict caller IPs - Filters (allows/denies) calls from specific IP addresses and/or address ranges.Set usage quota by subscription - Allows you to enforce a renewable or lifetime call volume and/or bandwidthquota, on a per subscription basis.Set usage quota by key - Allows you to enforce a renewable or lifetime call volume and/or bandwidth quota, ona per key basis.Validate JWT - Enforces existence and validity of a JWT extracted from either a specified HTTP Header or aspecified query parameter.
Use the check-header policy to enforce that a request has a specified HTTP header. You can optionally check to seeif the header has a specific value or check for a range of allowed values. If the check fails, the policy terminatesrequest processing and returns the HTTP status code and error message specified by the policy.
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
failed-check-error-message Error message to return inthe HTTP response body ifthe header doesn't exist orhas an invalid value. Thismessage must have anyspecial characters properlyescaped.
Yes N/A
failed-check-httpcode HTTP Status code to return ifthe header doesn't exist orhas an invalid value.
Yes N/A
header-name The name of the HTTPHeader to check.
Yes N/A
ignore-case Can be set to True or False. Ifset to True case is ignoredwhen the header value iscompared against the set ofacceptable values.
Yes N/A
UsageUsage
Limit call rate by subscription
IMPORTANTIMPORTANT
Policy statementPolicy statement
<rate-limit calls="number" renewal-period="seconds"> <api name="name" calls="number" renewal-period="seconds"> <operation name="name" calls="number" renewal-period="seconds" /> </api> </rate-limit>
ExampleExample
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound
Policy scopes: global, product, API, operation
The rate-limit policy prevents API usage spikes on a per subscription basis by limiting the call rate to a specifiednumber per a specified time period. When this policy is triggered the caller receives a 429 Too Many Requests
response status code.
This policy can be used only once per policy document.
Policy expressions cannot be used in any of the policy attributes for this policy.
<policies> <inbound> <base /> <rate-limit calls="20" renewal-period="90" /> </inbound> <outbound> <base /> </outbound> </policies>
ElementsElements
NAME DESCRIPTION REQUIRED
set-limit Root element. Yes
api Add one or more of these elements toimpose a call rate limit on APIs withinthe product. Product and API call ratelimits are applied independently.
No
operation Add one or more of these elements toimpose a call rate limit on operationswithin an API. Product, API, andoperation call rate limits are appliedindependently.
No
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
name The name of the API forwhich to apply the rate limit.
Yes N/A
calls The maximum total numberof calls allowed during thetime interval specified in the renewal-period .
Yes N/A
renewal-period The time period in secondsafter which the quota resets.
Yes N/A
UsageUsage
Limit call rate by key
This policy can be used in the following policy sections and scopes.
Policy sections: inbound
Policy scopes: product
The rate-limit-by-key policy prevents API usage spikes on a per key basis by limiting the call rate to a specifiednumber per a specified time period. The key can have an arbitrary string value and is typically provided using apolicy expression. Optional increment condition can be added to specify which requests should be counted towardsthe limit. When this policy is triggered the caller receives a 429 Too Many Requests response status code.
For more information and examples of this policy, see Advanced request throttling with Azure API Management.
IMPORTANTIMPORTANT
Policy statementPolicy statement
<rate-limit-by-key calls="number" renewal-period="seconds" increment-condition="condition" counter-key="key value" />
ExampleExample
<policies> <inbound> <base /> <rate-limit-by-key calls="10" renewal-period="60" increment-condition="@(context.Response.StatusCode == 200)" counter-key="@(context.Request.IpAddress)"/> </inbound> <outbound> <base /> </outbound> </policies>
ElementsElements
NAME DESCRIPTION REQUIRED
set-limit Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
calls The maximum total numberof calls allowed during thetime interval specified in the renewal-period .
Yes N/A
counter-key The key to use for the ratelimit policy.
Yes N/A
increment-condition The boolean expressionspecifying if the requestshould be counted towardsthe quota ( true ).
No N/A
renewal-period The time period in secondsafter which the quota resets.
Yes N/A
UsageUsage
This policy can be used only once per policy document.
In the following example, the rate limit is keyed by the caller IP address.
This policy can be used in the following policy sections and scopes.
Restrict caller IPs
Policy statementPolicy statement
<ip-filter action="allow | forbid"> <address>address</address> <address-range from="address" to="address" /> </ip-filter>
ExampleExample
<ip-filter action="allow | forbid"> <address>address</address> <address-range from="address" to="address" /> </ip-filter>
ElementsElements
NAME DESCRIPTION REQUIRED
ip-filter Root element. Yes
address Specifies a single IP address on which tofilter.
At least one address or address-range element is required.
address-range from="address"to="address"
Specifies a range of IP address on whichto filter.
At least one address or address-range element is required.
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
address-rangefrom="address"to="address"
A range of IP addresses toallow or deny access for.
Required when the address-range element is
used.
N/A
ip-filter action="allow |forbid"
Specifies whether callsshould be allowed or not forthe specified IP addressesand ranges.
Yes N/A
UsageUsage
Set usage quota by subscription
Policy sections: inbound
Policy scopes: global, product, API, operation
The ip-filter policy filters (allows/denies) calls from specific IP addresses and/or address ranges.
This policy can be used in the following policy sections and scopes.
Policy sections: inboundPolicy scopes: global, product, API, operation
The quota policy enforces a renewable or lifetime call volume and/or bandwidth quota, on a per subscription
IMPORTANTIMPORTANT
Policy statementPolicy statement
<quota calls="number" bandwidth="kilobytes" renewal-period="seconds"> <api name="name" calls="number" bandwidth="kilobytes"> <operation name="name" calls="number" bandwidth="kilobytes" /> </api> </quota>
ExampleExample
<policies> <inbound> <base /> <quota calls="10000" bandwidth="40000" renewal-period="3600" /> </inbound> <outbound> <base /> </outbound> </policies>
ElementsElements
NAME DESCRIPTION REQUIRED
quota Root element. Yes
api Add one or more of these elements toimpose a quota on APIs within theproduct. Product and API quotas areapplied independently.
No
operation Add one or more of these elements toimpose a quota on operations within anAPI. Product, API, and operation quotasare applied independently.
No
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
name The name of the API oroperation for which thequota applies.
Yes N/A
bandwidth The maximum total numberof kilobytes allowed duringthe time interval specified inthe renewal-period .
Either calls , bandwidth ,or both together must bespecified.
N/A
basis.
This policy can be used only once per policy document.
Policy expressions cannot be used in any of the policy attributes for this policy.
calls The maximum total numberof calls allowed during thetime interval specified in the renewal-period .
Either calls , bandwidth ,or both together must bespecified.
N/A
renewal-period The time period in secondsafter which the quota resets.
Yes N/A
NAME DESCRIPTION REQUIRED DEFAULT
UsageUsage
Set usage quota by key
IMPORTANTIMPORTANT
Policy statementPolicy statement
<quota-by-key calls="number" bandwidth="kilobytes" renewal-period="seconds" increment-condition="condition" counter-key="key value" />
ExampleExample
<policies> <inbound> <base /> <quota-by-key calls="10000" bandwidth="40000" renewal-period="3600" increment-condition="@(context.Response.StatusCode >= 200 && context.Response.StatusCode < 400)" counter-key="@(context.Request.IpAddress)" /> </inbound> <outbound> <base /> </outbound> </policies>
ElementsElements
This policy can be used in the following policy sections and scopes.
Policy sections: inboundPolicy scopes: product
The quota-by-key policy enforces a renewable or lifetime call volume and/or bandwidth quota, on a per key basis.The key can have an arbitrary string value and is typically provided using a policy expression. Optional incrementcondition can be added to specify which requests should be counted towards the quota.
For more information and examples of this policy, see Advanced request throttling with Azure API Management.
This policy can be used only once per policy document.
Policy expressions cannot be used in any of the policy attributes for this policy.
In the following example, the quota is keyed by the caller IP address.
NAME DESCRIPTION REQUIRED
quota Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
bandwidth The maximum total numberof kilobytes allowed duringthe time interval specified inthe renewal-period .
Either calls , bandwidth ,or both together must bespecified.
N/A
calls The maximum total numberof calls allowed during thetime interval specified in the renewal-period .
Either calls , bandwidth ,or both together must bespecified.
N/A
counter-key The key to use for the quotapolicy.
Yes N/A
increment-condition The boolean expressionspecifying if the requestshould be counted towardsthe quota ( true )
No N/A
renewal-period The time period in secondsafter which the quota resets.
Yes N/A
UsageUsage
Validate JWT
IMPORTANTIMPORTANT
Policy statementPolicy statement
This policy can be used in the following policy sections and scopes.
Policy sections: inboundPolicy scopes: global, product, API, operation
The validate-jwt policy enforces existence and validity of a JWT extracted from either a specified HTTP Header ora specified query parameter.
The validate-jwt policy requires that the exp registered claim is included in the JWT token, unless require-expiration-time attribute is specified and set to false .
The validate-jwt policy supports HS256 and RS256 signing algorithms. For HS256 the key must be provided inline withinthe policy in the base64 encoded form. For RS256 the key has to be provide via an Open ID configuration endpoint.
<validate-jwt header-name="name of http header containing the token (use query-parameter-name attribute if the token is passed in the URL)" failed-validation-httpcode="http status code to return on failure" failed-validation-error-message="error message to return on failure" require-expiration-time="true|false" require-scheme="scheme" require-signed-tokens="true|false" clock-skew="allowed clock skew in seconds"> <issuer-signing-keys> <key>base64 encoded signing key</key> <!-- if there are multiple keys, then add additional key elements --> </issuer-signing-keys> <audiences> <audience>audience string</audience> <!-- if there are multiple possible audiences, then add additional audience elements --> </audiences> <issuers> <issuer>issuer string</issuer> <!-- if there are multiple possible issuers, then add additional issuer elements --> </issuers> <required-claims> <claim name="name of the claim as it appears in the token" match="all|any" separator="separator character in a multi-valued claim"> <value>claim value as it is expected to appear in the token</value> <!-- if there is more than one allowed values, then add additional value elements --> </claim> <!-- if there are multiple possible allowed values, then add additional value elements --> </required-claims> <openid-config url="full URL of the configuration endpoint, e.g. https://login.constoso.com/openid-configuration" /> <zumo-master-key id="key identifier">key value</zumo-master-key> </validate-jwt>
ExamplesExamplesAzure Mobile Services token validationAzure Mobile Services token validation
<validate-jwt header-name="x-zumo-auth" failed-validation-httpcode="401" failed-validation-error-message="Unauthorized. Supplied access token is invalid."> <issuers> <issuer>urn:microsoft:windows-azure:zumo</issuer> </issuers> <audiences> <audience>Facebook</audience> </audiences> <issuer-signing-keys> <zumo-master-key id="0">insert key here</zumo-master-key> </issuer-signing-keys> </validate-jwt>
Azure Active Directory token validationAzure Active Directory token validation
<validate-jwt header-name="Authorization" failed-validation-httpcode="401" failed-validation-error-message="Unauthorized. Access token is missing or invalid."> <openid-config url="https://login.microsoftonline.com/contoso.onmicrosoft.com/.well-known/openid-configuration" /> <audiences> <audience>25eef6e4-c905-4a07-8eb4-0d08d5df8b3f</audience> </audiences> <required-claims> <claim name="id" match="all"> <value>insert claim here</value> </claim> </required-claims> </validate-jwt>
Azure Active Directory B2C token validationAzure Active Directory B2C token validation
<validate-jwt header-name="Authorization" failed-validation-httpcode="401" failed-validation-error-message="Unauthorized. Access token is missing or invalid."> <openid-config url="https://login.microsoftonline.com/tfp/contoso.onmicrosoft.com/b2c_1_signin/v2.0/.well-known/openid-configuration" /> <audiences> <audience>d313c4e4-de5f-4197-9470-e509a2f0b806</audience> </audiences> <required-claims> <claim name="id" match="all"> <value>insert claim here</value> </claim> </required-claims> </validate-jwt>
Authorize access to operations based on token claimsAuthorize access to operations based on token claims
This example shows how to use the Validate JWT policy to pre-authorize access to operations based on tokenclaims. For a demonstration of configuring and using this policy, see Cloud Cover Episode 177: More APIManagement Features with Vlad Vinogradsky and fast-forward to 13:50. Fast forward to 15:00 to see the policiesconfigured in the policy editor and then to 18:50 for a demonstration of calling an operation from the developerportal both with and without the required authorization token.
<!-- Copy the following snippet into the inbound section at the api (or higher) level to pre-authorize access to operations based on token claims --> <set-variable name="signingKey" value="insert signing key here" /> <choose> <when condition="@(context.Request.Method.Equals("patch",StringComparison.OrdinalIgnoreCase))"> <validate-jwt header-name="Authorization"> <issuer-signing-keys> <key>@((string)context.Variables["signingKey"])</key> </issuer-signing-keys> <required-claims> <claim name="edit"> <value>true</value> </claim> </required-claims> </validate-jwt> </when> <when condition="@(new [] {"post", "put"}.Contains(context.Request.Method,StringComparer.OrdinalIgnoreCase))"> <validate-jwt header-name="Authorization"> <issuer-signing-keys> <key>@((string)context.Variables["signingKey"])</key> </issuer-signing-keys> <required-claims> <claim name="create"> <value>true</value> </claim> </required-claims> </validate-jwt> </when> <otherwise> <validate-jwt header-name="Authorization"> <issuer-signing-keys> <key>@((string)context.Variables["signingKey"])</key> </issuer-signing-keys> </validate-jwt> </otherwise> </choose>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
validate-jwt Root element. Yes
audiences Contains a list of acceptable audienceclaims that can be present on the token.If multiple audience values are present,then each value is tried until either allare exhausted (in which case validationfails) or until one succeeds. At least oneaudience must be specified.
No
issuer-signing-keys A list of Base64-encoded security keysused to validate signed tokens. Ifmultiple security keys are present, theneach key is tried until either all areexhausted (in which case validation fails)or until one succeeds (useful for tokenrollover). Key elements have an optionalid attribute used to match against kid claim.
No
issuers A list of acceptable principals that issuedthe token. If multiple issuer values arepresent, then each value is tried untileither all are exhausted (in which casevalidation fails) or until one succeeds.
No
openid-config The element used for specifying acompliant Open ID configurationendpoint from which signing keys andissuer can be obtained.
No
required-claims Contains a list of claims expected to bepresent on the token for it to beconsidered valid. When the match
attribute is set to all every claimvalue in the policy must be present inthe token for validation to succeed.When the match attribute is set to any at least one claim must be
present in the token for validation tosucceed.
No
zumo-master-key Master key for tokens issued by AzureMobile Services
No
ELEMENT DESCRIPTION REQUIRED
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
clock-skew Timespan. Use to specifymaximum expected timedifference between thesystem clocks of the tokenissuer and the APIManagement instance.
No 0 seconds
failed-validation-error-message
Error message to return inthe HTTP response body ifthe JWT does not passvalidation. This messagemust have any specialcharacters properly escaped.
No Default error messagedepends on validation issue,for example "JWT notpresent."
failed-validation-httpcode HTTP Status code to return ifthe JWT doesn't passvalidation.
No 401
header-name The name of the HTTPheader holding the token.
Either header-name or query-parameter-name
must be specified; but notboth.
N/A
id The id attribute on the key element allows you to
specify the string that will bematched against kid claimin the token (if present) tofind out the appropriate keyto use for signaturevalidation.
No N/A
match The match attribute on theclaim element specifies
whether every claim value inthe policy must be presentin the token for validation tosucceed. Possible values are:
- all - every claim value inthe policy must be presentin the token for validation tosucceed.
- any - at least one claimvalue must be present in thetoken for validation tosucceed.
No all
query-paremeter-name The name of the the queryparameter holding thetoken.
Either header-name or query-paremeter-name
must be specified; but notboth.
N/A
require-expiration-time Boolean. Specifies whetheran expiration claim isrequired in the token.
No true
require-scheme The name of the tokenscheme, e.g. "Bearer". Whenthis attribute is set, thepolicy will ensure thatspecified scheme is presentin the Authorization headervalue.
No N/A
require-signed-tokens Boolean. Specifies whether atoken is required to besigned.
No true
separator String. Specifies a separator(e.g. ",") to be used forextracting a set of valuesfrom a multi-valued claim.
No N/A
NAME DESCRIPTION REQUIRED DEFAULT
url Open ID configurationendpoint URL from whereOpen ID configurationmetadata can be obtained.The response should beaccording to specs asdefined at URL:https://openid.net/specs/openid-connect-discovery-1_0.html#ProviderMetadata
. For Azure Active Directoryuse the following URL: https://login.microsoftonline.com/{tenant-name}/.well-known/openid-configuration
substituting your directorytenant name, e.g. contoso.onmicrosoft.com .
Yes N/A
NAME DESCRIPTION REQUIRED DEFAULT
UsageUsage
Next steps
This policy can be used in the following policy sections and scopes.
Policy sections: inboundPolicy scopes: global, product, API, operation
For more information working with policies, see:
Policies in API ManagementTransform APIsPolicy Reference for a full list of policy statements and their settingsPolicy samples
API Management advanced policies3/23/2018 • 20 min to read • Edit Online
Advanced policies
Control flow
Policy statementPolicy statement
<choose> <when condition="Boolean expression | Boolean constant"> <!— one or more policy statements to be applied if the above condition is true --> </when> <when condition="Boolean expression | Boolean constant"> <!— one or more policy statements to be applied if the above condition is true --> </when> <otherwise> <!— one or more policy statements to be applied if none of the above conditions are true --></otherwise></choose>
This topic provides a reference for the following API Management policies. For information on adding andconfiguring policies, see Policies in API Management.
Control flow - Conditionally applies policy statements based on the results of the evaluation of Booleanexpressions.Forward request - Forwards the request to the backend service.Limit concurrency - Prevents enclosed policies from executing by more than the specified number of requests ata time.Log to Event Hub - Sends messages in the specified format to an Event Hub defined by a Logger entity.Mock response - Aborts pipeline execution and returns a mocked response directly to the caller.Retry - Retries execution of the enclosed policy statements, if and until the condition is met. Execution willrepeat at the specified time intervals and up to the specified retry count.Return response - Aborts pipeline execution and returns the specified response directly to the caller.Send one way request - Sends a request to the specified URL without waiting for a response.Send request - Sends a request to the specified URL.Set HTTP proxy - Allows you to route forwarded requests via an HTTP proxy.Set request method - Allows you to change the HTTP method for a request.Set status code - Changes the HTTP status code to the specified value.Set variable - Persists a value in a named context variable for later access.Trace - Adds a string into the API Inspector output.Wait - Waits for enclosed Send request, Get value from cache, or Control flow policies to complete beforeproceeding.
The choose policy applies enclosed policy statements based on the outcome of evaluation of Boolean expressions,similar to an if-then-else or a switch construct in a programming language.
The control flow policy must contain at least one <when/> element. The <otherwise/> element is optional.Conditions in <when/> elements are evaluated in order of their appearance within the policy. Policy statement(s)enclosed within the first <when/> element with condition attribute equals true will be applied. Policies enclosed
ExamplesExamplesExampleExample
<policies> <inbound> <set-variable name="isMobile" value="@(context.Request.Headers["User-Agent"].Contains("iPad") || context.Request.Headers["User-Agent"].Contains("iPhone"))" /> <base /> <choose> <when condition="@(context.Variables.GetValueOrDefault<bool>("isMobile"))"> <set-query-parameter name="mobile" exists-action="override"> <value>true</value> </set-query-parameter> </when> <otherwise> <set-query-parameter name="mobile" exists-action="override"> <value>false</value> </set-query-parameter> </otherwise> </choose> </inbound> <outbound> <base /> <choose> <when condition="@(context.Variables.GetValueOrDefault<bool>("isMobile"))"> <xml-to-json kind="direct" apply="always" consider-accept-header="false"/> </when> </choose> </outbound></policies>
ExampleExample
within the <otherwise/> element, if present, will be applied if all of the <when/> element condition attributes are false .
The following example demonstrates a set-variable policy and two control flow policies.
The set variable policy is in the inbound section and creates an isMobile Boolean context variable that is set to trueif the User-Agent request header contains the text iPad or iPhone .
The first control flow policy is also in the inbound section, and conditionally applies one of two Set query stringparameter policies depending on the value of the isMobile context variable.
The second control flow policy is in the outbound section and conditionally applies the Convert XML to JSONpolicy when isMobile is set to true .
This example shows how to perform content filtering by removing data elements from the response received fromthe backend service when using the Starter product. For a demonstration of configuring and using this policy, seeCloud Cover Episode 177: More API Management Features with Vlad Vinogradsky and fast-forward to 34:30.Start at 31:50 to see an overview of The Dark Sky Forecast API used for this demo.
<!-- Copy this snippet into the outbound section to remove a number of data elements from the response received from the backend service based on the name of the api product --><choose> <when condition="@(context.Response.StatusCode == 200 && context.Product.Name.Equals("Starter"))"> <set-body>@{ var response = context.Response.Body.As<JObject>(); foreach (var key in new [] {"minutely", "hourly", "daily", "flags"}) { response.Property (key).Remove (); } return response.ToString(); } </set-body> </when></choose>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
choose Root element. Yes
when The condition to use for the if or ifelse parts of the choose policy. If
the choose policy has multiple when
sections, they are evaluatedsequentially. Once the condition of awhen element evaluates to true , nofurther when conditions are evaluated.
Yes
otherwise Contains the policy snippet to be used ifnone of the when conditions evaluateto true .
No
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED
condition="Boolean expression |Boolean constant"
The Boolean expression or constant toevaluated when the containing when
policy statement is evaluated.
Yes
UsageUsage
Forward request
NOTENOTE
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-error
Policy scopes: all scopes
The forward-request policy forwards the incoming request to the backend service specified in the request context.The backend service URL is specified in the API settings and can be changed using the set backend service policy.
Removing this policy results in the request not being forwarded to the backend service and the policies in the outboundsection are evaluated immediately upon the successful completion of the policies in the inbound section.
Policy statementPolicy statement
<forward-request timeout="time in seconds" follow-redirects="true | false"/>
ExamplesExamplesExampleExample
<!-- api level --><policies> <inbound> <base/> </inbound> <backend> <forward-request timeout="60"/> </backend> <outbound> <base/> </outbound></policies>
ExampleExample
<!-- operation level --><policies> <inbound> <base/> </inbound> <backend> <base/> </backend> <outbound> <base/> </outbound></policies>
ExampleExample
<!-- operation level --><policies> <inbound> <base/> </inbound> <backend> <forward-request timeout="120"/> <!-- effective policy. note the absence of <base/> --> </backend> <outbound> <base/> </outbound></policies>
ExampleExample
The following API level policy forwards all requests to the backend service with a timeout interval of 60 seconds.
This operation level policy uses the base element to inherit the backend policy from the parent API level scope.
This operation level policy explicitly forwards all requests to the backend service with a timeout of 120 and doesnot inherit the parent API level backend policy.
This operation level policy does not forward requests to the backend service.
<!-- operation level --><policies> <inbound> <base/> </inbound> <backend> <!-- no forwarding to backend --> </backend> <outbound> <base/> </outbound></policies>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
forward-request Root element. Yes
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
timeout="integer" The timeout interval inseconds before the call tothe backend service fails.
No 300 seconds
follow-redirects="true | false" Specifies whether redirectsfrom the backend service arefollowed by the gateway orreturned to the caller.
No false
UsageUsage
Limit concurrency
Policy statementPolicy statement
<limit-concurrency key="expression" max-count="number"> <!— nested policy statements --></limit-concurrency>
ExamplesExamplesExampleExample
This policy can be used in the following policy sections and scopes.
Policy sections: backendPolicy scopes: all scopes
The limit-concurrency policy prevents enclosed policies from executing by more than the specified number ofrequests at a given time. Upon exceeding that number, new requests will fail immediately with 429 Too ManyRequests status code.
The following example demonstrates how to limit number of requests forwarded to a backend based on the valueof a context variable.
<policies> <inbound>…</inbound> <backend> <limit-concurrency key="@((string)context.Variables["connectionId"])" max-count="3"> <forward-request timeout="120"/> <limit-concurrency/> </backend> <outbound>…</outbound></policies>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
limit-concurrency Root element. Yes
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
key A string. Expression allowed.Specifies the concurrencyscope. Can be shared bymultiple policies.
Yes N/A
max-count An integer. Specifies amaximum number ofrequests that are allowed toenter the policy.
Yes N/A
UsageUsage
Log to Event Hub
NOTENOTE
Policy statementPolicy statement
<log-to-eventhub logger-id="id of the logger entity" partition-id="index of the partition where messages are sent" partition-key="value used for partition assignment"> Expression returning a string to be logged</log-to-eventhub>
ExampleExample
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-error
Policy scopes: all scopes
The log-to-eventhub policy sends messages in the specified format to an Event Hub defined by a Logger entity. Asits name implies, the policy is used for saving selected request or response context information for online or offlineanalysis.
For a step-by-step guide on configuring an event hub and logging events, see How to log API Management events withAzure Event Hubs.
<policies> <inbound> <log-to-eventhub logger-id ='contoso-logger'> @( string.Join(",", DateTime.UtcNow, context.Deployment.ServiceName, context.RequestId, context.Request.IpAddress, context.Operation.Name) ) </log-to-eventhub> </inbound> <outbound> </outbound></policies>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
log-to-eventhub Root element. The value of this elementis the string to log to your event hub.
Yes
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED
logger-id The id of the Logger registered withyour API Management service.
Yes
partition-id Specifies the index of the partitionwhere messages are sent.
Optional. This attribute may not beused if partition-key is used.
partition-key Specifies the value used for partitionassignment when messages are sent.
Optional. This attribute may not beused if partition-id is used.
UsageUsage
Mock response
Policy statementPolicy statement
<mock-response status-code="code" content-type="media type"/>
ExamplesExamples
Any string can be used as the value to be logged in Event Hubs. In this example the date and time, deploymentservice name, request id, ip address, and operation name for all inbound calls are logged to the event hub Loggerregistered with the contoso-logger id.
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-error
Policy scopes: all scopes
The mock-response , as the name implies, is used to mock APIs and operations. It aborts normal pipeline executionand returns a mocked response to the caller. The policy always tries to return responses of highest fidelity. It prefersresponse content examples, whenever available. It generates sample responses from schemas, when schemas areprovided and examples are not. If neither examples or schemas are found, responses with no content are returned.
<!-- Returns 200 OK status code. Content is based on an example or schema, if provided for thisstatus code. First found content type is used. If no example or schema is found, the content is empty. --><mock-response/>
<!-- Returns 200 OK status code. Content is based on an example or schema, if provided for thisstatus code and media type. If no example or schema found, the content is empty. --><mock-response status-code='200' content-type='application/json'/>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
mock-response Root element. Yes
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
status-code Specifies response statuscode and is used to selectcorresponding example orschema.
No 200
content-type Specifies Content-Type
response header value and isused to select correspondingexample or schema.
No None
UsageUsage
Retry
Policy statementPolicy statement
<retry condition="boolean expression or literal" count="number of retry attempts" interval="retry interval in seconds" max-interval="maximum retry interval in seconds" delta="retry interval delta in seconds" first-fast-retry="boolean expression or literal"> <!-- One or more child policies. No restrictions --></retry>
ExampleExample
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, on-error
Policy scopes: all scopes
The retry policy executes its child policies once and then retries their execution until the retry condition
becomes false or retry count is exhausted.
In the following example, request forwarding is retried up to ten times using an exponential retry algorithm. Since first-fast-retry is set to false, all retry attempts are subject to the exponential retry algorithm.
<retry condition="@(context.Response.StatusCode == 500)" count="10" interval="10" max-interval="100" delta="10" first-fast-retry="false"> <forward-request /></retry>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
retry Root element. May contain any otherpolicies as its child elements.
Yes
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
condition A boolean literal orexpression specifying ifretries should be stopped (false ) or continued (true ).
Yes N/A
count A positive number specifyingthe maximum number ofretries to attempt.
Yes N/A
interval A positive number inseconds specifying the waitinterval between the retryattempts.
Yes N/A
max-interval A positive number inseconds specifying themaximum wait intervalbetween the retry attempts.It is used to implement anexponential retry algorithm.
No N/A
delta A positive number inseconds specifying the waitinterval increment. It is usedto implement the linear andexponential retry algorithms.
No N/A
first-fast-retry If set to true , the firstretry attempt is performedimmediately.
No false
NOTENOTE
UsageUsage
Return response
Policy statementPolicy statement
<return-response response-variable-name="existing context variable"> <set-header/> <set-body/> <set-status/></return-response>
ExampleExample
<return-response> <set-status code="401" reason="Unauthorized"/> <set-header name="WWW-Authenticate" exists-action="override"> <value>Bearer error="invalid_token"</value> </set-header></return-response>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
return-response Root element. Yes
set-header A set-header policy statement. No
set-body A set-body policy statement. No
set-status A set-status policy statement. No
AttributesAttributes
When only the interval is specified, fixed interval retries are performed. When only the interval and delta arespecified, a linear interval retry algorithm is used, where wait time between retries is calculated according the followingformula - interval + (count - 1)*delta . When the interval , max-interval and delta are specified, exponentialinterval retry algorithm is applied, where the wait time between the retries is growing exponentially from the value of interval to the value max-interval according to the following forumula - min(interval + (2^count - 1) * random(delta * 0.8, delta * 1.2), max-interval) .
This policy can be used in the following policy sections and scopes . Note that child policy usage restrictions will beinherited by this policy.
Policy sections: inbound, outbound, backend, on-error
Policy scopes: all scopes
The return-response policy aborts pipeline execution and returns either a default or custom response to the caller.Default response is 200 OK with no body. Custom response can be specified via a context variable or policystatements. When both are provided, the response contained within the context variable is modified by the policystatements before being returned to the caller.
ATTRIBUTE DESCRIPTION REQUIRED
response-variable-name The name of the context variablereferenced from, for example, anupstream send-request policy andcontaining a Response object
Optional.
UsageUsage
Send one way request
Policy statementPolicy statement
<send-one-way-request mode="new | copy"> <url>...</url> <method>...</method> <header name="" exists-action="override | skip | append | delete">...</header> <body>...</body> <authentication-certificate thumbprint="thumbprint" /></send-one-way-request>
ExampleExample
<choose> <when condition="@(context.Response.StatusCode >= 500)"> <send-one-way-request mode="new"> <set-url>https://hooks.slack.com/services/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</set-url> <set-method>POST</set-method> <set-body>@{ return new JObject( new JProperty("username","APIM Alert"), new JProperty("icon_emoji", ":ghost:"), new JProperty("text", String.Format("{0} {1}\nHost: {2}\n{3} {4}\n User: {5}", context.Request.Method, context.Request.Url.Path + context.Request.Url.QueryString, context.Request.Url.Host, context.Response.StatusCode, context.Response.StatusReason, context.User.Email )) ).ToString(); }</set-body> </send-one-way-request> </when></choose>
ElementsElements
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-error
Policy scopes: all scopes
The send-one-way-request policy sends the provided request to the specified URL without waiting for a response.
This sample policy shows an example of using the send-one-way-request policy to send a message to a Slack chatroom if the HTTP response code is greater than or equal to 500. For more information on this sample, see Usingexternal services from the Azure API Management service.
ELEMENT DESCRIPTION REQUIRED
send-one-way-request Root element. Yes
url The URL of the request. No if mode=copy; otherwise yes.
method The HTTP method for the request. No if mode=copy; otherwise yes.
header Request header. Use multiple headerelements for multiple request headers.
No
body The request body. No
authentication-certificate Certificate to use for clientauthentication
No
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
mode="string" Determines whether this is anew request or a copy of thecurrent request. Inoutbound mode,mode=copy does notinitialize the request body.
No New
name Specifies the name of theheader to be set.
Yes N/A
exists-action Specifies what action to takewhen the header is alreadyspecified. This attribute musthave one of the followingvalues.
- override - replaces thevalue of the existing header.- skip - does not replace theexisting header value.- append - appends thevalue to the existing headervalue.- delete - removes theheader from the request.
When set to override
enlisting multiple entrieswith the same name resultsin the header being setaccording to all entries(which will be listed multipletimes); only listed values willbe set in the result.
No override
UsageUsageThis policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-error
Send request
Policy statementPolicy statement
<send-request mode="new|copy" response-variable-name="" timeout="60 sec" ignore-error="false|true"> <set-url>...</set-url> <set-method>...</set-method> <set-header name="" exists-action="override|skip|append|delete">...</set-header> <set-body>...</set-body> <authentication-certificate thumbprint="thumbprint" /></send-request>
ExampleExample
<inbound> <!-- Extract Token from Authorization header parameter --> <set-variable name="token" value="@(context.Request.Headers.GetValueOrDefault("Authorization","scheme param").Split(' ').Last())" />
<!-- Send request to Token Server to validate token (see RFC 7662) --> <send-request mode="new" response-variable-name="tokenstate" timeout="20" ignore-error="true"> <set-url>https://microsoft-apiappec990ad4c76641c6aea22f566efc5a4e.azurewebsites.net/introspection</set-url> <set-method>POST</set-method> <set-header name="Authorization" exists-action="override"> <value>basic dXNlcm5hbWU6cGFzc3dvcmQ=</value> </set-header> <set-header name="Content-Type" exists-action="override"> <value>application/x-www-form-urlencoded</value> </set-header> <set-body>@($"token={(string)context.Variables["token"]}")</set-body> </send-request>
<choose> <!-- Check active property in response --> <when condition="@((bool)((IResponse)context.Variables["tokenstate"]).Body.As<JObject>()["active"] == false)"> <!-- Return 401 Unauthorized with http-problem payload --> <return-response> <set-status code="401" reason="Unauthorized" /> <set-header name="WWW-Authenticate" exists-action="override"> <value>Bearer error="invalid_token"</value> </set-header> </return-response> </when> </choose> <base /></inbound>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
send-request Root element. Yes
Policy scopes: all scopes
The send-request policy sends the provided request to the specified URL, waiting no longer than the set timeoutvalue.
This example shows one way to verify a reference token with an authorization server. For more information on thissample, see Using external services from the Azure API Management service.
url The URL of the request. No if mode=copy; otherwise yes.
method The HTTP method for the request. No if mode=copy; otherwise yes.
header Request header. Use multiple headerelements for multiple request headers.
No
body The request body. No
authentication-certificate Certificate to use for clientauthentication
No
ELEMENT DESCRIPTION REQUIRED
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
mode="string" Determines whether this is anew request or a copy of thecurrent request. Inoutbound mode,mode=copy does notinitialize the request body.
No New
response-variable-name="string"
If not present, context.Response is used.
No N/A
timeout="integer" The timeout interval inseconds before the call tothe URL fails.
No 60
ignore-error If true and the requestresults in an error:
- If response-variable-namewas specified it will contain anull value.- If response-variable-namewas not specified,context.Request will not beupdated.
No false
name Specifies the name of theheader to be set.
Yes N/A
exists-action Specifies what action to takewhen the header is alreadyspecified. This attribute musthave one of the followingvalues.
- override - replaces thevalue of the existing header.- skip - does not replace theexisting header value.- append - appends thevalue to the existing headervalue.- delete - removes theheader from the request.
When set to override
enlisting multiple entrieswith the same name resultsin the header being setaccording to all entries(which will be listed multipletimes); only listed values willbe set in the result.
No override
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
UsageUsage
Set HTTP proxy
Policy statementPolicy statement
<proxy url="http://hostname-or-ip:port" username="username" password="password" />
ExampleExample
<proxy url="http://192.168.1.1:8080" username={{username}} password={{password}} />
ElementsElements
ELEMENT DESCRIPTION REQUIRED
proxy Root element Yes
AttributesAttributes
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-error
Policy scopes: all scopes
The proxy policy allows you to route requests forwarded to backends via an HTTP proxy. Only HTTP (not HTTPS)is supported between the gateway and the proxy. Basic and NTLM authentication only.
Note the use of properties as values of the username and password to avoid storing sensitive information in thepolicy document.
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
url="string" Proxy URL in the form ofhttp://host:port.
Yes N/A
username="string" Username to be used forauthentication with theproxy.
No N/A
password="string" Password to be used forauthentication with theproxy.
No N/A
UsageUsage
Set request method
Policy statementPolicy statement
<set-method>METHOD</set-method>
ExampleExample
<choose> <when condition="@(context.Response.StatusCode >= 500)"> <send-one-way-request mode="new"> <set-url>https://hooks.slack.com/services/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</set-url> <set-method>POST</set-method> <set-body>@{ return new JObject( new JProperty("username","APIM Alert"), new JProperty("icon_emoji", ":ghost:"), new JProperty("text", String.Format("{0} {1}\nHost: {2}\n{3} {4}\n User: {5}", context.Request.Method, context.Request.Url.Path + context.Request.Url.QueryString, context.Request.Url.Host, context.Response.StatusCode, context.Response.StatusReason, context.User.Email )) ).ToString(); }</set-body> </send-one-way-request> </when></choose>
ElementsElements
This policy can be used in the following policy sections and scopes.
Policy sections: inbound
Policy scopes: all scopes
The set-method policy allows you to change the HTTP request method for a request.
This sample policy that uses the set-method policy shows an example of sending a message to a Slack chat room ifthe HTTP response code is greater than or equal to 500. For more information on this sample, see Using externalservices from the Azure API Management service.
ELEMENT DESCRIPTION REQUIRED
set-method Root element. The value of the elementspecifies the HTTP method.
Yes
UsageUsage
Set status code
Policy statementPolicy statement
<set-status code="" reason=""/>
ExampleExample
<choose> <when condition="@((bool)((IResponse)context.Variables["tokenstate"]).Body.As<JObject>()["active"] == false)"> <return-response response-variable-name="existing response variable"> <set-status code="401" reason="Unauthorized" /> <set-header name="WWW-Authenticate" exists-action="override"> <value>Bearer error="invalid_token"</value> </set-header> </return-response> </when></choose>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
set-status Root element. Yes
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
code="integer" The HTTP status code toreturn.
Yes N/A
reason="string" A description of the reasonfor returning the statuscode.
Yes N/A
UsageUsage
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, on-error
Policy scopes: all scopes
The set-status policy sets the HTTP status code to the specified value.
This example shows how to return a 401 response if the authorization token is invalid. For more information, seeUsing external services from the Azure API Management service
This policy can be used in the following policy sections and scopes.
Set variable
Policy statementPolicy statement
<set-variable name="variable name" value="Expression | String literal" />
ExampleExample
<set-variable name="IsMobile" value="@(context.Request.Headers["User-Agent"].Contains("iPad") || context.Request.Headers["User-Agent"].Contains("iPhone"))" />
ElementsElements
ELEMENT DESCRIPTION REQUIRED
set-variable Root element. Yes
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED
name The name of the variable. Yes
value The value of the variable. This can be anexpression or a literal value.
Yes
UsageUsage
Allowed typesAllowed types
Policy sections: outbound, backend, on-errorPolicy scopes: all scopes
The set-variable policy declares a context variable and assigns it a value specified via an expression or a stringliteral. if the expression contains a literal it will be converted to a string and the type of the value will be System.String .
The following example demonstrates a set variable policy in the inbound section. This set variable policy creates an isMobile Boolean context variable that is set to true if the User-Agent request header contains the text iPad or iPhone .
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-errorPolicy scopes: all scopes
Expressions used in the set-variable policy must return one of the following basic types.
System.BooleanSystem.SByteSystem.ByteSystem.UInt16System.UInt32System.UInt64System.Int16
Trace
Policy statementPolicy statement
<trace source="arbitrary string literal"/> <!-- string expression or literal --></trace>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
trace Root element. Yes
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
System.Int32System.Int64System.DecimalSystem.SingleSystem.DoubleSystem.GuidSystem.StringSystem.CharSystem.DateTimeSystem.TimeSpanSystem.Byte?System.UInt16?System.UInt32?System.UInt64?System.Int16?System.Int32?System.Int64?System.Decimal?System.Single?System.Double?System.Guid?System.String?System.Char?System.DateTime?
The trace policy adds a string into the API Inspector output. The policy will execute only when tracing is triggered,i.e. Ocp-Apim-Trace request header is present and set to true and Ocp-Apim-Subscription-Key request header ispresent and holds a valid key associated with the admin account.
source String literal meaningful tothe trace viewer andspecifying the source of themessage.
Yes N/A
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
UsageUsage
Wait
Policy statementPolicy statement
<wait for="all|any"> <!--Wait policy can contain send-request, cache-lookup-value, and choose policies as child elements --></wait>
ExampleExample
This policy can be used in the following policy sections and scopes .
Policy sections: inbound, outbound, backend, on-error
Policy scopes: all scopes
The wait policy executes its immediate child policies in parallel, and waits for either all or one of its immediatechild policies to complete before it completes. The wait policy can have as its immediate child policies Send request,Get value from cache, and Control flow policies.
In the following example there are two choose policies as immediate child policies of the wait policy. Each ofthese choose policies executes in parallel. Each choose policy attempts to retrieve a cached value. If there is acache miss, a backend service is called to provide the value. In this example the wait policy does not completeuntil all of its immediate child policies complete, because the for attribute is set to all . In this example thecontext variables ( execute-branch-one , value-one , execute-branch-two , and value-two ) are declared outside of thescope of this example policy.
<wait for="all"> <choose> <when condition="@((bool)context.Variables["execute-branch-one="])"> <cache-lookup-value key="key-one" variable-name="value-one" /> <choose> <when condition="@(!context.Variables.ContainsKey("value-one="))"> <send-request mode="new" response-variable-name="value-one"> <set-url>https://backend-one</set-url> <set-method>GET</set-method> </send-request> </when> </choose> </when> </choose> <choose> <when condition="@((bool)context.Variables["execute-branch-two="])"> <cache-lookup-value key="key-two" variable-name="value-two" /> <choose> <when condition="@(!context.Variables.ContainsKey("value-two="))"> <send-request mode="new" response-variable-name="value-two"> <set-url>https://backend-two</set-url> <set-method>GET</set-method> </send-request> </when> </choose> </when> </choose></wait>
ElementsElements
ELEMENT DESCRIPTION REQUIRED
wait Root element. May contain as childelements only send-request , cache-lookup-value , and choose
policies.
Yes
AttributesAttributes
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
for Determines whether the wait policy waits for all
immediate child policies tobe completed or just one.Allowed values are:
- all - wait for allimmediate child policies tocomplete- any - wait for anyimmediate child policy tocomplete. Once the firstimmediate child policy hascompleted, the wait policycompletes and execution ofany other immediate childpolicies is terminated.
No all
UsageUsage
Next steps
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backendPolicy scopes: all scopes
For more information working with policies, see:
Policies in API ManagementPolicy expressionsPolicy Reference for a full list of policy statements and their settingsPolicy samples
API Management authentication policies12/4/2017 • 1 min to read • Edit Online
Authentication policies
Authenticate with Basic
Policy statementPolicy statement
<authentication-basic username="username" password="password" />
ExampleExample
<authentication-basic username="testuser" password="testpassword" />
ElementsElements
NAME DESCRIPTION REQUIRED
authentication-basic Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
username Specifies the username ofthe Basic credential.
Yes N/A
password Specifies the password of theBasic credential.
Yes N/A
UsageUsage
Authenticate with client certificate
This topic provides a reference for the following API Management policies. For information on adding andconfiguring policies, see Policies in API Management.
Authenticate with Basic - Authenticate with a backend service using Basic authentication.
Authenticate with client certificate - Authenticate with a backend service using client certificates.
Use the authentication-basic policy to authenticate with a backend service using Basic authentication. This policyeffectively sets the HTTP Authorization header to the value corresponding to the credentials provided in the policy.
This policy can be used in the following policy sections and scopes.
Policy sections: inbound
Policy scopes: API
Use the authentication-certificate policy to authenticate with a backend service using client certificate. The
Policy statementPolicy statement
<authentication-certificate thumbprint="thumbprint" />
ExampleExample
<authentication-certificate thumbprint="....." />
ElementsElements
NAME DESCRIPTION REQUIRED
authentication-certificate Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
thumbprint The thumbprint for the clientcertificate.
Yes N/A
UsageUsage
Next steps
certificate needs to be installed into API Management first and is identified by its thumbprint.
This policy can be used in the following policy sections and scopes.
Policy sections: inbound
Policy scopes: API
For more information working with policies, see:
Policies in API ManagementTransform APIsPolicy Reference for a full list of policy statements and their settingsPolicy samples
API Management caching policies12/6/2017 • 7 min to read • Edit Online
Caching policies
Get from cache
NOTENOTE
Policy statementPolicy statement
<cache-lookup vary-by-developer="true | false" vary-by-developer-groups="true | false" downstream-caching-type="none | private | public" must-revalidate="true | false" allow-private-response-caching="@(expression to evaluate)"> <vary-by-header>Accept</vary-by-header> <!-- should be present in most cases --> <vary-by-header>Accept-Charset</vary-by-header> <!-- should be present in most cases --> <vary-by-header>Authorization</vary-by-header> <!-- should be present when allow-private-response-caching is "true"--> <vary-by-header>header name</vary-by-header> <!-- optional, can repeated several times --> <vary-by-query-parameter>parameter name</vary-by-query-parameter> <!-- optional, can repeated several times --> </cache-lookup>
ExamplesExamplesExampleExample
This topic provides a reference for the following API Management policies. For information on adding andconfiguring policies, see Policies in API Management.
Response caching policies
Get from cache - Perform cache look up and return a valid cached responses when available.Store to cache - Caches responses according to the specified cache control configuration.
Value caching policies
Get value from cache - Retrieve a cached item by key.Store value in cache - Store an item in the cache by key.Remove value from cache - Remove an item in the cache by key.
Use the cache-lookup policy to perform cache look up and return a valid cached response when available. Thispolicy can be applied in cases where response content remains static over a period of time. Response cachingreduces bandwidth and processing requirements imposed on the backend web server and lowers latencyperceived by API consumers.
This policy must have a corresponding Store to cache policy.
<policies> <inbound> <base /> <cache-lookup vary-by-developer="false" vary-by-developer-groups="false" downstream-caching-type="none" must-revalidate="true"> <vary-by-query-parameter>version</vary-by-query-parameter> </cache-lookup> </inbound> <outbound> <cache-store duration="seconds" /> <base /> </outbound> </policies>
Example using policy expressionsExample using policy expressions
<!-- The following cache policy snippets demonstrate how to control API Management reponse cache duration with Cache-Control headers sent by the backend service. -->
<!-- Copy this snippet into the inbound section --> <cache-lookup vary-by-developer="false" vary-by-developer-groups="false" downstream-caching-type="public" must-revalidate="true" > <vary-by-header>Accept</vary-by-header> <vary-by-header>Accept-Charset</vary-by-header> </cache-lookup>
<!-- Copy this snippet into the outbound section. Note that cache duration is set to the max-age value provided in the Cache-Control header received from the backend service or to the deafult value of 5 min if none is found --> <cache-store duration="@{ var header = context.Response.Headers.GetValueOrDefault("Cache-Control",""); var maxAge = Regex.Match(header, @"max-age=(?<maxAge>\d+)").Groups["maxAge"]?.Value; return (!string.IsNullOrEmpty(maxAge))?int.Parse(maxAge):300; }" />
ElementsElements
NAME DESCRIPTION REQUIRED
cache-lookup Root element. Yes
vary-by-header Start caching responses per value ofspecified header, such as Accept,Accept-Charset, Accept-Encoding,Accept-Language, Authorization, Expect,From, Host, If-Match.
No
vary-by-query-parameter Start caching responses per value ofspecified query parameters. Enter asingle or multiple parameters. Usesemicolon as a separator. If none arespecified, all query parameters are used.
No
This example shows how to to configure API Management response caching duration that matches the responsecaching of the backend service as specified by the backed service's Cache-Control directive. For a demonstration ofconfiguring and using this policy, see Cloud Cover Episode 177: More API Management Features with VladVinogradsky and fast-forward to 25:25.
For more information, see Policy expressions and Context variable.
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
allow-private-response-caching
When set to true , allowscaching of requests thatcontain an Authorizationheader.
No false
downstream-caching-type This attribute must be set toone of the following values.
- none - downstreamcaching is not allowed.- private - downstreamprivate caching is allowed.- public - private and shareddownstream caching isallowed.
No none
must-revalidate When downstream cachingis enabled this attributeturns on or off the must-revalidate cache
control directive in gatewayresponses.
No true
vary-by-developer Set to true to cacheresponses per developer key.
Yes
vary-by-developer-groups Set to true to cacheresponses per user role.
Yes
UsageUsage
Store to cache
NOTENOTE
Policy statementPolicy statement
<cache-store duration="seconds" />
ExamplesExamplesExampleExample
This policy can be used in the following policy sections and scopes.
Policy sections: inboundPolicy scopes: API, operation, product
The cache-store policy caches responses according to the specified cache settings. This policy can be applied incases where response content remains static over a period of time. Response caching reduces bandwidth andprocessing requirements imposed on the backend web server and lowers latency perceived by API consumers.
This policy must have a corresponding Get from cache policy.
<policies> <inbound> <base /> <cache-lookup vary-by-developer="true | false" vary-by-developer-groups="true | false" downstream-caching-type="none | private | public" must-revalidate="true | false"> <vary-by-query-parameter>parameter name</vary-by-query-parameter> <!-- optional, can repeated several times --> </cache-lookup> </inbound> <outbound> <base /> <cache-store duration="3600" /> </outbound> </policies>
Example using policy expressionsExample using policy expressions
<!-- The following cache policy snippets demonstrate how to control API Management reponse cache duration with Cache-Control headers sent by the backend service. -->
<!-- Copy this snippet into the inbound section --> <cache-lookup vary-by-developer="false" vary-by-developer-groups="false" downstream-caching-type="public" must-revalidate="true" > <vary-by-header>Accept</vary-by-header> <vary-by-header>Accept-Charset</vary-by-header> </cache-lookup>
<!-- Copy this snippet into the outbound section. Note that cache duration is set to the max-age value provided in the Cache-Control header received from the backend service or to the deafult value of 5 min if none is found --> <cache-store duration="@{ var header = context.Response.Headers.GetValueOrDefault("Cache-Control",""); var maxAge = Regex.Match(header, @"max-age=(?<maxAge>\d+)").Groups["maxAge"]?.Value; return (!string.IsNullOrEmpty(maxAge))?int.Parse(maxAge):300; }" />
ElementsElements
NAME DESCRIPTION REQUIRED
cache-store Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
duration Time-to-live of the cachedentries, specified in seconds.
Yes N/A
UsageUsage
This example shows how to to configure API Management response caching duration that matches the responsecaching of the backend service as specified by the backed service's Cache-Control directive. For a demonstration ofconfiguring and using this policy, see Cloud Cover Episode 177: More API Management Features with VladVinogradsky and fast-forward to 25:25.
For more information, see Policy expressions and Context variable.
This policy can be used in the following policy sections and scopes.
Policy sections: outbound
Get value from cache
NOTENOTE
Policy statementPolicy statement
<cache-lookup-value key="cache key value" default-value="value to use if cache lookup resulted in a miss" variable-name="name of a variable looked up value is assigned to" />
ExampleExample
<cache-lookup-value key="@("userprofile-" + context.Variables["enduserid"])" variable-name="userprofile" />
ElementsElements
NAME DESCRIPTION REQUIRED
cache-lookup-value Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
default-value A value that will be assignedto the variable if the cachekey lookup resulted in amiss. If this attribute is notspecified, null is assigned.
No null
key Cache key value to use inthe lookup.
Yes N/A
variable-name Name of the context variablethe looked up value will beassigned to, if lookup issuccessful. If lookup resultsin a miss, the variable will beassigned the value of the default-value attribute ornull , if the default-value attribute is
omitted.
Yes N/A
UsageUsage
Policy scopes: API, operation, product
Use the cache-lookup-value policy to perform cache lookup by key and return a cached value. The key can have anarbitrary string value and is typically provided using a policy expression.
This policy must have a corresponding Store value in cache policy.
For more information and examples of this policy, see Custom caching in Azure API Management.
Store value in cache
NOTENOTE
Policy statementPolicy statement
<cache-store-value key="cache key value" value="value to cache" duration="seconds" />
ExampleExample
<cache-store-value key="@("userprofile-" + context.Variables["enduserid"])" value="@((string)context.Variables["userprofile"])" duration="100000" />
ElementsElements
NAME DESCRIPTION REQUIRED
cache-store-value Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
duration Value will be cached for theprovided duration value,specified in seconds.
Yes N/A
key Cache key the value will bestored under.
Yes N/A
value The value to be cached. Yes N/A
UsageUsage
Remove value from cacheRemove value from cache
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-errorPolicy scopes: global, API, operation, product
The cache-store-value performs cache storage by key. The key can have an arbitrary string value and is typicallyprovided using a policy expression.
This policy must have a corresponding Get value from cache policy.
For more information and examples of this policy, see Custom caching in Azure API Management.
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-errorPolicy scopes: global, API, operation, product
The cache-remove-value deletes a cached item identified by its key. The key can have an arbitrary string value andis typically provided using a policy expression.
Policy statementPolicy statement
<cache-remove-value key="cache key value"/>
ExampleExample
<cache-remove-value key="@("userprofile-" + context.Variables["enduserid"])"/>
ElementsElements
NAME DESCRIPTION REQUIRED
cache-remove-value Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
key The key of the previouslycached value to be removedfrom the cache.
Yes N/A
UsageUsage
Next steps
This policy can be used in the following policy sections and scopes .
Policy sections: inbound, outbound, backend, on-errorPolicy scopes: global, API, operation, product
For more information working with policies, see:
Policies in API ManagementTransform APIsPolicy Reference for a full list of policy statements and their settingsPolicy samples
API Management cross domain policies12/4/2017 • 4 min to read • Edit Online
Cross domain policies
Allow cross-domain calls
Policy statementPolicy statement
<cross-domain> <!-Policy configuration is in the Adobe cross-domain policy file format, see http://www.adobe.com/devnet/articles/crossdomain_policy_file_spec.html--> </cross-domain>
ExampleExample
<cross-domain> <cross-domain-policy> <allow-http-request-headers-from domain='*' headers='*' /> </cross-domain-policy> </cross-domain>
ElementsElements
NAME DESCRIPTION REQUIRED
cross-domain Root element. Child elements mustconform to the Adobe cross-domainpolicy file specification.
Yes
UsageUsage
CORS
This topic provides a reference for the following API Management policies. For information on adding andconfiguring policies, see Policies in API Management.
Allow cross-domain calls - Makes the API accessible from Adobe Flash and Microsoft Silverlight browser-basedclients.CORS - Adds cross-origin resource sharing (CORS) support to an operation or an API to allow cross-domaincalls from browser-based clients.JSONP - Adds JSON with padding (JSONP) support to an operation or an API to allow cross-domain callsfrom JavaScript browser-based clients.
Use the cross-domain policy to make the API accessible from Adobe Flash and Microsoft Silverlight browser-based clients.
This policy can be used in the following policy sections and scopes.
Policy sections: inboundPolicy scopes: global
Policy statementPolicy statement
<cors allow-credentials="false|true"> <allowed-origins> <origin>origin uri</origin> </allowed-origins> <allowed-methods preflight-result-max-age="number of seconds"> <method>http verb</method> </allowed-methods> <allowed-headers> <header>header name</header> </allowed-headers> <expose-headers> <header>header name</header> </expose-headers> </cors>
ExampleExample
<cors allow-credentials="true"> <allowed-origins> <!-- Localhost useful for development --> <origin>http://localhost:8080/</origin> <origin>http://example.com/</origin> </allowed-origins> <allowed-methods preflight-result-max-age="300"> <method>GET</method> <method>POST</method> <method>PATCH</method> <method>DELETE</method> </allowed-methods> <allowed-headers> <!-- Examples below show Azure Mobile Services headers --> <header>x-zumo-installation-id</header> <header>x-zumo-application</header> <header>x-zumo-version</header> <header>x-zumo-auth</header> <header>content-type</header> <header>accept</header> </allowed-headers> <expose-headers> <!-- Examples below show Azure Mobile Services headers --> <header>x-zumo-installation-id</header> <header>x-zumo-application</header> </expose-headers> </cors>
ElementsElements
The cors policy adds cross-origin resource sharing (CORS) support to an operation or an API to allow cross-domain calls from browser-based clients.
CORS allows a browser and a server to interact and determine whether or not to allow specific cross-originrequests (i.e. XMLHttpRequests calls made from JavaScript on a web page to other domains). This allows for moreflexibility than only allowing same-origin requests, but is more secure than allowing all cross-origin requests.
This example demonstrates how to support pre-flight requests, such as those with custom headers or methodsother than GET and POST. To support custom headers and additional HTTP verbs, use the allowed-methods and allowed-headers sections as shown in the following example.
NAME DESCRIPTION REQUIRED DEFAULT
cors Root element. Yes N/A
allowed-origins Contains origin elementsthat describe the allowedorigins for cross-domainrequests. allowed-origins
can contain either a single origin element that
specifies * to allow anyorigin, or one or more origin elements that
contain a URI.
Yes N/A
origin The value can be either *
to allow all origins, or a URIthat specifies a single origin.The URI must include ascheme, host, and port.
Yes If the port is omitted in aURI, port 80 is used forHTTP and port 443 is usedfor HTTPS.
allowed-methods This element is required ifmethods other than GET orPOST are allowed. Contains method elements that
specify the supported HTTPverbs.
No If this section is not present,GET and POST aresupported.
method Specifies an HTTP verb. At least one method
element is required if the allowed-methods section is
present.
N/A
allowed-headers This element contains header elements specifying
names of the headers thatcan be included in therequest.
No N/A
expose-headers This element contains header elements specifying
names of the headers thatwill be accessible by theclient.
No N/A
header Specifies a header name. At least one header
element is required in allowed-headers or expose-headers if the
section is present.
N/A
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
allow-credentials The Access-Control-Allow-Credentials
header in the preflightresponse will be set to thevalue of this attribute andaffect the client’s abilityto submit credentials incross-domain requests.
No false
preflight-result-max-age The Access-Control-Max-Age
header in the preflightresponse will be set to thevalue of this attribute andaffect the user agent’sability to cache pre-flightresponse.
No 0
NAME DESCRIPTION REQUIRED DEFAULT
UsageUsage
JSONP
Policy statementPolicy statement
<jsonp callback-parameter-name="callback function name" />
ExampleExample
<jsonp callback-parameter-name="cb" />
ElementsElements
NAME DESCRIPTION REQUIRED
jsonp Root element. Yes
AttributesAttributes
This policy can be used in the following policy sections and scopes.
Policy sections: inboundPolicy scopes: API, operation
The jsonp policy adds JSON with padding (JSONP) support to an operation or an API to allow cross-domaincalls from JavaScript browser-based clients. JSONP is a method used in JavaScript programs to request data froma server in a different domain. JSONP bypasses the limitation enforced by most web browsers where access toweb pages must be in the same domain.
If you call the method without the callback parameter ?cb=XXX it will return plain JSON (without a function callwrapper).
If you add the callback parameter ?cb=XXX it will return a JSONP result, wrapping the original JSON resultsaround the callback function like XYZ('<json result goes here>');
NAME DESCRIPTION REQUIRED DEFAULT
callback-parameter-name The cross-domain JavaScriptfunction call prefixed withthe fully qualified domainname where the functionresides.
Yes N/A
UsageUsage
Next steps
This policy can be used in the following policy sections and scopes.
Policy sections: outboundPolicy scopes: global, product, API, operation
For more information working with policies, see:
Policies in API ManagementTransform APIsPolicy Reference for a full list of policy statements and their settingsPolicy samples
API Management transformation policies3/23/2018 • 16 min to read • Edit Online
Transformation policies
Convert JSON to XML
Policy statementPolicy statement
<json-to-xml apply="always | content-type-json" consider-accept-header="true | false" parse-date="true | false"/>
ExampleExample
<policies> <inbound> <base /> </inbound> <outbound> <base /> <json-to-xml apply="always" consider-accept-header="false" parse-date="false"/> </outbound></policies>
ElementsElements
This topic provides a reference for the following API Management policies. For information on adding andconfiguring policies, see Policies in API Management.
Convert JSON to XML - Converts request or response body from JSON to XML.
Convert XML to JSON - Converts request or response body from XML to JSON.
Find and replace string in body - Finds a request or response substring and replaces it with a differentsubstring.
Mask URLs in content - Re-writes (masks) links in the response body so that they point to the equivalentlink via the gateway.
Set backend service - Changes the backend service for an incoming request.
Set body - Sets the message body for incoming and outgoing requests.
Set HTTP header - Assigns a value to an existing response and/or request header or adds a new responseand/or request header.
Set query string parameter - Adds, replaces value of, or deletes request query string parameter.
Rewrite URL - Converts a request URL from its public form to the form expected by the web service.
Transform XML using an XSLT - Applies an XSL transformation to XML in the request or response body.
The json-to-xml policy converts a request or response body from JSON to XML.
NAME DESCRIPTION REQUIRED
json-to-xml Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
apply The attribute must be set toone of the following values.
- always - always applyconversion.- content-type-json -convert only if responseContent-Type headerindicates presence of JSON.
Yes N/A
consider-accept-header The attribute must be set toone of the following values.
- true - apply conversion ifJSON is requested in requestAccept header.- false -always applyconversion.
No true
parse-date When set to false datevalues are simply copiedduring transformation
No true
UsageUsage
Convert XML to JSON
Policy statementPolicy statement
<xml-to-json kind="javascript-friendly | direct" apply="always | content-type-xml" consider-accept-header="true | false"/>
ExampleExample
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, on-error
Policy scopes: global, product, API, operation
The xml-to-json policy converts a request or response body from XML to JSON. This policy can be used tomodernize APIs based on XML-only backend web services.
<policies> <inbound> <base /> </inbound> <outbound> <base /> <xml-to-json kind="direct" apply="always" consider-accept-header="false" /> </outbound></policies>
ElementsElements
NAME DESCRIPTION REQUIRED
xml-to-json Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
kind The attribute must be set toone of the following values.
- javascript-friendly - theconverted JSON has a formfriendly to JavaScriptdevelopers.- direct - the convertedJSON reflects the originalXML document's structure.
Yes N/A
apply The attribute must be set toone of the following values.
- always - convert always.- content-type-xml - convertonly if response Content-Type header indicatespresence of XML.
Yes N/A
consider-accept-header The attribute must be set toone of the following values.
- true - apply conversion ifXML is requested in requestAccept header.- false -always applyconversion.
No true
UsageUsage
Find and replace string in body
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, on-error
Policy scopes: global, product, API, operation
The find-and-replace policy finds a request or response substring and replaces it with a different substring.
Policy statementPolicy statement
<find-and-replace from="what to replace" to="replacement" />
ExampleExample
<find-and-replace from="notebook" to="laptop" />
ElementsElements
NAME DESCRIPTION REQUIRED
find-and-replace Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
from The string to search for. Yes N/A
to The replacement string.Specify a zero lengthreplacement string toremove the search string.
Yes N/A
UsageUsage
Mask URLs in content
NOTENOTE
Policy statementPolicy statement
<redirect-content-urls />
ExampleExample
<redirect-content-urls />
ElementsElements
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-error
Policy scopes: global, product, API, operation
The redirect-content-urls policy re-writes (masks) links in the response body so that they point to the equivalentlink via the gateway. Use in the outbound section to re-write response body links to make them point to thegateway. Use in the inbound section for an opposite effect.
This policy does not change any header values such as Location headers. To change header values, use the set-headerpolicy.
NAME DESCRIPTION REQUIRED
redirect-content-urls Root element. Yes
UsageUsage
Set backend service
Policy statementPolicy statement
<set-backend-service base-url="base URL of the backend service" />
ExampleExample
<policies> <inbound> <choose> <when condition="@(context.Request.Url.Query.GetValueOrDefault("version") == "2013-05")"> <set-backend-service base-url="http://contoso.com/api/8.2/" /> </when> <when condition="@(context.Request.Url.Query.GetValueOrDefault("version") == "2014-03")"> <set-backend-service base-url="http://contoso.com/api/9.1/" /> </when> </choose> <base /> </inbound> <outbound> <base /> </outbound></policies>
ExampleExample
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound
Policy scopes: global, product, API, operation
Use the set-backend-service policy to redirect an incoming request to a different backend than the one specifiedin the API settings for that operation. This policy changes the backend service base URL of the incoming request tothe one specified in the policy.
In this example the set backend service policy routes requests based on the version value passed in the querystring to a different backend service than the one specified in the API.
Initially the backend service base URL is derived from the API settings. So the request URL https://contoso.azure-api.net/api/partners/15?version=2013-05&subscription-key=abcdef becomes http://contoso.com/api/10.4/partners/15?version=2013-05&subscription-key=abcdef where http://contoso.com/api/10.4/ is the backend service URL specified in the API settings.
When the <choose> policy statement is applied the backend service base URL may change again either to http://contoso.com/api/8.2 or http://contoso.com/api/9.1 , depending on the value of the version request query
parameter. For example, if the value is "2013-15" the final request URL becomes http://contoso.com/api/8.2/partners/15?version=2013-05&subscription-key=abcdef .
If further transformation of the request is desired, other Transformation policies can be used. For example, toremove the version query parameter now that the request is being routed to a version specific backend, the Setquery string parameter policy can be used to remove the now redundant version attribute.
<policies> <inbound> <set-backend-service backend-id="my-sf-service" sf-partition-key="@(context.Request.Url.Query.GetValueOrDefault("userId","")" sf-replica-type="primary" /> </inbound> <outbound> <base /> </outbound></policies>
ElementsElements
NAME DESCRIPTION REQUIRED
set-backend-service Root element. Yes
AttributesAttributes
NAME DESCRIPTION REQUIRED DEFAULT
base-url New backend service baseURL.
No N/A
backend-id Identifier of the backend toroute to.
No N/A
sf-partition-key Only applicable when thebackend is a Service Fabricservice and is specified using'backend-id'. Used to resolvea specific partition from thename resolution service.
No N/A
sf-replica-type Only applicable when thebackend is a Service Fabricservice and is specified using'backend-id'. Controls if therequest should go to theprimary or secondary replicaof a partition.
No N/A
sf-resolve-condition Only applicable when thebackend is a Service Fabricservice. Condition identifyingif the call to Service Fabricbackend has to be repeatedwith new resolution.
No N/A
sf-service-instance-name Only applicable when thebackend is a Service Fabricservice. Allows to changeservice instances at runtime.
No N/A
In this example the policy routes the request to a service fabric backend, using the userId query string as thepartition key and using the primary replica of the partition.
sf-listener-name Only applicable when thebackend is a Service Fabricservice and is specified using‘backend-id’. ServiceFabric Reliable Servicesallows you to create multiplelisteners in a service. Thisattribute is used to select aspecific listener when abackend Reliable Service hasmore than one listener. Ifthis attribute is not specified,API Management willattempt to use a listenerwithout a name. A listenerwithout a name is typical forReliable Services that haveonly one listener.
No N/A
NAME DESCRIPTION REQUIRED DEFAULT
UsageUsage
Set body
IMPORTANTIMPORTANT
Policy statementPolicy statement
<set-body>new body value as text</set-body>
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, backend
Policy scopes: global, product, API, operation
Use the set-body policy to set the message body for incoming and outgoing requests. To access the messagebody you can use the context.Request.Body property or the context.Response.Body , depending on whether thepolicy is in the inbound or outbound section.
Note that by default when you access the message body using context.Request.Body or context.Response.Body , theoriginal message body is lost and must be set by returning the body back in the expression. To preserve the body content,set the preserveContent parameter to true when accessing the message. If preserveContent is set to true and adifferent body is returned by the expression, the returned body is used.
Please note the following considerations when using the set-body policy.
If you are using the set-body policy to return a new or updated body you don't need to set preserveContent to true because you are explicitly supplying the new body contents.
Preserving the content of a response in the inbound pipeline doesn't make sense because there is no responseyet.Preserving the content of a request in the outbound pipeline doesn't make sense because the request has alreadybeen sent to the backend at this point.If this policy is used when there is no message body, for example in an inbound GET, an exception is thrown.
For more information, see the context.Request.Body , context.Response.Body , and the IMessage sections in theContext variable table.
ExamplesExamplesLiteral text exampleLiteral text example
<set-body>Hello world!</set-body>
Example accessing the body as a string. Note that we are preserving the original request body so that we can access it later in theExample accessing the body as a string. Note that we are preserving the original request body so that we can access it later in thepipeline.pipeline.
<set-body>@{ string inBody = context.Request.Body.As<string>(preserveContent: true); if (inBody[0] =='c') { inBody[0] = 'm'; } return inBody; }</set-body>
Example accessing the body as a JObject. Note that since we are not reserving the original request body, accesing it later in theExample accessing the body as a JObject. Note that since we are not reserving the original request body, accesing it later in thepipeline will result in an exception.pipeline will result in an exception.
<set-body> @{ JObject inBody = context.Request.Body.As<JObject>(); if (inBody.attribute == <tag>) { inBody[0] = 'm'; } return inBody.ToString(); } </set-body>
Filter response based on productFilter response based on product
<!-- Copy this snippet into the outbound section to remove a number of data elements from the response received from the backend service based on the name of the api product --><choose> <when condition="@(context.Response.StatusCode == 200 && context.Product.Name.Equals("Starter"))"> <set-body>@{ var response = context.Response.Body.As<JObject>(); foreach (var key in new [] {"minutely", "hourly", "daily", "flags"}) { response.Property (key).Remove (); } return response.ToString(); } </set-body> </when></choose>
Using Liquid templates with set bodyUsing Liquid templates with set body
This example shows how to perform content filtering by removing data elements from the response received fromthe backend service when using the Starter product. For a demonstration of configuring and using this policy,see Cloud Cover Episode 177: More API Management Features with Vlad Vinogradsky and fast-forward to 34:30.Start at 31:50 to see an overview of The Dark Sky Forecast API used for this demo.
The set-body policy can be configured to use the Liquid templating language to transfom the body of a request orresponse. This can be very effective if you need to completely reshape the format of your message.
IMPORTANTIMPORTANT
IMPORTANTIMPORTANT
Convert JSON to SOAP using a Liquid templateConvert JSON to SOAP using a Liquid template
<set-body template="liquid"> <soap:Envelope xmlns="http://tempuri.org/" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"> <soap:Body> <GetOpenOrders> <cust>{{body.getOpenOrders.cust}}</cust> </GetOpenOrders> </soap:Body> </soap:Envelope></set-body>
Tranform JSON using a Liquid templateTranform JSON using a Liquid template
{"order": { "id": "{{body.customer.purchase.identifier}}", "summary": "{{body.customer.purchase.orderShortDesc}}" }}
ElementsElements
NAME DESCRIPTION REQUIRED
set-body Root element. Contains the body text oran expressions that returns a body.
Yes
PropertiesProperties
NAME DESCRIPTION REQUIRED DEFAULT
template Used to change thetemplating mode that theset body policy will run in.Currently the onlysupported value is:
- liquid - the set body policywill use the liquid templatingengine
No liquid
The implementation of Liquid used in the set-body policy is configured in 'C# mode'. This is particularly important whendoing things such as filtering. As an example, using a date filter requires the use of Pascal casing and C# date formatting e.g.:
{{body.foo.startDateTime| Date:"yyyyMMddTHH:mm:ddZ"}}
In order to correctly bind to an XML body using the Liquid template, use a set-header policy to set Content-Type to eitherapplication/xml, text/xml (or any type ending with +xml); for a JSON body, it must be application/json, text/json (or any typeending with +json).
For accessing information about the request and response, the Liquid template can bind to a context object withthe following properties:
context. Request. Url Method OriginalMethod OriginalUrl IpAddress MatchedParameters HasBody ClientCertificates Headers
Response. StatusCode Method HeadersUrl. Scheme Host Port Path Query QueryString ToUri ToString
OriginalUrl. Scheme Host Port Path Query QueryString ToUri ToString
UsageUsage
Set HTTP header
Policy statementPolicy statement
<set-header name="header name" exists-action="override | skip | append | delete"> <value>value</value> <!--for multiple headers with the same name add additional value elements--></set-header>
ExamplesExamples
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend
Policy scopes: global, product, API, operation
The set-header policy assigns a value to an existing response and/or request header or adds a new responseand/or request header.
Inserts a list of HTTP headers into an HTTP message. When placed in an inbound pipeline, this policy sets theHTTP headers for the request being passed to the target service. When placed in an outbound pipeline, this policysets the HTTP headers for the response being sent to the gateway’s client.
ExampleExample
<set-header name="some header name" exists-action="override"> <value>20</value></set-header>
Forward context information to the backend serviceForward context information to the backend service
<!-- Copy this snippet into the inbound element to forward some context information, user id and the region the gateway is hosted in, to the backend service for logging or evaluation --><set-header name="x-request-context-data" exists-action="override"> <value>@(context.User.Id)</value> <value>@(context.Deployment.Region)</value></set-header>
ElementsElements
NAME DESCRIPTION REQUIRED
set-header Root element. Yes
value Specifies the value of the header to beset. For multiple headers with the samename add additional value elements.
Yes
PropertiesProperties
NAME DESCRIPTION REQUIRED DEFAULT
exists-action Specifies what action to takewhen the header is alreadyspecified. This attribute musthave one of the followingvalues.
- override - replaces thevalue of the existing header.- skip - does not replace theexisting header value.- append - appends thevalue to the existing headervalue.- delete - removes theheader from the request.
When set to override
enlisting multiple entrieswith the same name resultsin the header being setaccording to all entries(which will be listed multipletimes); only listed values willbe set in the result.
No override
This example shows how to apply policy at the API level to supply context information to the backend service. Fora demonstration of configuring and using this policy, see Cloud Cover Episode 177: More API ManagementFeatures with Vlad Vinogradsky and fast-forward to 10:30. At 12:10 there is a demo of calling an operation in thedeveloper portal where you can see the policy at work.
For more information, see Policy expressions and Context variable.
name Specifies name of the headerto be set.
Yes N/A
NAME DESCRIPTION REQUIRED DEFAULT
UsageUsage
Set query string parameter
Policy statementPolicy statement
<set-query-parameter name="param name" exists-action="override | skip | append | delete"> <value>value</value> <!--for multiple parameters with the same name add additional value elements--></set-query-parameter>
ExamplesExamplesExampleExample
<set-query-parameter> <parameter name="api-key" exists-action="skip"> <value>12345678901</value> </parameter> <!-- for multiple parameters with the same name add additional value elements --></set-query-parameter>
Forward context information to the backend serviceForward context information to the backend service
<!-- Copy this snippet into the inbound element to forward a piece of context, product name in this example, to the backend service for logging or evaluation --><set-query-parameter name="x-product-name" exists-action="override"> <value>@(context.Product.Name)</value></set-query-parameter>
ElementsElements
NAME DESCRIPTION REQUIRED
set-query-parameter Root element. Yes
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound, backend, on-error
Policy scopes: global, product, API, operation
The set-query-parameter policy adds, replaces value of, or deletes request query string parameter. Can be used topass query parameters expected by the backend service which are optional or never present in the request.
This example shows how to apply policy at the API level to supply context information to the backend service. Fora demonstration of configuring and using this policy, see Cloud Cover Episode 177: More API ManagementFeatures with Vlad Vinogradsky and fast-forward to 10:30. At 12:10 there is a demo of calling an operation in thedeveloper portal where you can see the policy at work.
For more information, see Policy expressions and Context variable.
value Specifies the value of the queryparameter to be set. For multiple queryparameters with the same name addadditional value elements.
Yes
NAME DESCRIPTION REQUIRED
PropertiesProperties
NAME DESCRIPTION REQUIRED DEFAULT
exists-action Specifies what action to takewhen the query parameter isalready specified. Thisattribute must have one ofthe following values.
- override - replaces thevalue of the existingparameter.- skip - does not replace theexisting query parametervalue.- append - appends thevalue to the existing queryparameter value.- delete - removes the queryparameter from the request.
When set to override
enlisting multiple entrieswith the same name resultsin the query parameterbeing set according to allentries (which will be listedmultiple times); only listedvalues will be set in theresult.
No override
name Specifies name of the queryparameter to be set.
Yes N/A
UsageUsage
Rewrite URL
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, backend
Policy scopes: global, product, API, operation
The rewrite-uri policy converts a request URL from its public form to the form expected by the web service, asshown in the following example.
Public URL - http://api.example.com/storenumber/ordernumber
Request URL - http://api.example.com/v2/US/hardware/storenumber&ordernumber?City&State
This policy can be used when a human and/or browser-friendly URL should be transformed into the URLformat expected by the web service. This policy only needs to be applied when exposing an alternative URL
NOTENOTE
Policy statementPolicy statement
<rewrite-uri template="uri template" copy-unmatched-params="true | false" />
ExampleExample
<policies> <inbound> <base /> <rewrite-uri template="/v2/US/hardware/{storenumber}&{ordernumber}?City=city&State=state" /> </inbound> <outbound> <base /> </outbound></policies>
<!-- Assuming incoming request is /get?a=b&c=d and operation template is set to /get?a={b} --><policies> <inbound> <base /> <rewrite-uri template="/put" /> </inbound> <outbound> <base /> </outbound></policies><!-- Resulting URL will be /put?c=d -->
<!-- Assuming incoming request is /get?a=b&c=d and operation template is set to /get?a={b} --><policies> <inbound> <base /> <rewrite-uri template="/put" copy-unmatched-params="false" /> </inbound> <outbound> <base /> </outbound></policies><!-- Resulting URL will be /put -->
ElementsElements
NAME DESCRIPTION REQUIRED
rewrite-uri Root element. Yes
AttributesAttributes
format, such as clean URLs, RESTful URLs, user-friendly URLs or SEO-friendly URLs that are purelystructural URLs that do not contain a query string and instead contain only the path of the resource (afterthe scheme and the authority). This is often done for aesthetic, usability, or search engine optimization(SEO) purposes.
You can only add query string parameters using the policy. You cannot add extra template path parameters in the rewriteURL.
ATTRIBUTE DESCRIPTION REQUIRED DEFAULT
template The actual web service URLwith any query stringparameters. When usingexpressions, the whole valuemust be an expression.
Yes N/A
copy-unmatched-params Specifies whether queryparameters in the incomingrequest not present in theoriginal URL template areadded to the URL defined bythe re-write template
No true
UsageUsage
Transform XML using an XSLT
Policy statementPolicy statement
<xsl-transform> <parameter name="User-Agent">@(context.Request.Headers.GetValueOrDefault("User-Agent","non-specified"))</parameter> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="xml" indent="yes" /> <xsl:param name="User-Agent" /> <xsl:template match="* | @* | node()"> <xsl:copy> <xsl:if test="self::* and not(parent::*)"> <xsl:attribute name="User-Agent"> <xsl:value-of select="$User-Agent" /> </xsl:attribute> </xsl:if> <xsl:apply-templates select="* | @* | node()" /> </xsl:copy> </xsl:template> </xsl:stylesheet> </xsl-transform>
ExampleExample
This policy can be used in the following policy sections and scopes.
Policy sections: inbound
Policy scopes: product, API, operation
The Transform XML using an XSLT policy applies an XSL transformation to XML in the request or response body.
<policies> <inbound> <base /> </inbound> <outbound> <base /> <xsl-transform> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output omit-xml-declaration="yes" method="xml" indent="yes" /> <!-- Copy all nodes directly--> <xsl:template match="node()| @*|*"> <xsl:copy> <xsl:apply-templates select="@* | node()|*" /> </xsl:copy> </xsl:template> </xsl:stylesheet> </xsl-transform> </outbound></policies>
ElementsElements
NAME DESCRIPTION REQUIRED
xsl-transform Root element. Yes
parameter Used to define variables used in thetransform
No
xsl:stylesheet Root stylesheet element. All elementsand attributes defined within follow thestandard XSLT specification
Yes
UsageUsage
Next steps
This policy can be used in the following policy sections and scopes.
Policy sections: inbound, outbound
Policy scopes: global, product, API, operation
For more information, see the following topics:
Policies in API ManagementPolicy Reference for a full list of policy statements and their settingsPolicy samples
Developer portal templates12/4/2017 • 1 min to read • Edit Online
Developer portal templates
Next steps
Azure API Management provides you the ability to customize the content of developer portal pages using a set oftemplates that configure their content. Using DotLiquid syntax and the editor of your choice, such as DotLiquid forDesigners, and a provided set of localized String resources, Glyph resources, and Page controls, you have greatflexibility to configure the content of the pages as you see fit using these templates.
For more information about working with templates, see How to customize the API Management developerportal using templates.
APIs
Products
Applications
Issues
User Profile
Pages
API listOperationCode samples
CurlC#JavaJavaScriptObjective CPHPPythonRuby
Product listProduct
Application listApplication
Issue list
ProfileSubscriptionsApplicationsUpdate account info
Sign inSign upPage not found
Template reference
Data model referencePage controlsTemplate resources
API templates in Azure API Management12/4/2017 • 19 min to read • Edit Online
NOTENOTE
API list
Default templateDefault template
Azure API Management provides you the ability to customize the content of developer portal pages using a set oftemplates that configure their content. Using DotLiquid syntax and the editor of your choice, such as DotLiquid forDesigners, and a provided set of localized String resources, Glyph resources, and Page controls, you have greatflexibility to configure the content of the pages as you see fit using these templates.
The templates in this section allow you to customize the content of the API pages in the developer portal.
API listOperationCode samples
CurlC#JavaJavaScriptObjective CPHPPythonRuby
Sample default templates are included in the following documentation, but are subject to change due to continuousimprovements. You can view the live default templates in the developer portal by navigating to the desired individualtemplates. For more information about working with templates, see How to customize the API Management developerportal using templates.
The API list template allows you to customize the body of the API list page in the developer portal.
<search-control></search-control> <div class="row"> <div class="col-md-9"> <h2>{% localized "ApisStrings|PageTitleApis" %}</h2> </div> </div> <div class="row"> <div class="col-md-12"> {% if apis.size > 0 %} <ol class="list-unstyled"> {% for api in apis %} <li> <h3> <a href="/docs/services/{{api.id}}">{{api.name}}</a> </h3> {{api.description}} </li> {% endfor %} </ol> <paging-control></paging-control> {% else %} {% localized "CommonResources|NoItemsToDisplay" %} {% endif %} </div> </div>
ControlsControls
Data modelData model
PROPERTY TYPE DESCRIPTION
apis Collection of API summary entities. The APIs visible to the current user.
Sample template dataSample template data
{ "apis": [ { "id": "570275f1b16653124c8f9ba3", "name": "Basic Calculator", "description": "Arithmetics is just a call away!" }, { "id": "57026e30de15d80041040001", "name": "Echo API", "description": null } ], "pageTitle": "APIs" }
Operation
The API list template may use the following page controls.
paging-control
search-control
The Operation template allows you to customize the body of the operation page in the developer portal.
Default templateDefault template
<h2>{{api.name}}</h2> <p>{{api.description }}</p>
<div class="panel"> <h3>{{operation.name}}</h3> <p>{{operation.description }}</p> <a class="btn btn-primary" href="{{consoleUrl}}" id="btnOpenConsole" role="button"> Try it </a> </div>
<h4>{% localized "Documentation|SectionHeadingRequestUrl" %}</h4> <div class="panel"> <div class="panel-body"> <label>{{ sampleUrl | escape }}</label> </div> </div>
{% if operation.request %} {% if operation.request.parameters.size > 0 %} <h4>{% localized "Documentation|SectionHeadingRequestParameters" %}</h4>
<div class="panel"> {% for parameter in operation.request.parameters %} <div class="row panel-body"> <div class="col-md-3"> <label>{{parameter.name}}</label> {% unless parameter.required %} <span class="text-muted">({% localized "Documentation|FormLabelSubtextOptional" %})</span> {% endunless %} </div>
<div class="col-md-1"> {{parameter.typeName}} </div> <div class="col-md-8"> {{parameter.description}} </div> </div> {% endfor %} </div> {% endif %}
{% if operation.request.headers.size > 0 %} <h4>{% localized "Documentation|SectionHeadingRequestHeaders" %}</h4> <div class="panel"> {% for header in operation.request.headers %} <div class="row panel-body"> <div class="col-md-3"> <label>{{header.name}}</label> {%unless header.required %} <span class="text-muted">({% localized "Documentation|FormLabelSubtextOptional" %})</span> {% endunless %} </div> <div class="col-md-1"> {{header.typeName}} </div> <div class="col-md-8"> {{header.description}} </div> </div> {% endfor %} </div> {% endif %}
{% if operation.request.description or operation.request.representations.size > 0 %} <h4>{% localized "Documentation|SectionHeadingRequestBody" %}</h4> <div class="panel"> {% if operation.request.description %} <p>{{operation.request.description }}</p> {% endif %}
{% if operation.request.representations.size > 0 %} <div role="tabpanel"> <ul class="nav nav-tabs" role="tablist"> {% for representation in operation.request.representations %} <li role="presentation" {% if forloop.first %}class="active"{% endif %}> <a href="#requesttab{{forloop.index}}" role="tab" data-toggle="tab"> {{representation.contentType}} </a> </li> {% endfor %} </ul> <div class="tab-content tab-content-boxed"> {% for representation in operation.request.representations %} <div id="requesttab{{forloop.index}}" role="tabpanel" class="tab-pane snippet{% if forloop.first %} active{% endif %}">
{% if representation.sample or representation.schema %} <div role="tabpanel"> {% if representation.sample and representation.schema %} <ul class="nav nav-tabs-borderless" role="tablist"> <li role="presentation" class="active"> <a href="#requesttab{{forloop.index}}sample" role="tab" data-toggle="tab">Sample</a> </li> <li role="presentation"> <a href="#requesttab{{forloop.index}}schema" role="tab" data-toggle="tab">Schema</a> </li>
</ul> {% endif %}
<div class="tab-content"> {% if representation.sample %} <div id="requesttab{{forloop.index}}sample" role="tabpanel" class="tab-pane snippet active"> <pre><code class="{{representation.Brush}}">{{ representation.sample | escape }}</code></pre> </div> {% endif %}
{% if representation.schema %} <div id="requesttab{{forloop.index}}schema" role="tabpanel" class="tab-pane snippet"> <pre><code class="{{representation.Brush}}">{{ representation.schema | escape }}</code></pre> </div> {% endif %} </div> </div> {% endif %} </div> {% endfor %} </div> </div> {% endif %}
<div class="clearfix"></div> </div> {% endif %} {% endif %}
{% if operation.responses.size > 0 %} {% for response in operation.responses %} {% if response.description or response.representations.size > 0 %} <h4>{% localized "Documentation|SectionHeadingResponse" %} {{response.statusCode}}</h4>
<div class="panel"> {% if response.description %} <p>{{ response.description }}</p> {% endif %}
{% if response.representations.size > 0 %} <div role="tabpanel"> <ul class="nav nav-tabs" role="tablist"> {% for representation in response.representations %} <li role="presentation" {% if forloop.first %}class="active"{% endif %}> <a href="#response{{response.statusCode}}tab{{forloop.index}}" role="tab" data-toggle="tab"> {{representation.contentType}} </a> </li> {% endfor %} </ul> <div class="tab-content tab-content-boxed"> {% for representation in response.representations %} <div id="response{{response.statusCode}}tab{{forloop.index}}" role="tabpanel" class="tab-pane snippet{% if forloop.first %} active{% endif %}">
{% if representation.sample or representation.schema %} <div role="tabpanel">
{% if representation.sample and representation.schema %} <ul class="nav nav-tabs-borderless" role="tablist"> <li role="presentation" class="active"> <a href="#response{{response.statusCode}}tab{{forloop.index}}sample" role="tab" data-toggle="tab"> Sample
Sample </a> </li> <li role="presentation"> <a href="#response{{response.statusCode}}tab{{forloop.index}}schema" role="tab" data-toggle="tab"> Schema </a> </li> </ul> {% endif %}
<div class="tab-content"> {% if representation.sample %} <div id="response{{response.statusCode}}tab{{forloop.index}}sample" role="tabpanel" class="tab-pane snippet active"> <pre><code class="{{representation.Brush}}">{{ representation.sample | escape }}</code></pre> </div> {% endif %}
{% if representation.schema %} <div id="response{{response.statusCode}}tab{{forloop.index}}schema" role="tabpanel" class="tab-pane snippet"> <pre><code class="{{representation.Brush}}">{{ representation.schema | escape }}</code></pre> </div> {% endif %} </div> </div> {% endif %} </div> {% endfor %} </div> </div> {% endif %}
<div class="clearfix"></div> </div>
{% endif %} {% endfor %} {% endif %}
<h4>{% localized "Documentation|SectionHeadingCodeSamples" %}</h4> <div role="tabpanel"> <ul class="nav nav-tabs" role="tablist"> {% for sample in samples %} <li role="presentation" {% if forloop.first %}class="active"{% endif %}> <a href="#{{sample.brush}}" aria-controls="{{sample.brush}}" role="tab" data-toggle="tab"> {{sample.title}} </a> </li> {% endfor %} </ul> <div class="tab-content tab-content-boxed" title="{% localized "Documentation|TooltipTextDoubleClickToSelectAll=""" %}"> {% for sample in samples %} <div role="tabpanel" class="tab-pane tab-content-boxed {% if forloop.first %} active{% endif %} snippet snippet-resizable" id="{{sample.brush}}" > <pre><code class="{{sample.brush}}">{% partial sample.template for sample in samples %}</code></pre> </div> {% endfor %} </div> <div class="clearfix"></div> </div>
ControlsControls
Data modelData model
PROPERTY TYPE DESCRIPTION
apiId string The id of the current API.
apiName string The name of the API.
apiDescription string A description of the API.
api API summary entity. The current API.
operation Operation The currently displayed operation.
sampleUrl string The URL for the current operation.
operationMenu Operation menu A menu of operations for this API.
consoleUrl URI The URI for the Try it button.
samples Collection of Code sample entities. The code samples for the currentoperation..
Sample template dataSample template data
{ "apiId": "570275f1b16653124c8f9ba3", "apiName": "Basic Calculator", "apiDescription": "Arithmetics is just a call away!", "api": { "id": "570275f1b16653124c8f9ba3", "name": "Basic Calculator", "description": "Arithmetics is just a call away!" }, "operation": { "id": "570275f2b1665305c811cf49", "name": "Add two integers", "description": "Produces a sum of two numbers.", "scheme": "https", "uriTemplate": "calc/add?a={a}&b={b}", "host": "sdcontoso5.azure-api.net", "httpMethod": "GET", "request": { "description": null, "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [ { "name": "a",
The Operation template does not allow the use of any page controls.
"name": "a", "description": "First operand. Default value is <code>51</code>.", "value": "51", "options": [ "51" ], "required": true, "kind": 1, "typeName": null }, { "name": "b", "description": "Second operand. Default value is <code>49</code>.", "value": "49", "options": [ "49" ], "required": true, "kind": 1, "typeName": null } ], "representations": [] }, "responses": [] }, "sampleUrl": "https://sdcontoso5.azure-api.net/calc/add?a={a}&b={b}", "operationMenu": { "ApiId": "570275f1b16653124c8f9ba3", "CurrentOperationId": "570275f2b1665305c811cf49", "Action": "Operation", "MenuItems": [ { "Id": "570275f2b1665305c811cf49", "Title": "Add two integers", "HttpMethod": "GET" }, { "Id": "570275f2b1665305c811cf4c", "Title": "Divide two integers", "HttpMethod": "GET" }, { "Id": "570275f2b1665305c811cf4b", "Title": "Multiply two integers", "HttpMethod": "GET" }, { "Id": "570275f2b1665305c811cf4a", "Title": "Subtract two integers", "HttpMethod": "GET" } ] }, "consoleUrl": "/docs/services/570275f1b16653124c8f9ba3/operations/570275f2b1665305c811cf49/console", "samples": [ { "title": "Curl", "snippet": null, "brush": "plain", "template": "DocumentationSamplesCurl", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key",
"name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }, { "title": "C#", "snippet": null, "brush": "csharp", "template": "DocumentationSamplesCsharp", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }, { "title": "Java", "snippet": null, "brush": "java", "template": "DocumentationSamplesJava", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }, { "title": "JavaScript", "snippet": null, "brush": "xml", "template": "DocumentationSamplesJs", "body": "{body}", "method": "GET",
"scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }, { "title": "ObjC", "snippet": null, "brush": "objc", "template": "DocumentationSamplesObjc", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }, { "title": "PHP", "snippet": null, "brush": "php", "template": "DocumentationSamplesPhp", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }, {
{ "title": "Python", "snippet": null, "brush": "python", "template": "DocumentationSamplesPython", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }, { "title": "Ruby", "snippet": null, "brush": "ruby", "template": "DocumentationSamplesRuby", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] } ] }
Code samplesThe following templates allow you to customize the body of the individual code samples on the operation page.
CurlCurl
Default templateDefault template
@ECHO OFF
curl -v -X {{method}} "{{scheme}}://{{host}}{{path}}{{query | escape }}" {% for header in headers -%} -H "{{ header.name }}: {{ header.value }}" {% endfor -%} {% if body -%} --data-ascii "{{ body | replace:'"','^"' }}" {% endif -%}
ControlsControls
Data modelData model
Sample template dataSample template data
Curl
C#
Java
JavaScript
Objective C
PHP
Python
Ruby
The DocumentationSamplesCurl template allows you to customize that code sample in the code samplessection of the operation page.
The code sample templates do not allow the use of any page controls.
Code sample entity.
{ "title": "Curl", "snippet": null, "brush": "plain", "template": "DocumentationSamplesCurl", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }
C#C#
Default templateDefault template
using System; using System.Net.Http.Headers; using System.Text; using System.Net.Http; using System.Web;
namespace CSHttpClientSample { static class Program { static void Main() { MakeRequest(); Console.WriteLine("Hit ENTER to exit..."); Console.ReadLine(); }
static async void MakeRequest() { var client = new HttpClient(); var queryString = HttpUtility.ParseQueryString(string.Empty);
{% if headers.size > 0 -%} // Request headers {% for header in headers -%} {% case header.Name -%} {% when "Accept"%} client.DefaultRequestHeaders.Accept.Add(MediaTypeWithQualityHeaderValue.Parse("{{header.value}}")); {% when "Accept-Charset" -%} client.DefaultRequestHeaders.AcceptCharset.Add(StringWithQualityHeaderValue.Parse("{{header.value}}")); {% when "Accept-Encoding" -%} client.DefaultRequestHeaders.AcceptEncoding.Add(StringWithQualityHeaderValue.Parse("
The DocumentationSamplesCsharp template allows you to customize that code sample in the code samplessection of the operation page.
client.DefaultRequestHeaders.AcceptEncoding.Add(StringWithQualityHeaderValue.Parse("{{header.value}}")); {% when "Accept-Language" -%} client.DefaultRequestHeaders.AcceptLanguage.Add(StringWithQualityHeaderValue.Parse("{{header.value}}")); {% when "Cache-Control" -%} client.DefaultRequestHeaders.CacheControl = CacheControlHeaderValue.Parse("{{header.value}}"); {% when "Connection" -%} client.DefaultRequestHeaders.Connection.Add("{{header.value}}"); {% when "Date" -%} client.DefaultRequestHeaders.Date = DateTimeOffset.Parse("{{header.value}}"); {% when "Expect" -%} client.DefaultRequestHeaders.Expect.Add(NameValueWithParametersHeaderValue.Parse("{{header.value}}")); {% when "If-Match" -%} client.DefaultRequestHeaders.IfMatch.Add(EntityTagHeaderValue.Parse("{{header.value}}")); {% when "If-Modified-Since" -%} client.DefaultRequestHeaders.IfModifiedSince = DateTimeOffset.Parse("{{header.value}}"); {% when "If-None-Match" -%} client.DefaultRequestHeaders.IfNoneMatch.Add(EntityTagHeaderValue.Parse("{{header.value}}")); {% when "If-Range" -%} client.DefaultRequestHeaders.IfRange = RangeConditionHeaderValue.Parse("{{header.value}}"); {% when "If-Unmodified-Since" -%} client.DefaultRequestHeaders.IfUnmodifiedSince = DateTimeOffset.Parse("{{header.value}}"); {% when "Max-Forwards" -%} client.DefaultRequestHeaders.MaxForwards = int.Parse("{{header.value}}"); {% when "Pragma" -%} client.DefaultRequestHeaders.Pragma.Add(NameValueHeaderValue.Parse("{{header.value}}")); {% when "Range" -%} client.DefaultRequestHeaders.Range = RangeHeaderValue.Parse("{{header.value}}"); {% when "Referer" -%} client.DefaultRequestHeaders.Referrer = new Uri("{{header.value}}"); {% when "TE" -%} client.DefaultRequestHeaders.TE.Add(TransferCodingWithQualityHeaderValue.Parse("{{header.value}}")); {% when "Transfer-Encoding" -%} client.DefaultRequestHeaders.TransferEncoding.Add(TransferCodingHeaderValue.Parse("{{header.value}}")); {% when "Upgrade" -%} client.DefaultRequestHeaders.Upgrade.Add(ProductHeaderValue.Parse("{{header.value}}")); {% when "User-Agent" -%} client.DefaultRequestHeaders.UserAgent.Add(ProductInfoHeaderValue.Parse("{{header.value}}")); {% when "Via" -%} client.DefaultRequestHeaders.Via.Add(ViaHeaderValue.Parse("{{header.value}}")); {% when "Warning" -%} client.DefaultRequestHeaders.Warning.Add(WarningHeaderValue.Parse("{{header.value}}")); {% when "Content-Type" -%} {% else -%} client.DefaultRequestHeaders.Add("{{header.Name}}", "{{header.value}}"); {% endcase -%} {% endfor -%} {% endif -%}
{% if parameters.size > 0 -%} // Request parameters {% for parameter in parameters -%} queryString["{{parameter.Name}}"] = "{{parameter.Value}}"; {% endfor -%} {% endif -%} var uri = "{{scheme}}://{{host}}{{path}}{% if path contains '?' %}&{% else %}?{% endif %}" + queryString;
{% case method -%}
{% when "POST" -%} HttpResponseMessage response;
// Request body byte[] byteData = Encoding.UTF8.GetBytes("{{ body | replace:'"','\"'}}");
using (var content = new ByteArrayContent(byteData)) { {% if body -%} content.Headers.ContentType = new MediaTypeHeaderValue("< your content type, i.e. application/json >"); {% endif -%} response = await client.PostAsync(uri, content); }
{% when "GET" -%} var response = await client.GetAsync(uri); {% when "DELETE" -%} var response = await client.DeleteAsync(uri); {% when "PUT" -%} HttpResponseMessage response;
// Request body byte[] byteData = Encoding.UTF8.GetBytes("{{ body | replace:'"','\"'}}");
using (var content = new ByteArrayContent(byteData)) { {% if body -%} content.Headers.ContentType = new MediaTypeHeaderValue("< your content type, i.e. application/json >"); {% endif -%} response = await client.PutAsync(uri, content); } {% when "HEAD" -%} var response = await client.SendAsync(new HttpRequestMessage(HttpMethod.Head, uri)); {% when "OPTIONS" -%} var response = await client.SendAsync(new HttpRequestMessage(HttpMethod.Options, uri)); {% when "TRACE" -%} var response = await client.SendAsync(new HttpRequestMessage(HttpMethod.Trace, uri));
if (response.Content != null) { var responseString = await response.Content.ReadAsStringAsync(); Console.WriteLine(responseString); } {% endcase -%} } } }
ControlsControls
Data modelData model
Sample template dataSample template data
The code sample templates do not allow the use of any page controls.
Code sample entity.
{ "title": "C#", "snippet": null, "brush": "csharp", "template": "DocumentationSamplesCsharp", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }
JavaJava
Default templateDefault template
The DocumentationSamplesJava template allows you to customize that code sample in the code samplessection of the operation page.
// // This sample uses the Apache HTTP client from HTTP Components (http://hc.apache.org/httpcomponents-client-ga/) import java.net.URI; import org.apache.http.HttpEntity; import org.apache.http.HttpResponse; import org.apache.http.client.HttpClient; import org.apache.http.client.methods.HttpGet; import org.apache.http.client.utils.URIBuilder; import org.apache.http.impl.client.HttpClients; import org.apache.http.util.EntityUtils;
public class JavaSample { public static void main(String[] args) { HttpClient httpclient = HttpClients.createDefault();
try { URIBuilder builder = new URIBuilder("{{scheme}}://{{host}}{{path}}");
{% if parameters.size > 0 -%} {% for parameter in parameters -%} builder.setParameter("{{parameter.name}}", "{{parameter.value}}"); {% endfor -%} {% endif -%}
URI uri = builder.build(); Http{{ method | downcase | capitalize }} request = new Http{{ method | downcase | capitalize }}(uri); {% for header in headers -%} request.setHeader("{{header.Name}}", "{{header.value}}"); {% endfor %}
{% if body -%} // Request body StringEntity reqEntity = new StringEntity("{{ body | replace:'"','\"' }}"); request.setEntity(reqEntity); {% endif -%}
HttpResponse response = httpclient.execute(request); HttpEntity entity = response.getEntity();
if (entity != null) { System.out.println(EntityUtils.toString(entity)); } } catch (Exception e) { System.out.println(e.getMessage()); } } }
ControlsControls
Data modelData model
Sample template dataSample template data
The code sample templates do not allow the use of any page controls.
Code sample entity.
{ "title": "Java", "snippet": null, "brush": "java", "template": "DocumentationSamplesJava", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }
JavaScriptJavaScript
Default templateDefault template
The DocumentationSamplesJs template allows you to customize that code sample in the code samples sectionof the operation page.
<!DOCTYPE html> <html> <head> <title>JSSample</title> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.9.0/jquery.min.js"></script> </head> <body>
<script type="text/javascript"> $(function() { var params = { {% if parameters.size > 0 -%} // Request parameters {% for parameter in parameters -%} "{{parameter.name}}": "{{parameter.value}}", {% endfor -%} {% endif -%} };
$.ajax({ url: "{{scheme}}://{{host}}{{path}}{% if path contains '?' %}&{% else %}?{% endif %}" + $.param(params), {% if headers.size > 0 -%} beforeSend: function(xhrObj){ // Request headers {% for header in headers -%} xhrObj.setRequestHeader("{{header.name}}","{{header.value}}"); {% endfor -%} }, {% endif -%} type: "{{method}}", {% if body -%} // Request body data: "{{ body | replace:'"','\"' }}", {% endif -%} }) .done(function(data) { alert("success"); }) .fail(function() { alert("error"); }); }); </script> </body> </html>
ControlsControls
Data modelData model
Sample template dataSample template data
The code sample templates do not allow the use of any page controls.
Code sample entity.
{ "title": "JavaScript", "snippet": null, "brush": "xml", "template": "DocumentationSamplesJs", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }
Objective CObjective C
Default templateDefault template
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[]) { NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
NSString* path = @"{{scheme}}://{{host}}{{path}}"; NSArray* array = @[ // Request parameters @"entities=true", {% if parameters.size > 0 -%} {% for parameter in parameters -%} @"{{parameter.name}}={{parameter.value}}", {% endfor -%} {% endif -%} ];
NSString* string = [array componentsJoinedByString:@"&"]; path = [path stringByAppendingFormat:@"?%@", string];
NSLog(@"%@", path);
NSMutableURLRequest* _request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:path]]; [_request setHTTPMethod:@"{{method}}"]; {% if headers.size > 0 -%} // Request headers {% for header in headers -%} [_request setValue:@"{{header.value}}" forHTTPHeaderField:@"{{header.name}}"]; {% endfor -%} {% endif -%} {% if body -%} // Request body [_request setHTTPBody:[@"{{ body | replace:'"','\"' }}" dataUsingEncoding:NSUTF8StringEncoding]]; {% endif -%}
The DocumentationSamplesObjc template allows you to customize that code sample in the code samplessection of the operation page.
{% endif -%}
NSURLResponse *response = nil; NSError *error = nil; NSData* _connectionData = [NSURLConnection sendSynchronousRequest:_request returningResponse:&response error:&error];
if (nil != error) { NSLog(@"Error: %@", error); } else { NSError* error = nil; NSMutableDictionary* json = nil; NSString* dataString = [[NSString alloc] initWithData:_connectionData encoding:NSUTF8StringEncoding]; NSLog(@"%@", dataString);
if (nil != _connectionData) { json = [NSJSONSerialization JSONObjectWithData:_connectionData options:NSJSONReadingMutableContainers error:&error]; }
if (error || !json) { NSLog(@"Could not parse loaded json with error:%@", error); }
NSLog(@"%@", json); _connectionData = nil; }
[pool drain];
return 0; }
ControlsControls
Data modelData model
Sample template dataSample template data
The code sample templates do not allow the use of any page controls.
Code sample entity.
{ "title": "ObjC", "snippet": null, "brush": "objc", "template": "DocumentationSamplesObjc", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }
PHPPHP
Default templateDefault template
The DocumentationSamplesPhp template allows you to customize that code sample in the code samplessection of the operation page.
<?php // This sample uses the Apache HTTP client from HTTP Components (http://hc.apache.org/httpcomponents-client-ga/) require_once 'HTTP/Request2.php';
$request = new Http_Request2('{{scheme}}://{{host}}{{path}}'); $url = $request->getUrl();
{% if headers.size > 0 -%} $headers = array( // Request headers {% for header in headers -%} '{{header.name}}' => '{{header.value}}', {% endfor -%} );
$request->setHeader($headers); {% endif -%}
{% if parameters.size > 0 -%} $parameters = array( // Request parameters {% for parameter in parameters -%} '{{parameter.name}}' => '{{parameter.value}}', {% endfor -%} );
$url->setQueryVariables($parameters); {% endif -%}
$request->setMethod(HTTP_Request2::METHOD_{{method}});
{% if body -%} // Request body $request->setBody("{{ body | replace:'"','\"' }}"); {% endif -%}
try { $response = $request->send(); echo $response->getBody(); } catch (HttpException $ex) { echo $ex; }
?>
ControlsControls
Data modelData model
Sample template dataSample template data
The code sample templates do not allow the use of any page controls.
Code sample entity.
{ "title": "PHP", "snippet": null, "brush": "php", "template": "DocumentationSamplesPhp", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }
PythonPython
Default templateDefault template
########### Python 2.7 ############# import httplib, urllib, base64
headers = { {% if headers.size > 0 -%} # Request headers {% for header in headers -%} '{{header.name}}': '{{header.value}}', {% endfor -%} {% endif -%} }
params = urllib.urlencode({ {% if parameters.size > 0 -%} # Request parameters {% for parameter in parameters -%} '{{parameter.name}}': '{{parameter.value}}', {% endfor -%} {% endif -%} })
try: {% case scheme -%} {% when "http" -%} conn = httplib.HTTPConnection('{{host}}') {% when "https" -%} conn = httplib.HTTPSConnection('{{host}}') {% endcase -%} conn.request("{{method}}", "{{path}}{% if path contains '?' %}&{% else %}?{% endif %}%s" % params{% if body %}, "{{ body | replace:'"','\"' }}"{% endif %}, headers) response = conn.getresponse() data = response.read() print(data) conn.close()
The DocumentationSamplesPython template allows you to customize that code sample in the code samplessection of the operation page.
conn.close() except Exception as e: print("[Errno {0}] {1}".format(e.errno, e.strerror))
####################################
########### Python 3.2 ############# import http.client, urllib.request, urllib.parse, urllib.error, base64
headers = { {% if headers.size > 0 -%} # Request headers {% for header in headers -%} '{{header.name}}': '{{header.value}}', {% endfor -%} {% endif -%} }
params = urllib.parse.urlencode({ {% if parameters.size > 0 -%} # Request parameters {% for parameter in parameters -%} '{{parameter.name}}': '{{parameter.value}}', {% endfor -%} {% endif -%} })
try: {% case scheme -%} {% when "http" -%} conn = http.client.HTTPConnection('{{host}}') {% when "https" -%} conn = http.client.HTTPSConnection('{{host}}') {% endcase -%} conn.request("{{method}}", "{{path}}{% if path contains '?' %}&{% else %}?{% endif %}%s" % params{% if body %}, "{{ body | replace:'"','\"' }}"{% endif %}, headers) response = conn.getresponse() data = response.read() print(data) conn.close() except Exception as e: print("[Errno {0}] {1}".format(e.errno, e.strerror))
####################################
ControlsControls
Data modelData model
Sample template dataSample template data
The code sample templates do not allow the use of any page controls.
Code sample entity.
{ "title": "Python", "snippet": null, "brush": "python", "template": "DocumentationSamplesPython", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }
RubyRuby
Default templateDefault template
require 'net/http'
uri = URI('{{scheme}}://{{host}}{{path}}') uri.query = URI.encode_www_form({ {% if parameters.size > 0 -%} # Request parameters {% for parameter in parameters -%} '{{parameter.name}}' => '{{parameter.value}}'{% unless forloop.last %},{% endunless %} {% endfor -%} {% endif -%} })
request = Net::HTTP::{{ method | downcase | capitalize }}.new(uri.request_uri) {% for header in headers -%} # Request headers request['{{header.name}}'] = '{{header.value}}' {% endfor -%} {% if body -%} # Request body request.body = "{{ body | replace:'"','\"' }}" {% endif -%}
response = Net::HTTP.start(uri.host, uri.port, :use_ssl => uri.scheme == 'https') do |http| http.request(request) end
puts response.body
ControlsControls
Data modelData model
The DocumentationSamplesRuby template allows you to customize that code sample in the code samplessection of the operation page.
The code sample templates do not allow the use of any page controls.
Sample template dataSample template data
{ "title": "Ruby", "snippet": null, "brush": "ruby", "template": "DocumentationSamplesRuby", "body": "{body}", "method": "GET", "scheme": "https", "path": "/calc/add?a={a}&b={b}", "query": "", "host": "sdcontoso5.azure-api.net", "headers": [ { "name": "Ocp-Apim-Subscription-Key", "description": "Subscription key which provides access to this API. Found in your <a href='/developer'>Profile</a>.", "value": "{subscription key}", "typeName": "string", "options": null, "required": true, "readonly": false } ], "parameters": [] }
Next steps
Code sample entity.
For more information about working with templates, see How to customize the API Management developer portalusing templates.
Product templates in Azure API Management8/30/2017 • 4 min to read • Edit Online
NOTENOTE
Product list
Default templateDefault template
Azure API Management provides you the ability to customize the content of developer portal pages using a set oftemplates that configure their content. Using DotLiquid syntax and the editor of your choice, such as DotLiquid forDesigners, and a provided set of localized String resources, Glyph resources, and Page controls, you have greatflexibility to configure the content of the pages as you see fit using these templates.
The templates in this section allow you to customize the content of the product pages in the developer portal.
Product list
Product
Sample default templates are included in the following documentation, but are subject to change due to continuousimprovements. You can view the live default templates in the developer portal by navigating to the desired individualtemplates. For more information about working with templates, see How to customize the API Management developerportal using templates.
The Product list template allows you to customize the body of the product list page in the developer portal.
<search-control></search-control> <div class="row"> <div class="col-md-9"> <h2>{% localized "ProductsStrings|PageTitleProducts" %}</h2> </div> </div> <div class="row"> <div class="col-md-12"> {% if products.size > 0 %} <ul class="list-unstyled"> {% for product in products %} <li> <h3><a href="/products/{{product.id}}">{{product.title}}</a></h3> {{product.description}} </li> {% endfor %} </ul> <paging-control></paging-control> {% else %} {% localized "CommonResources|NoItemsToDisplay" %} {% endif %} </div> </div>
ControlsControls
Data modelData model
PROPERTY TYPE DESCRIPTION
Paging Paging entity. The paging information for the productscollection.
Filtering Filtering entity. The filtering information for theproducts list page.
Products Collection of Product entities. The products visible to the current user.
Sample template dataSample template data
The Product list template may use the following page controls.
paging-control
search-control
{ "Paging": { "Page": 1, "PageSize": 10, "TotalItemCount": 2, "ShowAll": false, "PageCount": 1 }, "Filtering": { "Pattern": null, "Placeholder": "Search products" }, "Products": [ { "Id": "56f9445ffaf7560049060001", "Title": "Starter", "Description": "Subscribers will be able to run 5 calls/minute up to a maximum of 100 calls/week.", "Terms": "", "ProductState": 1, "AllowMultipleSubscriptions": false, "MultipleSubscriptionsCount": 1 }, { "Id": "56f9445ffaf7560049060002", "Title": "Unlimited", "Description": "Subscribers have completely unlimited access to the API. Administrator approval is required.", "Terms": null, "ProductState": 1, "AllowMultipleSubscriptions": false, "MultipleSubscriptionsCount": 1 } ] }
Product
Default templateDefault template
<h2>{{Product.Title}}</h2> <p>{{Product.Description}}</p>
{% assign replaceString0 = '{0}' %}
The Product template allows you to customize the body of the product page in the developer portal.
{% if Limits and Limits.size > 0 %} <h3>{% localized "ProductDetailsStrings|WebProductsUsageLimitsHeader"%}</h3> <ul> {% for limit in Limits %} <li>{{limit.DisplayName}}</li> {% endfor %} </ul> {% endif %}
{% if apis.size > 0 %} <p> <b> {% if apis.size == 1 %} {% capture apisCountText %}{% localized "ProductDetailsStrings|TextblockSingleApisCount" %}{% endcapture %} {% else %} {% capture apisCountText %}{% localized "ProductDetailsStrings|TextblockMultipleApisCount" %}{% endcapture %} {% endif %}
{% capture apisCount %}{{apis.size}}{% endcapture %} {{ apisCountText | replace : replaceString0, apisCount }} </b> </p>
<ul> {% for api in Apis %} <li> <a href="/docs/services/{{api.Id}}">{{api.Name}}</a> </li> {% endfor %} </ul> {% endif %}
{% if subscriptions.size > 0 %} <p> <b> {% if subscriptions.size == 1 %} {% capture subscriptionsCountText %}{% localized "ProductDetailsStrings|TextblockSingleSubscriptionsCount" %}{% endcapture %} {% else %} {% capture subscriptionsCountText %}{% localized "ProductDetailsStrings|TextblockMultipleSubscriptionsCount" %}{% endcapture %} {% endif %}
{% capture subscriptionsCount %}{{subscriptions.size}}{% endcapture %} {{ subscriptionsCountText | replace : replaceString0, subscriptionsCount }} </b> </p>
<ul> {% for subscription in subscriptions %} <li> <a href="/developer#{{subscription.Id}}">{{subscription.DisplayName}}</a> </li> {% endfor %} </ul> {% endif %} {% if CannotAddBecauseSubscriptionNumberLimitReached %} <b>{% localized "ProductDetailsStrings|TextblockSubscriptionLimitReached" %}</b> {% elsif CannotAddBecauseMultipleSubscriptionsNotAllowed == false %} <subscribe-button></subscribe-button> {% endif %}
ControlsControls
Data modelData model
PROPERTY TYPE DESCRIPTION
Product Product The specified product.
IsDeveloperSubscribed boolean Whether the current user is subscribedto this product.
SubscriptionState number The state of the subscription. Possiblestates are:
- 0 - suspended – the subscription isblocked, and the subscriber cannot callany APIs of the product.- 1 - active – the subscription isactive.- 2 - expired – the subscriptionreached its expiration date and wasdeactivated.- 3 - submitted – the subscriptionrequest has been made by thedeveloper, but has not yet beenapproved or rejected.- 4 - rejected – the subscriptionrequest has been denied by anadministrator.- 5 - cancelled – the subscriptionhas been cancelled by the developer oradministrator.
Limits array This property is deprecated and shouldnot be used.
DelegatedSubscriptionEnabled boolean Whether delegation is enabled for thissubscription.
DelegatedSubscriptionUrl string If delegation is enabled, the delegatedsubscription URL.
IsAgreed boolean If the product has terms, whether thecurrent user has agreed to the terms.
Subscriptions Collection of Subscription summaryentities.
The subscriptions to the product.
Apis Collection of API entities. The APIs in this product.
CannotAddBecauseSubscriptionNumberLimitReached
boolean Whether the current user is eligible tosubscribe to this product with regard tothe subscription limit.
The Product list template may use the following page controls.
subscribe-button
CannotAddBecauseMultipleSubscriptionsNotAllowed
boolean Whether the current user is eligible tosubscribe to this product with regard tomultiple subscriptions being allowed ornot.
PROPERTY TYPE DESCRIPTION
Sample template dataSample template data
{ "Product": { "Id": "56f9445ffaf7560049060001", "Title": "Starter", "Description": "Subscribers will be able to run 5 calls/minute up to a maximum of 100 calls/week.", "Terms": "", "ProductState": 1, "AllowMultipleSubscriptions": false, "MultipleSubscriptionsCount": 1 }, "IsDeveloperSubscribed": true, "SubscriptionState": 1, "Limits": [], "DelegatedSubscriptionEnabled": false, "DelegatedSubscriptionUrl": null, "IsAgreed": false, "Subscriptions": [ { "Id": "56f9445ffaf7560049070001", "DisplayName": "Starter (default)" } ], "Apis": [ { "id": "56f9445ffaf7560049040001", "name": "Echo API", "description": null, "serviceUrl": "http://echoapi.cloudapp.net/api", "path": "echo", "protocols": [ 2 ], "authenticationSettings": null, "subscriptionKeyParameterNames": null } ], "CannotAddBecauseSubscriptionNumberLimitReached": false, "CannotAddBecauseMultipleSubscriptionsNotAllowed": true }
Next stepsFor more information about working with templates, see How to customize the API Management developer portalusing templates.
Application templates in Azure API Management8/30/2017 • 2 min to read • Edit Online
NOTENOTE
Application list
Default templateDefault template
Azure API Management provides you the ability to customize the content of developer portal pages using a set oftemplates that configure their content. Using DotLiquid syntax and the editor of your choice, such as DotLiquid forDesigners, and a provided set of localized String resources, Glyph resources, and Page controls, you have greatflexibility to configure the content of the pages as you see fit using these templates.
The templates in this section allow you to customize the content of the Application pages in the developer portal.
Application list
Application
Sample default templates are included in the following documentation, but are subject to change due to continuousimprovements. You can view the live default templates in the developer portal by navigating to the desired individualtemplates. For more information about working with templates, see How to customize the API Management developerportal using templates.
The Application list template allows you to customize the body of the application list page in the developerportal.
<div class="row"> <div class="col-md-9"> <h2>{% localized "AppStrings|WebApplicationsHeader" %}</h2> </div> </div> <div class="row"> <div class="col-md-12"> {% if applications.size > 0 %} <ul class="list-unstyled"> {% for app in applications %} <li> {% if app.application.icon.url != "" %} <aside> <a href="/applications/details/{{app.application.id}}"><img src="{{app.application.icon.url}}" alt="App Icon" /></a> </aside> {% endif %} <h3><a href="/applications/details/{{app.application.id}}">{{app.application.title}}</a></h3> {{app.application.description}} </li> {% endfor %} </ul> <paging-control></paging-control> {% else %} {% localized "CommonResources|NoItemsToDisplay" %} {% endif %} </div> </div>
ControlsControls
Data modelData model
PROPERTY TYPE DESCRIPTION
Paging Paging entity. The paging information for theapplications collection.
Applications Collection of Application entities. The applications visible to the currentuser.
CategoryName string The category of application.
Sample template dataSample template data
The Product list template may use the following page controls.
paging-control
{ "Paging": { "Page": 1, "PageSize": 10, "TotalItemCount": 1, "ShowAll": false, "PageCount": 1 }, "Applications": [ { "Application": { "Id": "5702b96fb16653124c8f9ba8", "Title": "Contoso Calculator", "Description": "A simple online calculator.", "Url": null, "Version": null, "Requirements": "Free application with no requirements.", "State": 2, "RegistrationDate": "2016-04-04T18:59:00", "CategoryId": 5, "DeveloperId": "5702b5b0b16653124c8f9ba4", "Attachments": [ { "UniqueId": "a58af001-e6c3-45fd-8bc9-c60a1875c3f6", "Url": "https://apimgmtst65gdjvjrgdbfhr4.blob.core.windows.net/content/applications/a58af001-e6c3-45fd-8bc9-c60a1875c3f6.png", "Type": "Icon", "ContentType": "image/png" }, { "UniqueId": "2b4fa5dd-00ff-4a8f-b1b7-51e715849ede", "Url": "https://apimgmtst65gdjvjrgdbfhr4.blob.core.windows.net/content/applications/2b4fa5dd-00ff-4a8f-b1b7-51e715849ede.png", "Type": "Screenshot", "ContentType": "image/png" } ], "Icon": { "UniqueId": "a58af001-e6c3-45fd-8bc9-c60a1875c3f6", "Url": "https://apimgmtst65gdjvjrgdbfhr4.blob.core.windows.net/content/applications/a58af001-e6c3-45fd-8bc9-c60a1875c3f6.png", "Type": "Icon", "ContentType": "image/png" } }, "CategoryName": "Finance" } ] }
ApplicationThe Application template allows you to customize the body of the application page in the developer portal.
Default templateDefault template
<h2>{{title}}</h2> {% if icon.url != "" %} <aside class="applications_aside"> <div class="image-placeholder"> <img src="{{icon.url}}" alt="Application Icon" /> </div> </aside> {% endif %}
<article> {% if url != "" %} <a target="_blank" href="{{url}}">{{url}}</a> {% endif %}
<p>{{description}}</p>
{% if requirements != null %} <h3>{% localized "AppDetailsStrings|WebApplicationsRequirementsHeader" %}</h3> <p>{{requirements}}</p> {% endif %}
{% if attachments.size > 0 %} <h3>{% localized "AppDetailsStrings|WebApplicationsScreenshotsHeader" %}</h3> {% for screenshot in attachments %} {% if screenshot.type != "Icon" %} <a href="{{screenshot.url}}" data-lightbox="example-set"> <img src="/Developer/Applications/Thumbnail?url={{screenshot.url}}" alt='{% localized "AppDetailsStrings|WebApplicationsScreenshotAlt" %}' /> </a> {% endif %} {% endfor %} {% endif %} </article>
ControlsControls
Data modelData model
Sample template dataSample template data
{ "Id": "5702b96fb16653124c8f9ba8", "Title": "Contoso Calculator", "Description": "A simple online calculator.", "Url": null, "Version": null, "Requirements": "Free application with no requirements.", "State": 2, "RegistrationDate": "2016-04-04T18:59:00", "CategoryId": 5, "DeveloperId": "5702b5b0b16653124c8f9ba4", "Attachments": [ { "UniqueId": "a58af001-e6c3-45fd-8bc9-c60a1875c3f6", "Url": "https://apimgmtst3aybshdqqcqrle4.blob.core.windows.net/content/applications/a58af001-e6c3-45fd-8bc9-c60a1875c3f6.png", "Type": "Icon", "ContentType": "image/png" }, { "UniqueId": "2b4fa5dd-00ff-4a8f-b1b7-51e715849ede", "Url": "https://apimgmtst3aybshdqqcqrle4.blob.core.windows.net/content/applications/2b4fa5dd-00ff-4a8f-b1b7-51e715849ede.png", "Type": "Screenshot", "ContentType": "image/png" } ], "Icon": { "UniqueId": "a58af001-e6c3-45fd-8bc9-c60a1875c3f6", "Url": "https://apimgmtst3aybshdqqcqrle4.blob.core.windows.net/content/applications/a58af001-e6c3-45fd-8bc9-c60a1875c3f6.png", "Type": "Icon", "ContentType": "image/png" } }
Next steps
The Application template does not allow the use of any page controls.
Application entity.
For more information about working with templates, see How to customize the API Management developer portalusing templates.
Issue templates in Azure API Management8/30/2017 • 2 min to read • Edit Online
NOTENOTE
Issue list
Default templateDefault template
Azure API Management provides you the ability to customize the content of developer portal pages using a set oftemplates that configure their content. Using DotLiquid syntax and the editor of your choice, such as DotLiquid forDesigners, and a provided set of localized String resources, Glyph resources, and Page controls, you have greatflexibility to configure the content of the pages as you see fit using these templates.
The templates in this section allow you to customize the content of the Issue pages in the developer portal.
Issue list
Sample default templates are included in the following documentation, but are subject to change due to continuousimprovements. You can view the live default templates in the developer portal by navigating to the desired individualtemplates. For more information about working with templates, see How to customize the API Management developerportal using templates.
The Issue list template allows you to customize the body of the issue list page in the developer portal.
<div class="row"> <div class="col-md-9"> <h2>{% localized "IssuesStrings|WebIssuesIndexTitle" %}</h2> </div> </div> <div class="row"> <div class="col-md-12"> {% if issues.size > 0 %} <ul class="list-unstyled"> {% capture reportedBy %}{% localized "IssuesStrings|WebIssuesStatusReportedBy" %}{% endcapture %} {% assign replaceString0 = '{0}' %} {% assign replaceString1 = '{1}' %} {% for issue in issues %} <li> <h3> <a href="/issues/{{issue.id}}">{{issue.title}}</a> </h3> <p>{{issue.description}}</p> <em> {% capture state %}{{issue.issueState}}{% endcapture %} {% capture devName %}{{issue.subscriptionDeveloperName}}{% endcapture %} {% capture str1 %}{{ reportedBy | replace : replaceString0, state }}{% endcapture %} {{ str1 | replace : replaceString1, devName }} <span class="UtcDateElement">{{ issue.reportedOn | date: "r" }}</span> </em> </li> {% endfor %} </ul> <paging-control></paging-control> {% else %} {% localized "CommonResources|NoItemsToDisplay" %} {% endif %} {% if canReportIssue %} <a class="btn btn-primary" id="createIssue" href="/Issues/Create">{% localized "IssuesStrings|WebIssuesReportIssueButton" %}</a> {% elsif isAuthenticated %} <hr /> <p>{% localized "IssuesStrings|WebIssuesNoActiveSubscriptions" %}</p> {% else %} <hr /> <p> {% capture signIntext %}{% localized "IssuesStrings|WebIssuesNotSignin" %}{% endcapture %} {% capture link %}<a href="/signin">{% localized "IssuesStrings|WebIssuesSignIn" %}</a>{% endcapture %} {{ signIntext | replace : replaceString0, link }} </p> {% endif %} </div> </div>
ControlsControls
Data modelData model
PROPERTY TYPE DESCRIPTION
Issues Collection of Issue entities. The issues visible to the current user.
Paging Paging entity. The paging information for theapplications collection.
The Issue list template may use the following page controls.
paging-control
IsAuthenticated boolean Whether the current user is signed-in tothe developer portal.
CanReportIssues boolean Whether the current user haspermissions to file an issue.
Search string This property is deprecated and shouldnot be used.
PROPERTY TYPE DESCRIPTION
Sample template dataSample template data
{ "Issues": [ { "Id": "5702b68bb16653124c8f9ba7", "ApiId": "570275f1b16653124c8f9ba3", "Title": "I couldn't figure out how to connect my application to the API", "Description": "I'm having trouble connecting my application to the backend API.", "SubscriptionDeveloperName": "Clayton", "IssueState": "Proposed", "ReportedOn": "2016-04-04T18:46:35.64", "Comments": null, "Attachments": null, "Services": null } ], "Paging": { "Page": 1, "PageSize": 10, "TotalItemCount": 1, "ShowAll": false, "PageCount": 1 }, "IsAuthenticated": true, "CanReportIssue": true, "Search": null }
Next stepsFor more information about working with templates, see How to customize the API Management developer portalusing templates.
User profile templates in Azure API Management8/30/2017 • 9 min to read • Edit Online
NOTENOTE
Profile
Default templateDefault template
Azure API Management provides you the ability to customize the content of developer portal pages using a set oftemplates that configure their content. Using DotLiquid syntax and the editor of your choice, such as DotLiquid forDesigners, and a provided set of localized String resources, Glyph resources, and Page controls, you have greatflexibility to configure the content of the pages as you see fit using these templates.
The templates in this section allow you to customize the content of the User profile pages in the developer portal.
Profile
Subscriptions
Applications
Update account info
Sample default templates are included in the following documentation, but are subject to change due to continuousimprovements. You can view the live default templates in the developer portal by navigating to the desired individualtemplates. For more information about working with templates, see How to customize the API Management developerportal using templates.
The profile template allows you to customize the user profile section of the user profile page in the developerportal.
<div class="pull-right"> {% if canChangePassword == true %} <a class="btn btn-default" id="ChangePassword" role="button" href="{{changePasswordUrl}}">{% localized "UserProfile|ButtonLabelChangePassword" %}</a> {% endif %} <a id="changeAccountInfo" href="{{changeNameOrEmailUrl}}" class="btn btn-default"> <span class="glyphicon glyphicon-user"></span> <span>{% localized "UserProfile|ButtonLabelChangeAccountInfo" %}</span> </a> </div> <h2>{% localized "SubscriptionStrings|PageTitleDeveloperProfile" %}</h2> <div class="container-fluid"> <div class="row"> <div class="col-sm-3"> <label for="Email">{% localized "UserProfile|TextboxLabelEmail" %}</label> </div> <div class="col-sm-9" id="Email">{{email}}</div> </div>
{% if isSystemUser != true %} <div class="row"> <div class="col-sm-3"> <label for="FirstName">{% localized "UserProfile|TextboxLabelEmailFirstName" %}</label> </div> <div class="col-sm-9" id="FirstName">{{FirstName}}</div> </div> <div class="row"> <div class="col-sm-3"> <label for="LastName">{% localized "UserProfile|TextboxLabelEmailLastName" %}</label> </div> <div class="col-sm-9" id="LastName">{{LastName}}</div> </div> {% else %} <div class="row"> <div class="col-sm-3"> <label for="CompanyName">{% localized "UserProfile|TextboxLabelOrganizationName" %}</label> </div> <div class="col-sm-9" id="CompanyName">{{CompanyName}}</div> </div> <div class="row"> <div class="col-sm-3"> <label for="AddresserEmail">{% localized "UserProfile|TextboxLabelNotificationsSenderEmail" %}</label> </div> <div class="col-sm-9" id="AddresserEmail">{{AddresserEmail}}</div> </div> {% endif %}
</div>
ControlsControls
Data modelData model
NOTENOTE
PROPERTY TYPE DESCRIPTION
firstName string First name of the current user.
This template may not use any page controls.
The Profile, Applications, and Subscriptions templates share the same data model and receive the same template data.
lastName string Last name of the current user.
companyName string The company name of the current user.
addresserEmail string Email address of the current user.
developersUsageStatisticsLinkk string Relative URL to view analytics for thecurrent user.
subscriptions Collection of Subscription entities. The subscriptions for the current user.
applications Collection of Application entities. The applications of the current user.
changePasswordUrl string The relative URL to change the currentuser's password.
changeNameOrEmailUrl string The relative URL to change the nameand email for the current user.
canChangePassword boolean Whether the current user can changetheir password.
isSystemUser boolean Whether the current user is a memberof one of the built-in groups.
PROPERTY TYPE DESCRIPTION
Sample template dataSample template data
{ "firstName": "Administrator", "lastName": "", "companyName": "Contoso", "addresserEmail": "[email protected]", "email": "[email protected]", "developersUsageStatisticsLink": "/Developer/Analytics", "subscriptions": [ { "Id": "57026e30de15d80041070001", "ProductId": "57026e30de15d80041060001", "ProductTitle": "Starter", "ProductDescription": "Subscribers will be able to run 5 calls/minute up to a maximum of 100 calls/week.", "ProductDetailsUrl": "/Products/57026e30de15d80041060001", "State": "Active", "DisplayName": "Starter (default)", "CreatedDate": "2016-04-04T13:37:52.847", "CanBeCancelled": true, "IsAwaitingApproval": false, "StartDate": null, "ExpirationDate": null, "NotificationDate": null, "PrimaryKey": "b6b2870953d04420a4e02c58f2c08e74", "SecondaryKey": "cfe28d5a1cd04d8abc93f48352076ea5", "UserId": 1, "CanBeRenewed": false, "HasExpired": false, "IsRejected": false, "CancelUrl": "/Subscriptions/57026e30de15d80041070001/Cancel", "RenewUrl": "/Subscriptions/57026e30de15d80041070001/Renew" }, { "Id": "57026e30de15d80041070002", "ProductId": "57026e30de15d80041060002", "ProductTitle": "Unlimited", "ProductDescription": "Subscribers have completely unlimited access to the API. Administrator approval is required.", "ProductDetailsUrl": "/Products/57026e30de15d80041060002", "State": "Active", "DisplayName": "Unlimited (default)", "CreatedDate": "2016-04-04T13:37:52.923", "CanBeCancelled": true, "IsAwaitingApproval": false, "StartDate": null, "ExpirationDate": null, "NotificationDate": null, "PrimaryKey": "8fe7843c36de4cceb4728e6cae297336", "SecondaryKey": "96c850d217e74acf9b514ff8a5b38551", "UserId": 1, "CanBeRenewed": false, "HasExpired": false, "IsRejected": false, "CancelUrl": "/Subscriptions/57026e30de15d80041070002/Cancel", "RenewUrl": "/Subscriptions/57026e30de15d80041070002/Renew" } ], "applications": [], "changePasswordUrl": "/account/password/change", "changeNameOrEmailUrl": "/account/update", "canChangePassword": false, "isSystemUser": true }
Subscriptions
Default templateDefault template
<div class="ap-account-subscriptions"> <a href="{{developersUsageStatisticsLink}}" id="UsageStatistics" class="btn btn-default pull-right"> <span class="glyphicon glyphicon-stats"></span> <span>{% localized "SubscriptionListStrings|WebDevelopersUsageStatisticsLink" %}</span> </a>
<h2>{% localized "SubscriptionListStrings|WebDevelopersYourSubscriptions" %}</h2>
<table class="table"> <thead> <tr> <th>Subscription details</th> <th>Product</th> <th>{% localized "SubscriptionListStrings|WebDevelopersSubscriptionTableStateHeader" %}</th> <th>Action</th> </tr> </thead> <tbody> {% if subscriptions.size == 0 %} <tr> <td class="text-center" colspan="4"> {% localized "CommonResources|NoItemsToDisplay" %} </td> </tr> {% else %} {% for subscription in subscriptions %} <tr id="{{subscription.id}}" {% if subscription.hasExpired %} class="expired" {% endif %}> <td> <div class="row"> <label class="col-lg-3">{% localized "SubscriptionListStrings|SubscriptionPropertyLabelName" %}</label> <div class="col-lg-6"> {{ subscription.displayName }} </div> <div class="col-lg-2"> <a class="btn-link" href="/Subscriptions/{{subscription.id}}/Rename">Rename</a> </div>
The Subscriptions template allows you to customize the subscriptions section of the user profile page in thedeveloper portal.
<div class="clearfix"></div> </div> {% if subscription.isAwaitingApproval %} <div class="row"> <label class="col-lg-3">{% localized "SubscriptionListStrings|SubscriptionPropertyLabelRequestedDate" %}</label> <div class="col-lg-6"> {{ subscription.createdDate | date:"MM/dd/yyyy" }} </div> </div> {% else %} {% if subscription.isRejected == false %} {% if subscription.startDate %} <div class="row"> <label class="col-lg-3">{% localized "SubscriptionListStrings|SubscriptionPropertyLabelStartedDate" %}</label> <div class="col-lg-6"> {{ subscription.startDate | date:"MM/dd/yyyy" }} </div> </div> {% endif %}
<!-- ko with: Developers.Account.Root.account.key('{{subscription.primaryKey}}', '{{subscription.id}}', true) --> <div class="row"> <label class="col-lg-3">{% localized "SubscriptionListStrings|WebDevelopersPrimaryKey" %}</label> <div class="col-lg-6"> <code data-bind="text: $data.displayKey()" id="primary_{{subscription.id}}"></code> </div> <div class="col-lg-2"> <!-- ko if: !requestInProgress() --> <div class="nowrap"> <a href="#" class="btn-link" id="togglePrimary_{{subscription.id}}" data-bind="click: toggleKeyDisplay, text: toggleKeyLabel"></a> | <a href="#" class="btn-link" id="regeneratePrimary_{{subscription.id}}" data-bind="click: regenerateKey, text: regenerateKeyLabel"></a> </div> <!-- /ko --> <!-- ko if: requestInProgress() --> <div class="progress progress-striped active"> <div class="progress-bar" role="progressbar" aria-valuenow="100" aria-valuemin="0" aria-valuemax="100" style="width: 100%"> <span class="sr-only"></span> </div> </div> <!-- /ko --> </div> <div class="clearfix"></div> </div> <!-- /ko --> <!-- ko with: Developers.Account.Root.account.key('{{subscription.secondaryKey}}', '{{subscription.id}}', false) --> <div class="row"> <label class="col-lg-3">{% localized "SubscriptionListStrings|WebDevelopersSecondaryKey" %}</label> <div class="col-lg-6"> <code data-bind="text: $data.displayKey()" id="secondary_{{subscription.id}}"></code> </div> <div class="col-lg-2"> <div class="nowrap"> <a href="#" class="btn-link" id="toggleSecondary_{{subscription.id}}" data-bind="click: toggleKeyDisplay, text: toggleKeyLabel">{% localized "SubscriptionListStrings|ButtonLabelShowKey" %}</a> | <a href="#" class="btn-link" id="regenerateSecondary_{{subscription.id}}" data-bind="click: regenerateKey, text: regenerateKeyLabel">{% localized "SubscriptionListStrings|WebDevelopersRegenerateLink" %}</a> </div> </div>
</div> <div class="clearfix"> </div> </div> <!-- /ko --> {% endif %} {% endif %} </td> <td> <a href="{{subscription.productDetailsUrl}}">{{subscription.productTitle}}</a> </td> <td> <strong> {{subscription.state}} </strong> </td> <td> <div class="nowrap"> {% if subscription.canBeCancelled %} <subscription-cancel params="{ subscriptionId: '{{subscription.id}}', cancelUrl: '{{subscription.cancelUrl}}' }"></subscription-cancel> {% endif %} </div> </td> </tr> {% endfor %} {% endif %} </tbody> </table> </div>
ControlsControls
Data modelData model
NOTENOTE
PROPERTY TYPE DESCRIPTION
firstName string First name of the current user.
lastName string Last name of the current user.
companyName string The company name of the current user.
addresserEmail string Email address of the current user.
developersUsageStatisticsLinkk string Relative URL to view analytics for thecurrent user.
subscriptions Collection of Subscription entities. The subscriptions for the current user.
applications Collection of Application entities. The applications of the current user.
This template may use the following page controls.
subscription-cancel
The Profile, Applications, and Subscriptions templates share the same data model and receive the same template data.
changePasswordUrl string The relative URL to change the currentuser's password.
changeNameOrEmailUrl string The relative URL to change the nameand email for the current user.
canChangePassword boolean Whether the current user can changetheir password.
isSystemUser boolean Whether the current user is a memberof one of the built-in groups.
PROPERTY TYPE DESCRIPTION
Sample template dataSample template data
{ "firstName": "Administrator", "lastName": "", "companyName": "Contoso", "addresserEmail": "[email protected]", "email": "[email protected]", "developersUsageStatisticsLink": "/Developer/Analytics", "subscriptions": [ { "Id": "57026e30de15d80041070001", "ProductId": "57026e30de15d80041060001", "ProductTitle": "Starter", "ProductDescription": "Subscribers will be able to run 5 calls/minute up to a maximum of 100 calls/week.", "ProductDetailsUrl": "/Products/57026e30de15d80041060001", "State": "Active", "DisplayName": "Starter (default)", "CreatedDate": "2016-04-04T13:37:52.847", "CanBeCancelled": true, "IsAwaitingApproval": false, "StartDate": null, "ExpirationDate": null, "NotificationDate": null, "PrimaryKey": "b6b2870953d04420a4e02c58f2c08e74", "SecondaryKey": "cfe28d5a1cd04d8abc93f48352076ea5", "UserId": 1, "CanBeRenewed": false, "HasExpired": false, "IsRejected": false, "CancelUrl": "/Subscriptions/57026e30de15d80041070001/Cancel", "RenewUrl": "/Subscriptions/57026e30de15d80041070001/Renew" }, { "Id": "57026e30de15d80041070002", "ProductId": "57026e30de15d80041060002", "ProductTitle": "Unlimited", "ProductDescription": "Subscribers have completely unlimited access to the API. Administrator approval is required.", "ProductDetailsUrl": "/Products/57026e30de15d80041060002", "State": "Active", "DisplayName": "Unlimited (default)", "CreatedDate": "2016-04-04T13:37:52.923", "CanBeCancelled": true, "IsAwaitingApproval": false, "StartDate": null, "ExpirationDate": null, "NotificationDate": null, "PrimaryKey": "8fe7843c36de4cceb4728e6cae297336", "SecondaryKey": "96c850d217e74acf9b514ff8a5b38551", "UserId": 1, "CanBeRenewed": false, "HasExpired": false, "IsRejected": false, "CancelUrl": "/Subscriptions/57026e30de15d80041070002/Cancel", "RenewUrl": "/Subscriptions/57026e30de15d80041070002/Renew" } ], "applications": [], "changePasswordUrl": "/account/password/change", "changeNameOrEmailUrl": "/account/update", "canChangePassword": false, "isSystemUser": true }
Applications
Default templateDefault template
The Applications template allows you to customize the subscriptions section of the user profile page in thedeveloper portal.
<div class="ap-account-applications"> <a id="RegisterApplication" href="/Developer/Applications/Register" class="btn btn-success pull-right"> <span class="glyphicon glyphicon-plus"></span> <span>{% localized "ApplicationListStrings|WebDevelopersRegisterAppLink" %}</span> </a> <h2>{% localized "ApplicationListStrings|WebDevelopersYourApplicationsHeader" %}</h2>
<table class="table"> <thead> <tr> <th class="col-md-8">{% localized "ApplicationListStrings|WebDevelopersAppTableNameHeader" %}</th> <th class="col-md-2">{% localized "ApplicationListStrings|WebDevelopersAppTableCategoryHeader" %}</th> <th class="col-md-2" colspan="2">{% localized "ApplicationListStrings|WebDevelopersAppTableStateHeader" %}</th> </tr> </thead> <tbody>
{% if applications.size == 0 %}
<tr> <td class="col-md-12 text-center" colspan="4"> {% localized "CommonResources|NoItemsToDisplay" %} </td> </tr>
{% else %}
{% for app in applications %} <tr> <td class="col-md-8"> {{app.title}} </td> <td class="col-md-2"> {{app.categoryName}} </td> <td class="col-md-2"> <strong> {% case app.state %} {% when ApplicationStateModel.Registered %} {% localized "ApplicationListStrings|WebDevelopersAppNotSubminted" %}
{% when ApplicationStateModel.Unpublished %} {% localized "ApplicationListStrings|WebDevelopersAppNotPublished" %}
{% else %} {{ app.state }} {% endcase %} </strong> </td> <td class="col-md-1"> <div class="nowrap"> {% if app.state != ApplicationStateModel.Submitted and app.state != ApplicationStateModel.Published %} <app-actions params="{ appId: '{{app.id}}' }"></app-actions> {% endif %} </div> </td> </tr> {% endfor %}
{% endif %} </tbody> </table> </div>
ControlsControls
Data modelData model
NOTENOTE
PROPERTY TYPE DESCRIPTION
firstName string First name of the current user.
lastName string Last name of the current user.
companyName string The company name of the current user.
addresserEmail string Email address of the current user.
developersUsageStatisticsLinkk string Relative URL to view analytics for thecurrent user.
subscriptions Collection of Subscription entities. The subscriptions for the current user.
applications Collection of Application entities. The applications of the current user.
changePasswordUrl string The relative URL to change the currentuser's password.
changeNameOrEmailUrl string The relative URL to change the nameand email for the current user.
canChangePassword boolean Whether the current user can changetheir password.
isSystemUser boolean Whether the current user is a memberof one of the built-in groups.
Sample template dataSample template data
This template may use the following page controls.
app-actions
The Profile, Applications, and Subscriptions templates share the same data model and receive the same template data.
{ "firstName": "Administrator", "lastName": "", "companyName": "Contoso", "addresserEmail": "[email protected]", "email": "[email protected]", "developersUsageStatisticsLink": "/Developer/Analytics", "subscriptions": [ { "Id": "57026e30de15d80041070001", "ProductId": "57026e30de15d80041060001", "ProductTitle": "Starter", "ProductDescription": "Subscribers will be able to run 5 calls/minute up to a maximum of 100 calls/week.", "ProductDetailsUrl": "/Products/57026e30de15d80041060001", "State": "Active", "DisplayName": "Starter (default)", "CreatedDate": "2016-04-04T13:37:52.847", "CanBeCancelled": true, "IsAwaitingApproval": false, "StartDate": null, "ExpirationDate": null, "NotificationDate": null, "PrimaryKey": "b6b2870953d04420a4e02c58f2c08e74", "SecondaryKey": "cfe28d5a1cd04d8abc93f48352076ea5", "UserId": 1, "CanBeRenewed": false, "HasExpired": false, "IsRejected": false, "CancelUrl": "/Subscriptions/57026e30de15d80041070001/Cancel", "RenewUrl": "/Subscriptions/57026e30de15d80041070001/Renew" }, { "Id": "57026e30de15d80041070002", "ProductId": "57026e30de15d80041060002", "ProductTitle": "Unlimited", "ProductDescription": "Subscribers have completely unlimited access to the API. Administrator approval is required.", "ProductDetailsUrl": "/Products/57026e30de15d80041060002", "State": "Active", "DisplayName": "Unlimited (default)", "CreatedDate": "2016-04-04T13:37:52.923", "CanBeCancelled": true, "IsAwaitingApproval": false, "StartDate": null, "ExpirationDate": null, "NotificationDate": null, "PrimaryKey": "8fe7843c36de4cceb4728e6cae297336", "SecondaryKey": "96c850d217e74acf9b514ff8a5b38551", "UserId": 1, "CanBeRenewed": false, "HasExpired": false, "IsRejected": false, "CancelUrl": "/Subscriptions/57026e30de15d80041070002/Cancel", "RenewUrl": "/Subscriptions/57026e30de15d80041070002/Renew" } ], "applications": [], "changePasswordUrl": "/account/password/change", "changeNameOrEmailUrl": "/account/update", "canChangePassword": false, "isSystemUser": true }
Update account info
Default templateDefault template
<div class="row"> <div class="col-sm-6 col-md-6"> <div class="form-group"> <label for="Email">{% localized "SigninResources|TextboxLabelEmail" %}</label> <input autofocus="autofocus" class="form-control" id="Email" name="Email" type="text" value="{{email}}"> </div> <div class="form-group"> <label for="FirstName">{% localized "SigninResources|TextboxLabelEmailFirstName" %}</label> <input class="form-control" id="FirstName" name="FirstName" type="text" value="{{firstName}}"> </div> <div class="form-group"> <label for="LastName">{% localized "SigninResources|TextboxLabelEmailLastName" %}</label> <input class="form-control" id="LastName" name="LastName" type="text" value="{{lastName}}"> </div> <div class="form-group"> <label for="Password">{% localized "SigninResources|WebAuthenticationSigninPasswordLabel" %}</label> <input class="form-control" id="Password" name="Password" type="password"> </div> </div> </div>
<button type="submit" class="btn btn-primary" id="UpdateProfile"> {% localized "UpdateProfileStrings|ButtonLabelUpdateProfile" %} </button> <a class="btn btn-default" href="/developer" role="button"> {% localized "CommonStrings|ButtonLabelCancel" %} </a>
ControlsControls
The Uodate account info template allows you to customize the Update account information page in thedeveloper portal.
This template may not use any page controls.
Data modelData model
Sample template dataSample template data
{ "FirstName": "Administrator", "LastName": "", "Email": "[email protected]", "Password": null, "NameIdentifier": null, "ProviderName": null, "IsBasicAccount": false }
Next steps
User account info entity.
For more information about working with templates, see How to customize the API Management developer portalusing templates.
Page templates in Azure API Management1/10/2018 • 3 min to read • Edit Online
NOTENOTE
Sign in
Azure API Management provides you the ability to customize the content of developer portal pages using a set oftemplates that configure their content. Using DotLiquid syntax and the editor of your choice, such as DotLiquid forDesigners, and a provided set of localized String resources, Glyph resources, and Page controls, you have greatflexibility to configure the content of the pages as you see fit using these templates.
The templates in this section allow you to customize the content of the sign in, sign up, and page not found pagesin the developer portal.
Sign in
Sign up
Page not found
Sample default templates are included in the following documentation, but are subject to change due to continuousimprovements. You can view the live default templates in the developer portal by navigating to the desired individualtemplates. For more information about working with templates, see How to customize the API Management developerportal using templates.
The sign in template allows you to customize the sign in page in the developer portal.
Default templateDefault template
<h2 class="text-center">{% localized "SigninStrings|WebAuthenticationSigninTitle" %}</h2> {% if registrationEnabled == true %} <p class="text-center">{% localized "SigninStrings|WebAuthenticationNotAMember" %}</p> {% endif %}
<div class="row center-block ap-idp-container"> <div class="col-md-6"> {% if registrationEnabled == true %} <p>{% localized "SigninStrings|WebAuthenticationSigininWithPassword" %}</p> <basic-SignIn></basic-SignIn> {% endif %} </div>
{% if registrationEnabled != true and providers.size == 0 %} {% localized "ProviderInfoStrings|TextboxExternalIdentitiesDisabled" %} {% else %} {% if providers.size > 0 %} <div class="col-md-6"> <div class="providers-list"> <p class="text-left"> {% if registrationEnabled == true %} {% localized "ProviderInfoStrings|TextboxExternalIdentitiesSigninInvitation" %} {% else %} {% localized "ProviderInfoStrings|TextboxExternalIdentitiesSigninInvitationPrimary" %} {% endif %} </p> <providers></providers> </div> </div> {% endif %} {% endif %}
{% if userRegistrationTermsEnabled == true %} <div class="col-md-6"> <div id="terms" class="modal" role="dialog" tabindex="-1"> <div class="modal-dialog"> <div class="modal-content"> <div class="modal-header"> <h4 class="modal-title">{% localized "SigninResources|DialogHeadingTermsOfUse" %}</h4> </div> <div class="modal-body break-all">{{userRegistrationTerms}}</div> <div class="modal-footer"> <button type="button" class="btn btn-default" data-dismiss="modal">{% localized "CommonStrings|ButtonLabelClose" %}</button> </div> </div> </div> </div> <p>{% localized "SigninResources|TextblockUserRegistrationTermsProvided" %}</p> </div> {% endif %} </div>
ControlsControls
Data modelData model
Sample template dataSample template data
This template may use the following page controls.
basic-signin
providers
User sign in entity.
{ "Email": null, "Password": null, "ReturnUrl": null, "RememberMe": false, "RegistrationEnabled": true, "DelegationEnabled": false, "DelegationUrl": null, "SsoSignUpUrl": null, "AuxServiceUrl": "https://portal.azure.com/#resource/subscriptions/{subscription ID}/resourceGroups/Api-Default-West-US/providers/Microsoft.ApiManagement/service/contoso5", "Providers": [ { "Properties": { "AuthenticationType": "Aad", "Caption": "Azure Active Directory" }, "AuthenticationType": "Aad", "Caption": "Azure Active Directory" } ], "UserRegistrationTerms": null, "UserRegistrationTermsEnabled": false}
Sign upThe sign up template allows you to customize the sign up page in the developer portal.
Default templateDefault template
<h2 class="text-center">{% localized "SignupStrings|PageTitleSignup" %}</h2> <p class="text-center"> {% localized "SignupStrings|WebAuthenticationAlreadyAMember" %} <a href="/signin">{% localized "SignupStrings|WebAuthenticationSigninNow" %}</a> </p>
<div class="row center-block ap-idp-container"> <div class="col-md-6"> <p>{% localized "SignupStrings|WebAuthenticationCreateNewAccount" %}</p> <sign-up></sign-up> </div> </div>
ControlsControls
Data modelData model
This template may use the following page controls.
sign-up
Sample template dataSample template data
{ "PasswordConfirm": null, "Password": null, "PasswordVerdictLevel": 0, "UserRegistrationTerms": null, "UserRegistrationTermsOptions": 0, "ConsentAccepted": false, "Email": null, "FirstName": null, "LastName": null, "UserData": null, "NameIdentifier": null, "ProviderName": null }
Page not found
Default templateDefault template
User sign up entity.
The page not found template allows you to customize the page not found page in the developer portal.
<h2>{% localized "NotFoundStrings|PageTitleNotFound" %}</h2>
<h3>{% localized "NotFoundStrings|TitlePotentialCause" %}</h3> <ul> <li>{% localized "NotFoundStrings|TextblockPotentialCauseOldLink" %}</li> <li>{% localized "NotFoundStrings|TextblockPotentialCauseMisspelledUrl" %}</li> </ul>
<h3>{% localized "NotFoundStrings|TitlePotentialSolution" %}</h3> <ul> <li>{% localized "NotFoundStrings|TextblockPotentialSolutionRetype" %}</li> <li> {% capture textPotentialSolutionStartOver %}{% localized "NotFoundStrings|TextblockPotentialSolutionStartOver" %}{% endcapture %} {% capture homeLink %}<a href="/">{% localized "NotFoundStrings|LinkLabelHomePage" %}</a>{% endcapture %} {% assign replaceString = '{0}' %}
{{ textPotentialSolutionStartOver | replace : replaceString, homeLink }} </li> </ul>
<p> {% capture textReportProblem %}{% localized "NotFoundStrings|TextReportProblem" %}{% endcapture %} {% capture emailLink %}<a href="mailto:[email protected]" target="_self" title="API Management Support">{% localized "NotFoundStrings|LinkLabelSendUsEmail" %}</a>{% endcapture %} {% assign replaceString = '{0}' %}
{{ textReportProblem | replace : replaceString, emailLink }} </p>
ControlsControls
Data modelData model
PROPERTY TYPE DESCRIPTION
referenceCode string Code generated if this page wasdisplayed as the result of an internalerror.
errorCode string Code generated if this page wasdisplayed as the result of an internalerror.
emailBody string Email body generated if this page wasdisplayed as the result of an internalerror.
requestedUrl string The URL requested when the page wasnot found.
referrerUrl string The referrer URL to the requested URL.
Sample template dataSample template data
This template may not use any page controls.
{ "referenceCode": null, "errorCode": null, "emailBody": null, "requestedUrl": "https://contoso5.portal.azure-api.net:443/NotFoundPage?startEditTemplate=NotFoundPage", "referrerUrl": "https://contoso5.portal.azure-api.net/signup?startEditTemplate=SignUpTemplate" }
Next stepsFor more information about working with templates, see How to customize the API Management developer portalusing templates.
Azure API Management template resources8/30/2017 • 21 min to read • Edit Online
String resources
{% localized "Prefix|Name" %}
<h2>{% localized "ProductsStrings|PageTitleProducts" %}</h2>
Azure API Management provides the following types of resources for use in the developer portal templates.
String resources
Glyph resources
API Management provides a comprehensive set of string resources for use in the developer portal. Theseresources are localized into all of the languages supported by API Management. The default set of templates usesthese resources for page headers, labels, and any constant strings that are displayed in the developer portal. To usea string resource in your templates, provide the resource string prefix followed by the string name, as shown in thefollowing example.
The following example is from the Product list template, and displays Products at the top of the page.
Refer to the following tables for the string resources available for use in your developer portal templates. Use thetable name as the prefix for the string resources in that table.
ApisStrings
ApplicationListStrings
AppDetailsStrings
AppStrings
CommonResources
CommonStrings
Documentation
ErrorPageStrings
IssuesStrings
NotFoundStrings
ProductDetailsStrings
ProductsStrings
ProviderInfoStrings
SigninResources
SigninStrings
ApisStringsApisStrings
NAME TEX T
PageTitleApis APIs
AppDetailsStringsAppDetailsStrings
NAME TEX T
WebApplicationsDetailsTitle Application preview
WebApplicationsRequirementsHeader Requirements
WebApplicationsScreenshotAlt Screenshot
WebApplicationsScreenshotsHeader Screenshots
ApplicationListStringsApplicationListStrings
NAME TEX T
WebDevelopersAppDeleteConfirmation Are you sure that you want to remove application?
WebDevelopersAppNotPublished Not published
WebDevelopersAppNotSubminted Not submitted
WebDevelopersAppTableCategoryHeader Category
WebDevelopersAppTableNameHeader Name
WebDevelopersAppTableStateHeader State
WebDevelopersEditLink Edit
WebDevelopersRegisterAppLink Register application
WebDevelopersRemoveLink Remove
WebDevelopersSubmitLink Submit
WebDevelopersYourApplicationsHeader Your applications
AppStringsAppStrings
SignupStrings
SubscriptionListStrings
SubscriptionStrings
UpdateProfileStrings
UserProfile
NAME TEX T
WebApplicationsHeader Applications
CommonResourcesCommonResources
NAME TEX T
NoItemsToDisplay No results found.
GeneralExceptionMessage Something is not right. It could be a temporary glitch or abug. Please, try again.
GeneralJsonExceptionMessage Something is not right. It could be a temporary glitch or abug. Please, reload the page and try again.
ConfirmationMessageUnsavedChanges There are some unsaved changes. Are you sure you want tocancel and discard the changes?
AzureActiveDirectory Azure Active Directory
HttpLargeRequestMessage Http Request Body too large.
CommonStringsCommonStrings
NAME TEX T
ButtonLabelCancel Cancel
ButtonLabelSave Save
GeneralExceptionMessage Something is not right. It could be a temporary glitch or abug. Please, try again.
NoItemsToDisplay There are no items to display.
PagerButtonLabelFirst First
PagerButtonLabelLast Last
PagerButtonLabelNext Next
PagerButtonLabelPrevious Prev
PagerLabelPageNOfM Page {0} of {1}
PasswordTooShort The Password is too short
EmailAsPassword Do not use your email as your password
PasswordSameAsUserName Your password cannot contain your username
PasswordTwoCharacterClasses Use different character classes
PasswordTooManyRepetitions Too many repetitions
PasswordSequenceFound Your password contains sequences
PagerLabelPageSize Page size
CurtainLabelLoading Loading...
TablePlaceholderNothingToDisplay There is no data for the selected period and scope
ButtonLabelClose Close
NAME TEX T
DocumentationDocumentation
NAME TEX T
WebDocumentationInvalidHeaderErrorMessage Invalid header '{0}'
WebDocumentationInvalidRequestErrorMessage Invalid Request URL
TextboxLabelAccessToken Access token *
DropdownOptionPrimaryKeyFormat Primary-{0}
DropdownOptionSecondaryKeyFormat Secondary-{0}
WebDocumentationSubscriptionKeyText Your subscription key
WebDocumentationTemplatesAddHeaders Add required HTTP headers
WebDocumentationTemplatesBasicAuthSample Basic Authorization Sample
WebDocumentationTemplatesCurlForBasicAuth for Basic Authorization use: --user {username}:{password}
WebDocumentationTemplatesCurlValuesForPath Specify values for path parameters (shown as {...}), yoursubscription key and values for query parameters
WebDocumentationTemplatesDeveloperKey Specify your subscription key
WebDocumentationTemplatesJavaApache This sample uses the Apache HTTP client from HTTPComponents (http://hc.apache.org/httpcomponents-client-ga/)
WebDocumentationTemplatesOptionalParams Specify values for optional parameters, as needed
WebDocumentationTemplatesPhpPackage This sample uses the HTTP_Request2 package. (for moreinformation: http://pear.php.net/package/HTTP_Request2)
WebDocumentationTemplatesPythonValuesForPath Specify values for path parameters (shown as {...}) and requestbody if needed
WebDocumentationTemplatesRequestBody Specify request body
WebDocumentationTemplatesRequiredParams Specify values for the following required parameters
WebDocumentationTemplatesValuesForPath Specify values for path parameters (shown as {...})
OAuth2AuthorizationEndpointDescription The authorization endpoint is used to interact with theresource owner and obtain an authorization grant.
OAuth2AuthorizationEndpointName Authorization endpoint
OAuth2TokenEndpointDescription The token endpoint is used by the client to obtain an accesstoken by presenting its authorization grant or refresh token.
OAuth2TokenEndpointName Token endpoint
OAuth2Flow_AuthorizationCodeGrant_Step_AuthorizationRequest_Description
<p> The client initiates the flow by directing the resourceowner's user-agent to the authorization endpoint. The clientincludes its client identifier, requested scope, local state, and aredirection URI to which the authorization server will send theuser-agent back once access is granted (or denied). </p> <p>The authorization server authenticates the resource owner (viathe user-agent) and establishes whether the resource ownergrants or denies the client's access request. </p> <p>Assuming the resource owner grants access, the authorizationserver redirects the user-agent back to the client using theredirection URI provided earlier (in the request or during clientregistration). The redirection URI includes an authorizationcode and any local state provided by the client earlier. </p>
OAuth2Flow_AuthorizationCodeGrant_Step_AuthorizationRequest_ErrorDescription
<p> If the user denies the access request of if the request isinvalid, the client will be informed using the followingparameters added on to the redirect: </p>
OAuth2Flow_AuthorizationCodeGrant_Step_AuthorizationRequest_Name
Authorization request
OAuth2Flow_AuthorizationCodeGrant_Step_AuthorizationRequest_RequestDescription
<p> The client app must send the user to the authorizationendpoint in order to initiate the OAuth process. At theauthorization endpoint, the user authenticates and thengrants or denies access to the app. </p>
OAuth2Flow_AuthorizationCodeGrant_Step_AuthorizationRequest_ResponseDescription
<p> Assuming the resource owner grants access,authorization server redirects the user-agent back to the clientusing the redirection URI provided earlier (in the request orduring client registration). The redirection URI includes anauthorization code and any local state provided by the clientearlier. </p>
NAME TEX T
OAuth2Flow_AuthorizationCodeGrant_Step_TokenRequest_Description
<p> The client requests an access token from theauthorization server''s token endpoint by including theauthorization code received in the previous step. Whenmaking the request, the client authenticates with theauthorization server. The client includes the redirection URIused to obtain the authorization code for verification. </p><p> The authorization server authenticates the client,validates the authorization code, and ensures that theredirection URI received matches the URI used to redirect theclient in step (C). If valid, the authorization server respondsback with an access token and, optionally, a refresh token.</p>
OAuth2Flow_AuthorizationCodeGrant_Step_TokenRequest_ErrorDescription
<p> If the request client authentication failed or is invalid, theauthorization server responds with an HTTP 400 (BadRequest) status code (unless specified otherwise) and includesthe following parameters with the response. </p>
OAuth2Flow_AuthorizationCodeGrant_Step_TokenRequest_RequestDescription
<p> The client makes a request to the token endpoint bysending the following parameters using the "application/x-www-form-urlencoded" format with a character encoding ofUTF-8 in the HTTP request entity-body. </p>
OAuth2Flow_AuthorizationCodeGrant_Step_TokenRequest_ResponseDescription
<p> The authorization server issues an access token andoptional refresh token, and constructs the response by addingthe following parameters to the entity-body of the HTTPresponse with a 200 (OK) status code. </p>
OAuth2Flow_ClientCredentialsGrant_Step_TokenRequest_Description
<p> The client authenticates with the authorization serverand requests an access token from the token endpoint. </p><p> The authorization server authenticates the client, and ifvalid, issues an access token. </p>
OAuth2Flow_ClientCredentialsGrant_Step_TokenRequest_ErrorDescription
<p> If the request failed client authentication or is invalid theauthorization server responds with an HTTP 400 (BadRequest) status code (unless specified otherwise) and includesthe following parameters with the response. </p>
OAuth2Flow_ClientCredentialsGrant_Step_TokenRequest_RequestDescription
<p> The client makes a request to the token endpoint byadding the following parameters using the "application/x-www-form-urlencoded" format with a character encoding ofUTF-8 in the HTTP request entity-body. </p>
OAuth2Flow_ClientCredentialsGrant_Step_TokenRequest_ResponseDescription
<p> If the access token request is valid and authorized, theauthorization server issues an access token and optionalrefresh token, and constructs the response by adding thefollowing parameters to the entity-body of the HTTP responsewith a 200 (OK) status code. </p>
NAME TEX T
OAuth2Flow_ImplicitGrant_Step_AuthorizationRequest_Description
<p> The client initiates the flow by directing the resourceowner''s user-agent to the authorization endpoint. The clientincludes its client identifier, requested scope, local state, and aredirection URI to which the authorization server will send theuser-agent back once access is granted (or denied). </p> <p>The authorization server authenticates the resource owner (viathe user-agent) and establishes whether the resource ownergrants or denies the client''s access request. </p> <p>Assuming the resource owner grants access, the authorizationserver redirects the user-agent back to the client using theredirection URI provided earlier. The redirection URI includesthe access token in the URI fragment. </p>
OAuth2Flow_ImplicitGrant_Step_AuthorizationRequest_ErrorDescription
<p> If the resource owner denies the access request or if therequest fails for reasons other than a missing or invalidredirection URI, the authorization server informs the client byadding the following parameters to the fragment componentof the redirection URI using the "application/x-www-form-urlencoded" format. </p>
OAuth2Flow_ImplicitGrant_Step_AuthorizationRequest_RequestDescription
<p> The client app must send the user to the authorizationendpoint in order to initiate the OAuth process. At theauthorization endpoint, the user authenticates and thengrants or denies access to the app. </p>
OAuth2Flow_ImplicitGrant_Step_AuthorizationRequest_ResponseDescription
<p> If the resource owner grants the access request, theauthorization server issues an access token and delivers it tothe client by adding the following parameters to the fragmentcomponent of the redirection URI using the "application/x-www-form-urlencoded" format. </p>
OAuth2Flow_ObtainAuthorization_AuthorizationCodeGrant_Description
Authorization code flow is optimized for clients capable ofmaintaining the confidentiality of their credentials (e.g., webserver applications implemented using PHP, Java, Python,Ruby, ASP.NET, etc.).
OAuth2Flow_ObtainAuthorization_AuthorizationCodeGrant_Name
Authorization Code grant
OAuth2Flow_ObtainAuthorization_ClientCredentialsGrant_Description
Client credentials flow is suitable in cases where the client(your application) is requesting access to the protectedresources under its control. The client is considered as aresource owner, so no end-user interaction is required.
OAuth2Flow_ObtainAuthorization_ClientCredentialsGrant_Name
Client Credentials grant
OAuth2Flow_ObtainAuthorization_ImplicitGrant_Description Implicit flow is optimized for clients incapable of maintainingthe confidentiality of their credentials known to operate aparticular redirection URI. These clients are typicallyimplemented in a browser using a scripting language such asJavaScript.
OAuth2Flow_ObtainAuthorization_ImplicitGrant_Name Implicit grant
NAME TEX T
OAuth2Flow_ObtainAuthorization_ResourceOwnerPasswordCredentialsGrant_Description
Resource owner password credentials flow is suitable in caseswhere the resource owner has a trust relationship with theclient (your application), such as the device operating systemor a highly privileged application. This flow is suitable forclients capable of obtaining the resource owner's credentials(username and password, typically using an interactive form).
OAuth2Flow_ObtainAuthorization_ResourceOwnerPasswordCredentialsGrant_Name
Resource Owner Password Credentials grant
OAuth2Flow_ResourceOwnerPasswordCredentialsGrant_Step_TokenRequest_Description
<p> The resource owner provides the client with its usernameand password. </p> <p> The client requests an access tokenfrom the authorization server''s token endpoint by includingthe credentials received from the resource owner. Whenmaking the request, the client authenticates with theauthorization server. </p> <p> The authorization serverauthenticates the client and validates the resource ownercredentials, and if valid, issues an access token. </p>
OAuth2Flow_ResourceOwnerPasswordCredentialsGrant_Step_TokenRequest_ErrorDescription
<p> If the request failed client authentication or is invalid theauthorization server responds with an HTTP 400 (BadRequest) status code (unless specified otherwise) and includesthe following parameters with the response. </p>
OAuth2Flow_ResourceOwnerPasswordCredentialsGrant_Step_TokenRequest_RequestDescription
<p> The client makes a request to the token endpoint byadding the following parameters using the "application/x-www-form-urlencoded" format with a character encoding ofUTF-8 in the HTTP request entity-body. </p>
OAuth2Flow_ResourceOwnerPasswordCredentialsGrant_Step_TokenRequest_ResponseDescription
<p> If the access token request is valid and authorized, theauthorization server issues an access token and optionalrefresh token, and constructs the response by adding thefollowing parameters to the entity-body of the HTTP responsewith a 200 (OK) status code. </p>
OAuth2Step_AccessTokenRequest_Name Access token request
OAuth2Step_AuthorizationRequest_Name Authorization request
OAuth2AccessToken_AuthorizationCodeGrant_TokenResponse REQUIRED. The access token issued by the authorizationserver.
OAuth2AccessToken_ClientCredentialsGrant_TokenResponse REQUIRED. The access token issued by the authorizationserver.
OAuth2AccessToken_ImplicitGrant_AuthorizationResponse REQUIRED. The access token issued by the authorizationserver.
OAuth2AccessToken_ResourceOwnerPasswordCredentialsGrant_TokenResponse
REQUIRED. The access token issued by the authorizationserver.
OAuth2ClientId_AuthorizationCodeGrant_AuthorizationRequest
REQUIRED. Client identifier.
NAME TEX T
OAuth2ClientId_AuthorizationCodeGrant_TokenRequest REQUIRED if the client is not authenticating with theauthorization server.
OAuth2ClientId_ImplicitGrant_AuthorizationRequest REQUIRED. The client identifier.
OAuth2Code_AuthorizationCodeGrant_AuthorizationResponse
REQUIRED. The authorization code generated by theauthorization server.
OAuth2Code_AuthorizationCodeGrant_TokenRequest REQUIRED. The authorization code received from theauthorization server.
OAuth2ErrorDescription_AuthorizationCodeGrant_AuthorizationErrorResponse
OPTIONAL. Human-readable ASCII text providing additionalinformation.
OAuth2ErrorDescription_AuthorizationCodeGrant_TokenErrorResponse
OPTIONAL. Human-readable ASCII text providing additionalinformation.
OAuth2ErrorDescription_ClientCredentialsGrant_TokenErrorResponse
OPTIONAL. Human-readable ASCII text providing additionalinformation.
OAuth2ErrorDescription_ImplicitGrant_AuthorizationErrorResponse
OPTIONAL. Human-readable ASCII text providing additionalinformation.
OAuth2ErrorDescription_ResourceOwnerPasswordCredentialsGrant_TokenErrorResponse
OPTIONAL. Human-readable ASCII text providing additionalinformation.
OAuth2ErrorUri_AuthorizationCodeGrant_AuthorizationErrorResponse
OPTIONAL. A URI identifying a human-readable web pagewith information about the error.
OAuth2ErrorUri_AuthorizationCodeGrant_TokenErrorResponse OPTIONAL. A URI identifying a human-readable web pagewith information about the error.
OAuth2ErrorUri_ClientCredentialsGrant_TokenErrorResponse OPTIONAL. A URI identifying a human-readable web pagewith information about the error.
OAuth2ErrorUri_ImplicitGrant_AuthorizationErrorResponse OPTIONAL. A URI identifying a human-readable web pagewith information about the error.
OAuth2ErrorUri_ResourceOwnerPasswordCredentialsGrant_TokenErrorResponse
OPTIONAL. A URI identifying a human-readable web pagewith information about the error.
OAuth2Error_AuthorizationCodeGrant_AuthorizationErrorResponse
REQUIRED. A single ASCII error code from the following:invalid_request, unauthorized_client, access_denied,unsupported_response_type, invalid_scope, server_error,temporarily_unavailable.
OAuth2Error_AuthorizationCodeGrant_TokenErrorResponse REQUIRED. A single ASCII error code from the following:invalid_request, invalid_client, invalid_grant,unauthorized_client, unsupported_grant_type, invalid_scope.
OAuth2Error_ClientCredentialsGrant_TokenErrorResponse REQUIRED. A single ASCII error code from the following:invalid_request, invalid_client, invalid_grant,unauthorized_client, unsupported_grant_type, invalid_scope.
NAME TEX T
OAuth2Error_ImplicitGrant_AuthorizationErrorResponse REQUIRED. A single ASCII error code from the following:invalid_request, unauthorized_client, access_denied,unsupported_response_type, invalid_scope, server_error,temporarily_unavailable.
OAuth2Error_ResourceOwnerPasswordCredentialsGrant_TokenErrorResponse
REQUIRED. A single ASCII error code from the following:invalid_request, invalid_client, invalid_grant,unauthorized_client, unsupported_grant_type, invalid_scope.
OAuth2ExpiresIn_AuthorizationCodeGrant_TokenResponse RECOMMENDED. The lifetime in seconds of the access token.
OAuth2ExpiresIn_ClientCredentialsGrant_TokenResponse RECOMMENDED. The lifetime in seconds of the access token.
OAuth2ExpiresIn_ImplicitGrant_AuthorizationResponse RECOMMENDED. The lifetime in seconds of the access token.
OAuth2ExpiresIn_ResourceOwnerPasswordCredentialsGrant_TokenResponse
RECOMMENDED. The lifetime in seconds of the access token.
OAuth2GrantType_AuthorizationCodeGrant_TokenRequest REQUIRED. Value MUST be set to "authorization_code".
OAuth2GrantType_ClientCredentialsGrant_TokenRequest REQUIRED. Value MUST be set to "client_credentials".
OAuth2GrantType_ResourceOwnerPasswordCredentialsGrant_TokenRequest
REQUIRED. Value MUST be set to "password".
OAuth2Password_ResourceOwnerPasswordCredentialsGrant_TokenRequest
REQUIRED. The resource owner password.
OAuth2RedirectUri_AuthorizationCodeGrant_AuthorizationRequest
OPTIONAL. The redirection endpoint URI must be an absoluteURI.
OAuth2RedirectUri_AuthorizationCodeGrant_TokenRequest REQUIRED if the "redirect_uri" parameter was included in theauthorization request, and their values MUST be identical.
OAuth2RedirectUri_ImplicitGrant_AuthorizationRequest OPTIONAL. The redirection endpoint URI must be an absoluteURI.
OAuth2RefreshToken_AuthorizationCodeGrant_TokenResponse OPTIONAL. The refresh token, which can be used to obtainnew access tokens.
OAuth2RefreshToken_ClientCredentialsGrant_TokenResponse OPTIONAL. The refresh token, which can be used to obtainnew access tokens.
OAuth2RefreshToken_ResourceOwnerPasswordCredentialsGrant_TokenResponse
OPTIONAL. The refresh token, which can be used to obtainnew access tokens.
OAuth2ResponseType_AuthorizationCodeGrant_AuthorizationRequest
REQUIRED. Value MUST be set to "code".
OAuth2ResponseType_ImplicitGrant_AuthorizationRequest REQUIRED. Value MUST be set to "token".
OAuth2Scope_AuthorizationCodeGrant_AuthorizationRequest OPTIONAL. The scope of the access request.
NAME TEX T
OAuth2Scope_AuthorizationCodeGrant_TokenResponse OPTIONAL if identical to the scope requested by the client;otherwise, REQUIRED.
OAuth2Scope_ClientCredentialsGrant_TokenRequest OPTIONAL. The scope of the access request.
OAuth2Scope_ClientCredentialsGrant_TokenResponse OPTIONAL, if identical to the scope requested by the client;otherwise, REQUIRED.
OAuth2Scope_ImplicitGrant_AuthorizationRequest OPTIONAL. The scope of the access request.
OAuth2Scope_ImplicitGrant_AuthorizationResponse OPTIONAL if identical to the scope requested by the client;otherwise, REQUIRED.
OAuth2Scope_ResourceOwnerPasswordCredentialsGrant_TokenRequest
OPTIONAL. The scope of the access request.
OAuth2Scope_ResourceOwnerPasswordCredentialsGrant_TokenResponse
OPTIONAL, if identical to the scope requested by the client;otherwise, REQUIRED.
OAuth2State_AuthorizationCodeGrant_AuthorizationErrorResponse
REQUIRED if the "state" parameter was present in the clientauthorization request. The exact value received from the client.
OAuth2State_AuthorizationCodeGrant_AuthorizationRequest RECOMMENDED. An opaque value used by the client tomaintain state between the request and callback. Theauthorization server includes this value when redirecting theuser-agent back to the client. The parameter SHOULD be usedfor preventing cross-site request forgery.
OAuth2State_AuthorizationCodeGrant_AuthorizationResponse REQUIRED if the "state" parameter was present in the clientauthorization request. The exact value received from the client.
OAuth2State_ImplicitGrant_AuthorizationErrorResponse REQUIRED if the "state" parameter was present in the clientauthorization request. The exact value received from the client.
OAuth2State_ImplicitGrant_AuthorizationRequest RECOMMENDED. An opaque value used by the client tomaintain state between the request and callback. Theauthorization server includes this value when redirecting theuser-agent back to the client. The parameter SHOULD be usedfor preventing cross-site request forgery.
OAuth2State_ImplicitGrant_AuthorizationResponse REQUIRED if the "state" parameter was present in the clientauthorization request. The exact value received from the client.
OAuth2TokenType_AuthorizationCodeGrant_TokenResponse REQUIRED. The type of the token issued.
OAuth2TokenType_ClientCredentialsGrant_TokenResponse REQUIRED. The type of the token issued.
OAuth2TokenType_ImplicitGrant_AuthorizationResponse REQUIRED. The type of the token issued.
OAuth2TokenType_ResourceOwnerPasswordCredentialsGrant_TokenResponse
REQUIRED. The type of the token issued.
OAuth2UserName_ResourceOwnerPasswordCredentialsGrant_TokenRequest
REQUIRED. The resource owner username.
NAME TEX T
OAuth2UnsupportedTokenType Token type '{0}' is not supporetd.
OAuth2InvalidState Invalid response from authorization server
OAuth2GrantType_AuthorizationCode Authorization code
OAuth2GrantType_Implicit Implicit
OAuth2GrantType_ClientCredentials Client credentials
OAuth2GrantType_ResourceOwnerPassword Resource owner password
WebDocumentation302Code 302 Found
WebDocumentation400Code 400 (Bad request)
OAuth2SendingMethod_AuthHeader Authorization header
OAuth2SendingMethod_QueryParam Query parameter
OAuth2AuthorizationServerGeneralException An error has occurred while authorizing access via {0}
OAuth2AuthorizationServerCommunicationException An HTTP connection to authorization server could not beestablished or it has been unexpectedly closed.
WebDocumentationOAuth2GeneralErrorMessage Unexpected error occured.
AuthorizationServerCommunicationException Authorization server communication exception has happened.Please contact administrator.
TextblockSubscriptionKeyHeaderDescription Subscription key which provides access to this API. Found inyour <a href='/developer'>Profile</a>.
TextblockOAuthHeaderDescription OAuth 2.0 access token obtained from <i>{0}</i>. Supportedgrant types: <i>{1}</i>.
TextblockContentTypeHeaderDescription Media type of the body sent to the API.
ErrorMessageApiNotAccessible The API you are trying to call is not accessible at this time.Please contact the API publisher <a href="/issues">here</a>.
ErrorMessageApiTimedout The API you are trying to call is taking longer than normal toget response back. Please contact the API publisher <ahref="/issues">here</a>.
BadRequestParameterExpected "'{0}' parameter is expected"
TooltipTextDoubleClickToSelectAll Double click to select all.
TooltipTextHideRevealSecret Show/Hide
NAME TEX T
ButtonLinkOpenConsole Try it
SectionHeadingRequestBody Request body
SectionHeadingRequestParameters Request parameters
SectionHeadingRequestUrl Request URL
SectionHeadingResponse Response
SectionHeadingRequestHeaders Request headers
FormLabelSubtextOptional optional
SectionHeadingCodeSamples Code samples
TextblockOpenidConnectHeaderDescription OpenID Connect id token obtained from <i>{0}</i>.Supported grant types: <i>{1}</i>.
NAME TEX T
ErrorPageStringsErrorPageStrings
NAME TEX T
LinkLabelBack back
LinkLabelHomePage home page
LinkLabelSendUsEmail Send us an e-mail
PageTitleError Sorry, there was a problem serving the requested page
TextblockPotentialCauseIntermittentIssue This may be an intermittent data access issue that is alreadygone.
TextblockPotentialCauseOldLink The link you have clicked on may be old and not point to thecorrect location anymore.
TextblockPotentialCauseTechnicalProblem There may be a technical problem on our end.
TextblockPotentialSolutionRefresh Try refreshing the page.
TextblockPotentialSolutionStartOver Start over from our {0}.
TextblockPotentialSolutionTryAgain Go {0} and try the action you performed again.
TextReportProblem {0} describing what went wrong and we will look at it as soonas we can.
TitlePotentialCause Potential cause
TitlePotentialSolution It's possibly just a temporary issue, a few things to try
IssuesStringsIssuesStrings
NAME TEX T
WebIssuesIndexTitle Issues
WebIssuesNoActiveSubscriptions You have no active subscriptions. You need to subscribe for aproduct to report an issue.
WebIssuesNotSignin You're not signed in. Please {0} to report an issue or post acomment.
WebIssuesReportIssueButton Report Issue
WebIssuesSignIn sign in
WebIssuesStatusReportedBy Status: {0} | Reported by {1}
NotFoundStringsNotFoundStrings
NAME TEX T
LinkLabelHomePage home page
LinkLabelSendUsEmail send us an e-mail
PageTitleNotFound Sorry, we can’t find the page you are looking for
TextblockPotentialCauseMisspelledUrl You may have misspelled the URL if you typed it in.
TextblockPotentialCauseOldLink The link you have clicked on may be old and not point to thecorrect location anymore.
TextblockPotentialSolutionRetype Try retyping the URL.
TextblockPotentialSolutionStartOver Start over from our {0}.
TextReportProblem {0} describing what went wrong and we will look at it as soonas we can.
TitlePotentialCause Potential cause
TitlePotentialSolution Potential solution
ProductDetailsStringsProductDetailsStrings
NAME TEX T
WebProductsAgreement By subscribing to {0} Product, I agree to the <a data-toggle='modal' href='#legal-terms'\>Terms ofUse</a\>
.
WebProductsLegalTermsLink Terms of Use
WebProductsSubscribeButton Subscribe
WebProductsUsageLimitsHeader Usage limits
WebProductsYouAreNotSubscribed You are subscribed to this product.
WebProductsYouRequestedSubscription You requested subscription to this product.
ErrorYouNeedtoAgreeWithLegalTerms You must agree to the Terms of Use before you can proceed.
ButtonLabelAddSubscription Add subscription
LinkLabelChangeSubscriptionName change
ButtonLabelConfirm Confirm
TextblockMultipleSubscriptionsCount You have {0} subscriptions to this product:
TextblockSingleSubscriptionsCount You have {0} subscription to this product:
TextblockSingleApisCount This product contains {0} API:
TextblockMultipleApisCount This product contains {0} APIs:
TextblockHeaderSubscribe Subscribe to product
TextblockSubscriptionDescription A new subscription will be created as follows:
TextblockSubscriptionLimitReached Subscriptions limit reached.
NAME TEX T
ProductsStringsProductsStrings
NAME TEX T
PageTitleProducts Products
ProviderInfoStringsProviderInfoStrings
NAME TEX T
TextboxExternalIdentitiesDisabled Sign in is disabled by the administrators at the moment.
TextboxExternalIdentitiesSigninInvitation Alternatively, sign in with
TextboxExternalIdentitiesSigninInvitationPrimary Sign in with:
SigninResourcesSigninResources
NAME TEX T
PrincipalNotFound Principal is not found or signature is invalid
ErrorSsoAuthenticationFailed SSO authentication failed
ErrorSsoAuthenticationFailedDetailed Invalid token provided or signature cannot be verified.
ErrorSsoTokenInvalid SSO token is invalid
ValidationErrorSpecificEmailAlreadyExists Email '{0}' already registered
ValidationErrorSpecificEmailInvalid Email '{0}' is invalid
ValidationErrorPasswordInvalid Password is invalid. Please correct the errors and try again.
PropertyTooShort {0} is too short
WebAuthenticationAddresserEmailInvalidErrorMessage Invalid email address.
ValidationMessageNewPasswordConfirmationRequired Confirm new password
ValidationErrorPasswordConfirmationRequired Confirm password is empty
WebAuthenticationEmailChangeNotice Change confirmation email is on the way to {0}. Please followinstructions within it to confirm your new email address. If theemail does not arrive to your inbox in the next few minutes,please check your junk email folder.
WebAuthenticationEmailChangeNoticeHeader Your email change request was successfully processed
WebAuthenticationEmailChangeNoticeTitle Email change requested
WebAuthenticationEmailHasBeenRevertedNotice You email already exist. Request has been reverted
ValidationErrorEmailAlreadyExists Email already exist
ValidationErrorEmailInvalid Invalid e-mail address
TextboxLabelEmail Email
ValidationErrorEmailRequired Email is required.
WebAuthenticationErrorNoticeHeader Error
WebAuthenticationFieldLengthErrorMessage {0} must be a maximum length of {1}
TextboxLabelEmailFirstName First name
ValidationErrorFirstNameRequired First name is required.
ValidationErrorFirstNameInvalid Invalid first name
NAME TEX T
NoticeInvalidInvitationToken Please note that confirmation links are valid for only 48 hours.If you are still within this timeframe, please make sure yourlink is correct. If your link has expired, then please repeat theaction you're trying to confirm.
NoticeHeaderInvalidInvitationToken Invalid invitation token
NoticeTitleInvalidInvitationToken Confirmation error
WebAuthenticationLastNameInvalidErrorMessage Invalid last name
TextboxLabelEmailLastName Last name
ValidationErrorLastNameRequired Last name is required.
WebAuthenticationLinkExpiredNotice Confirmation link sent to you has expired. <a href={0}?token={1}>Resend confirmation email.</a\>
NoticePasswordResetLinkInvalidOrExpired Your password reset link is invalid or expired.
WebAuthenticationLinkExpiredNoticeTitle Link sent
WebAuthenticationNewPasswordLabel New password
ValidationMessageNewPasswordRequired New password is required.
TextboxLabelNotificationsSenderEmail Notifications sender email
TextboxLabelOrganizationName Organization name
WebAuthenticationOrganizationRequiredErrorMessage Organization name is empty
WebAuthenticationPasswordChangedNotice Your password was successfully updated
WebAuthenticationPasswordChangedNoticeTitle Password updated
WebAuthenticationPasswordCompareErrorMessage Passwords don't match
WebAuthenticationPasswordConfirmLabel Confirm password
ValidationErrorPasswordInvalidDetailed Password is too weak.
WebAuthenticationPasswordLabel Password
ValidationErrorPasswordRequired Password is required.
WebAuthenticationPasswordResetSendNotice Change password confirmation email is on the way to {0}.Please follow the instructions within the email to continueyour password change process.
WebAuthenticationPasswordResetSendNoticeHeader Your password reset request was successfully processed
NAME TEX T
WebAuthenticationPasswordResetSendNoticeTitle Password reset requested
WebAuthenticationRequestNotFoundNotice Request not found
WebAuthenticationSenderEmailRequiredErrorMessage Notifications sender email is empty
WebAuthenticationSigninPasswordLabel Please confirm the change by entering a password
WebAuthenticationSignupConfirmNotice Registration confirmation email is on its way to {0}.<br />Please follow instructions within the email to activate youraccount.<br /> If the email does not arrive in your inboxwithin the next few minutes, please check your junk emailfolder.
WebAuthenticationSignupConfirmNoticeHeader Your account was successfully created
WebAuthenticationSignupConfirmNoticeRepeatHeader Registration confirmation email was sent again
WebAuthenticationSignupConfirmNoticeTitle Account created
WebAuthenticationTokenRequiredErrorMessage Token is empty
WebAuthenticationUserAlreadyRegisteredNotice It seems a user with this email is already registered in thesystem. If you forgot your password, please try to restore it orcontact our support team.
WebAuthenticationUserAlreadyRegisteredNoticeHeader User already registered
WebAuthenticationUserAlreadyRegisteredNoticeTitle Already registered
ButtonLabelChangePassword Change password
ButtonLabelChangeAccountInfo Change account information
ButtonLabelCloseAccount Close account
WebAuthenticationInvalidCaptchaErrorMessage Text entered doesn't match text on the picture. Please tryagain.
ValidationErrorCredentialsInvalid Email or password is invalid. Please correct the errors and tryagain.
WebAuthenticationRequestIsNotValid Request is not valid
WebAuthenticationUserIsNotConfirm Please confirm your registration before attempting to sign in.
WebAuthenticationInvalidEmailFormated Email is invalid: {0}
WebAuthenticationUserNotFound User not found
NAME TEX T
WebAuthenticationTenantNotRegistered Your account belongs to a Azure Active Directory tenantwhich is not authorized to access this portal.
WebAuthenticationAuthenticationFailed Authentication has failed.
WebAuthenticationGooglePlusNotEnabled Authentication has failed. If you authorized the applicationthen please contact the admin to make sure that Googleauthentication is configured correctly.
ValidationErrorAllowedTenantIsRequired Allowed Tenant is required
ValidationErrorTenantIsNotValid The Azure Active Directory tenant '{0}' is not valid.
WebAuthenticationActiveDirectoryTitle Azure Active Directory
WebAuthenticationLoginUsingYourProvider Log in using your {0} account
WebAuthenticationUserLimitNotice This service has reached the maximum number of allowedusers. Please <a href="mailto:{0}"\>contact the administrator</a\>
to upgrade their service and re-enable user registration.
WebAuthenticationUserLimitNoticeHeader User registration disabled
WebAuthenticationUserLimitNoticeTitle User registration disabled
WebAuthenticationUserRegistrationDisabledNotice Registration of users has been disabled by the administrator.Please login with external identity provider.
WebAuthenticationUserRegistrationDisabledNoticeHeader User registration disabled
WebAuthenticationUserRegistrationDisabledNoticeTitle User registration disabled
WebAuthenticationSignupPendingConfirmationNotice Before we can complete the creation of your account we needto verify your e-mail address. We’ve sent an e-mail to {0}.Please follow the instructions inside the e-mail to activate youraccount. If the e-mail doesn’t arrive within the next fewminutes, please check your junk email folder.
WebAuthenticationSignupPendingConfirmationAccountFoundNotice
We found an unconfirmed account for the e-mail address {0}.To complete the creation of your account we need to verifyyour e-mail address. We’ve sent an e-mail to {0}. Please followthe instructions inside the e-mail to activate your account. Ifthe e-mail doesn’t arrive within the next few minutes, pleasecheck your junk email folder
WebAuthenticationSignupConfirmationAlmostDone Almost Done
WebAuthenticationSignupConfirmationEmailSent We’ve sent an e-mail to {0}. Please follow the instructionsinside the e-mail to activate your account. If the e-maildoesn’t arrive within the next few minutes, please check yourjunk email folder.
WebAuthenticationEmailSentNotificationMessage Email sent successfully to {0}
NAME TEX T
WebAuthenticationNoAadTenantConfigured No Azure Active Directory tenant configured for the service.
CheckboxLabelUserRegistrationTermsConsentRequired I agree to the <a data-toggle="modal" href="#" data-target="#terms"\>Terms of Use</a\>
.
TextblockUserRegistrationTermsProvided Please review <a data-toggle="modal" href="#" data-target="#terms"\>Terms of Use.</a\>
DialogHeadingTermsOfUse Terms of Use
ValidationMessageConsentNotAccepted You must agree to the Terms of Use before you can proceed.
NAME TEX T
SigninStringsSigninStrings
NAME TEX T
WebAuthenticationForgotPassword Forgot your password?
WebAuthenticationIfAdministrator If you are an Administrator you must sign in <a href="{0}"\>here</a\> .
WebAuthenticationNotAMember Not a member yet? <a href="/signup"\>Sign up now</a\>
WebAuthenticationRemember Remember me on this computer
WebAuthenticationSigininWithPassword Sign in with your username and password
WebAuthenticationSigninTitle Sign in
WebAuthenticationSignUpNow Sign up now
SignupStringsSignupStrings
NAME TEX T
PageTitleSignup Sign up
WebAuthenticationAlreadyAMember Already a member?
WebAuthenticationCreateNewAccount Create a new API Management account
WebAuthenticationSigninNow Sign in now
ButtonLabelSignup Sign up
SubscriptionListStringsSubscriptionListStrings
NAME TEX T
SubscriptionCancelConfirmation Are you sure that you want to cancel this subscription?
SubscriptionRenewConfirmation Are you sure that you want to renew this subscription?
WebDevelopersManageSubscriptions Manage subscriptions
WebDevelopersPrimaryKey Primary key
WebDevelopersRegenerateLink Regenerate
WebDevelopersSecondaryKey Secondary key
ButtonLabelShowKey Show
ButtonLabelRenewSubscription Renew
WebDevelopersSubscriptionReqested Requested on {0}
WebDevelopersSubscriptionRequestedState Requested
WebDevelopersSubscriptionTableNameHeader Name
WebDevelopersSubscriptionTableStateHeader State
WebDevelopersUsageStatisticsLink Analytics reports
WebDevelopersYourSubscriptions Your subscriptions
SubscriptionPropertyLabelRequestedDate Requested on
SubscriptionPropertyLabelStartedDate Started on
PageTitleRenameSubscription Rename subscription
SubscriptionPropertyLabelName Subscription name
SubscriptionStringsSubscriptionStrings
NAME TEX T
SectionHeadingCloseAccount Looking to close your account?
PageTitleDeveloperProfile Profile
ButtonLabelHideKey Hide
ButtonLabelRegenerateKey Regenerate
InformationMessageKeyWasRegenerated Are you sure that you want to regenerate this key?
ButtonLabelShowKey Show
NAME TEX T
UpdateProfileStringsUpdateProfileStrings
NAME TEX T
ButtonLabelUpdateProfile Update profile
PageTitleUpdateProfile Update account information
UserProfileUserProfile
NAME TEX T
ButtonLabelChangeAccountInfo Change account information
ButtonLabelChangePassword Change password
ButtonLabelCloseAccount Close account
TextboxLabelEmail Email
TextboxLabelEmailFirstName First name
TextboxLabelEmailLastName Last name
TextboxLabelNotificationsSenderEmail Notifications sender email
TextboxLabelOrganizationName Organization name
SubscriptionStateActive Active
SubscriptionStateCancelled Cancelled
SubscriptionStateExpired Expired
SubscriptionStateRejected Rejected
SubscriptionStateRequested Requested
SubscriptionStateSuspended Suspended
DefaultSubscriptionNameTemplate {0} (default)
SubscriptionNameTemplate Developer access #{0}
TextboxLabelSubscriptionName Subscription name
ValidationMessageSubscriptionNameRequired Subscription name cannot be empty.
ApiManagementUserLimitReached This service has reached the maximum number of allowedusers. Please upgrade to a higher pricing tier.
NAME TEX T
Glyph resources
<span class="glyphicon glyphicon-user">
Next steps
API Management developer portal templates can use the glyphs from Glyphicons from Bootstrap. This set ofglyphs includes over 250 glyphs in font format from the Glyphicon Halflings set. To use a glyph from this set, usethe following syntax.
For the complete list of glyphs, see Glyphicons from Bootstrap.
For more information about working with templates, see How to customize the API Management developer portalusing templates.
Azure API Management template data modelreference2/14/2018 • 12 min to read • Edit Online
API
PROPERTY TYPE DESCRIPTION
This topic describes the entity and type representations for common items used in the data models for thedeveloper portal templates in Azure API Management.
For more information about working with templates, see How to customize the API Management developer portalusing templates.
APIAPI summaryApplicationAttachmentCode sampleCommentFilteringHeaderHTTP RequestHTTP ResponseIssueOperationOperation menuOperation menu itemPagingParameterProductProviderRepresentationSubscriptionSubscription summaryUser account infoUser sign-inUser sign-up
The API entity has the following properties:
id string Resource identifier. Uniquely identifiesthe API within the current APIManagement service instance. Thevalue is a valid relative URL in theformat of apis/{id} where {id} isan API identifier. This property is read-only.
name string Name of the API. Must not be empty.Maximum length is 100 characters.
description string Description of the API. Must not beempty. May include HTML formattingtags. Maximum length is 1000characters.
serviceUrl string Absolute URL of the backend serviceimplementing this API.
path string Relative URL uniquely identifying thisAPI and all of its resource paths withinthe API Management service instance.It is appended to the API endpoint baseURL specified during the serviceinstance creation to form a public URLfor this API.
protocols array of number Describes on which protocols theoperations in this API can be invoked.Allowed values are 1 - http and 2 - https , or both.
authenticationSettings Authorization server authenticationsettings
Collection of authentication settingsincluded in this API.
subscriptionKeyParameterNames object Optional property that can be used tospecify custom names for query and/orheader parameters containing thesubscription key. When this property ispresent, it must contain at least one ofthe two following properties.
{"subscriptionKeyParameterNames":{ "query":“customQueryParameterName","header":“customHeaderParameterName" } }
PROPERTY TYPE DESCRIPTION
API summary
PROPERTY TYPE DESCRIPTION
The API summary entity has the following properties:
id string Resource identifier. Uniquely identifiesthe API within the current APIManagement service instance. Thevalue is a valid relative URL in theformat of apis/{id} where {id} isan API identifier. This property is read-only.
name string Name of the API. Must not be empty.Maximum length is 100 characters.
description string Description of the API. Must not beempty. May include HTML formattingtags. Maximum length is 1000characters.
PROPERTY TYPE DESCRIPTION
Application
PROPERTY TYPE DESCRIPTION
Id string The unique identifier of the application.
Title string The title of the application.
Description string The description of the application.
Url URI The URI for the application.
Version string Version information for the application.
Requirements string A description of requirements for theapplication.
State number The current state of the application.
- 0 - Registered
- 1 - Submitted
- 2 - Published
- 3 - Rejected
- 4 - Unpublished
RegistrationDate DateTime The date and time the application wasregistered.
CategoryId number The category of the application(Finance, entertainment, etc.)
The application entity has the following properties:
DeveloperId string The unique identifier of the developerthat submitted the application.
Attachments Collection of Attachment entities. Any attachments for the applicationsuch as screenshots or icons.
Icon Attachment The icon the for the application.
PROPERTY TYPE DESCRIPTION
Attachment
PROPERTY TYPE DESCRIPTION
UniqueId string The unique identifier for theattachment.
Url string The URL of the resource.
Type string The type of attachment.
ContentType string The media type of the attachment.
Code samplePROPERTY TYPE DESCRIPTION
title string The name of the operation.
snippet string This property is deprecated and shouldnot be used.
brush string Which code syntax coloring template tobe used when displaying the codesample. Allowed values are plain , php , java , xml , objc , python , ruby , and csharp .
template string The name of this code sample template.
body string A placeholder for the code sampleportion of the snippet.
method string The HTTP method of the operation.
scheme string The protocol to use for the operationrequest.
path string The path of the operation.
The attachment entity has the following properties:
query string Query string example with definedparameters.
host string The URL of the API Managementservice gateway for the API thatcontains this operation.
headers Collection of Header entities. Headers for this operation.
parameters Collection of Parameter entities. Parameters that are defined for thisoperation.
PROPERTY TYPE DESCRIPTION
Comment
PROPERTY TYPE DESCRIPTION
Id number The id of the comment.
CommentText string The body of the comment. May includeHTML.
DeveloperCompany string The company name of the developer.
PostedOn DateTime The date and time the comment wasposted.
Issue
PROPERTY TYPE DESCRIPTION
Id string The unique identifier for the issue.
ApiID string The id for the API for which this issuewas reported.
Title string Title of the issue.
Description string Description of the issue.
SubscriptionDeveloperName string First name of the developer thatreported the issue.
IssueState string The current state of the issue. Possiblevalues are Proposed, Opened, Closed.
ReportedOn DateTime The date and time the issue wasreported.
The API entity has the following properties:
The issue entity has the following properties.
Comments Collection of Comment entities. Comments on this issue.
Attachments Collection of Attachment entities. Any attachments to the issue.
Services Collection of API entities. The APIs subscribed to by the user thatfiled the issue.
PROPERTY TYPE DESCRIPTION
Filtering
PROPERTY TYPE DESCRIPTION
Pattern string The current search term; or null ifthere is no search term.
Placeholder string The text to display in the search boxwhen there is no search term specified.
Header
PROPERTY DESCRIPTION TYPE
name string Parameter name.
description string Parameter description.
value string Header value.
typeName string Data type of header value.
options string Options.
required boolean Whether the header is required.
readOnly boolean Whether the header is read-only.
HTTP Request
PROPERTY TYPE DESCRIPTION
description string Operation request description.
headers array of Header entities. Request headers.
The filtering entity has the following properties:
This section describes the parameter representation.
This section describes the request representation.
parameters array of Parameter Collection of operation requestparameters.
representations array of Representation Collection of operation requestrepresentations.
PROPERTY TYPE DESCRIPTION
HTTP Response
PROPERTY TYPE DESCRIPTION
statusCode positive integer Operation response status code.
description string Operation response description.
representations array of Representation Collection of operation responserepresentations.
Operation
PROPERTY TYPE DESCRIPTION
id string Resource identifier. Uniquely identifiesthe operation within the current APIManagement service instance. Thevalue is a valid relative URL in theformat of apis/{aid}/operations/{id} where {aid} is an API identifier and {id} is
an operation identifier. This property isread-only.
name string Name of the operation. Must not beempty. Maximum length is 100characters.
description string Description of the operation. Must notbe empty. May include HTMLformatting tags. Maximum length is1000 characters.
scheme string Describes on which protocols theoperations in this API can be invoked.Allowed values are http , https , orboth http and https .
uriTemplate string Relative URL template identifying thetarget resource for this operation. Mayinclude parameters. Example: customers/{cid}/orders/{oid}/?date={date}
This section describes the response representation.
The operation entity has the following properties:
host string The API Management gateway URL thathosts the API.
httpMethod string Operation HTTP method.
request HTTP Request An entity containing request details.
responses array of HTTP Response Array of operation HTTP Responseentities.
PROPERTY TYPE DESCRIPTION
Operation menu
PROPERTY TYPE DESCRIPTION
ApiId string The id of the current API.
CurrentOperationId string The id of the current operation.
Action string The menu type.
MenuItems Collection of Operation menu itementities.
The operations for the current API.
Operation menu item
PROPERTY TYPE DESCRIPTION
Id string The id of the operation.
Title string The description of the operation.
HttpMethod string The Http method of the operation.
Paging
PROPERTY TYPE DESCRIPTION
Page number The current page number.
PageSize number The maximum results to be displayedon a single page.
TotalItemCount number The number of items for display.
The operation menu entity has the following properties:
The operation menu item entity has the following properties:
The paging entity has the following properties:
ShowAll boolean Whether to sho all results on a singlepage.
PageCount number The number of pages of results.
PROPERTY TYPE DESCRIPTION
Parameter
PROPERTY DESCRIPTION TYPE
name string Parameter name.
description string Parameter description.
value string Parameter value.
options array of string Values defined for query parametervalues.
required boolean Specifies whether parameter is requiredor not.
kind number Whether this parameter is a pathparameter (1), or a querystringparameter (2).
typeName string Parameter type.
Product
PROPERTY TYPE DESCRIPTION
Id string Resource identifier. Uniquely identifiesthe product within the current APIManagement service instance. Thevalue is a valid relative URL in theformat of products/{pid} where {pid} is a product identifier. This
property is read-only.
Title string Name of the product. Must not beempty. Maximum length is 100characters.
Description string Description of the product. Must not beempty. May include HTML formattingtags. Maximum length is 1000characters.
This section describes the parameter representation.
The product entity has the following properties:
Terms string Product terms of use. Developers tryingto subscribe to the product will bepresented and required to accept theseterms before they can complete thesubscription process.
ProductState number Specifies whether the product ispublished or not. Published productsare discoverable by developers on thedeveloper portal. Non-publishedproducts are visible only toadministrators.
The allowable values for product stateare:
- 0 - Not Published
- 1 - Published
- 2 - Deleted
AllowMultipleSubscriptions boolean Specifies whether a user can havemultiple subscriptions to this product atthe same time.
MultipleSubscriptionsCount number Maximum number of subscriptions tothis product a user is allowed to have atthe same time.
PROPERTY TYPE DESCRIPTION
Provider
PROPERTY TYPE DESCRIPTION
Properties string dictionary Properties for this authenticationprovider.
AuthenticationType string The provider type. (Azure ActiveDirectory, Facebook login, GoogleAccount, Microsoft Account, Twitter).
Caption string Display name of the provider.
Representation
PROPERTY TYPE DESCRIPTION
contentType string Specifies a registered or custom contenttype for this representation, forexample, application/xml .
The provider entity has the following properties:
This section describes a representation .
sample string An example of the representation.
PROPERTY TYPE DESCRIPTION
Subscription
PROPERTY TYPE DESCRIPTION
Id string Resource identifier. Uniquely identifiesthe subscription within the current APIManagement service instance. Thevalue is a valid relative URL in theformat of subscriptions/{sid}
where {sid} is a subscriptionidentifier. This property is read-only.
ProductId string The product resource identifier of thesubscribed product. The value is a validrelative URL in the format of products/{pid} where {pid} is a
product identifier.
ProductTitle string Name of the product. Must not beempty. Maximum length is 100characters.
ProductDescription string Description of the product. Must not beempty. May include HTML formattingtags. Maximum length is 1000characters.
ProductDetailsUrl string Relative URL to the product details.
The subscription entity has the following properties:
state string The state of the subscription. Possiblestates are:
- 0 - suspended – the subscription isblocked, and the subscriber cannot callany APIs of the product.
- 1 - active – the subscription isactive.
- 2 - expired – the subscriptionreached its expiration date and wasdeactivated.
- 3 - submitted – the subscriptionrequest has been made by thedeveloper, but has not yet beenapproved or rejected.
- 4 - rejected – the subscriptionrequest has been denied by anadministrator.
- 5 - cancelled – the subscriptionhas been canceled by the developer oradministrator.
DisplayName string Display name of the subscription.
CreatedDate dateTime The date the subscription was created,in ISO 8601 format: 2014-06-24T16:25:00Z .
CanBeCancelled boolean Whether the subscription can becanceled by the current user.
IsAwaitingApproval boolean Whether the subscription is awaitingapproval.
StartDate dateTime The start date for the subscription, inISO 8601 format: 2014-06-24T16:25:00Z .
ExpirationDate dateTime The expiration date for the subscription,in ISO 8601 format: 2014-06-24T16:25:00Z .
NotificationDate dateTime The notification date for thesubscription, in ISO 8601 format: 2014-06-24T16:25:00Z .
primaryKey string The primary subscription key. Maximumlength is 256 characters.
secondaryKey string The secondary subscription key.Maximum length is 256 characters.
PROPERTY TYPE DESCRIPTION
CanBeRenewed boolean Whether the subscription can berenewed by the current user.
HasExpired boolean Whether the subscription has expired.
IsRejected boolean Whether the subscription request wasdenied.
CancelUrl string The relative Url to cancel thesubscription.
RenewUrl string The relative Url to renew thesubscription.
PROPERTY TYPE DESCRIPTION
Subscription summary
PROPERTY TYPE DESCRIPTION
Id string Resource identifier. Uniquely identifiesthe subscription within the current APIManagement service instance. Thevalue is a valid relative URL in theformat of subscriptions/{sid}
where {sid} is a subscriptionidentifier. This property is read-only.
DisplayName string The display name of the subscription
User account info
PROPERTY TYPE DESCRIPTION
FirstName string First name. Must not be empty.Maximum length is 100 characters.
LastName string Last name. Must not be empty.Maximum length is 100 characters.
Email string Email address. Must not be empty andmust be unique within the serviceinstance. Maximum length is 254characters.
Password string User account password.
NameIdentifier string Account identifier, the same as the useremail.
The subscription summary entity has the following properties:
The user account info entity has the following properties:
ProviderName string Authentication provider name.
IsBasicAccount boolean True if this account was registered usingemail and password; false if the accountwas registered using a provider.
PROPERTY TYPE DESCRIPTION
User sign in
PROPERTY TYPE DESCRIPTION
Email string Email address. Must not be empty andmust be unique within the serviceinstance. Maximum length is 254characters.
Password string User account password.
ReturnUrl string The URL of the page where the userclicked sign in.
RememberMe boolean Whether to save the current user'sinformation.
RegistrationEnabled boolean Whether registration is enabled.
DelegationEnabled boolean Whether delegated sign in is enabled.
DelegationUrl string The delegated sign in url, if enabled.
SsoSignUpUrl string The single sign on URL for the user, ifpresent.
AuxServiceUrl string If the current user is an administrator,this is a link to the service instance inthe Azure portal.
Providers Collection of Provider entities The authentication providers for thisuser.
UserRegistrationTerms string Terms that a user must agree to beforesigning in.
UserRegistrationTermsEnabled boolean Whether terms are enabled.
User sign up
The user sign in entity has the following properties:
The user sign up entity has the following properties:
PROPERTY TYPE DESCRIPTION
PasswordConfirm boolean Value used by the sign-upsign-upcontrol.
Password string User account password.
PasswordVerdictLevel number Value used by the sign-upsign-upcontrol.
UserRegistrationTerms string Terms that a user must agree to beforesigning in.
UserRegistrationTermsOptions number Value used by the sign-upsign-upcontrol.
ConsentAccepted boolean Value used by the sign-upsign-upcontrol.
Email string Email address. Must not be empty andmust be unique within the serviceinstance. Maximum length is 254characters.
FirstName string First name. Must not be empty.Maximum length is 100 characters.
LastName string Last name. Must not be empty.Maximum length is 100 characters.
UserData string Value used by the sign-up control.
NameIdentifier string Value used by the sign-upsign-upcontrol.
ProviderName string Authentication provider name.
Next stepsFor more information about working with templates, see How to customize the API Management developer portalusing templates.
Azure API Management page controls12/4/2017 • 2 min to read • Edit Online
<app-actions params="{ appId: '{{app.id}}' }"></app-actions>
Developer portal template page controls
app-actions
UsageUsage
<app-actions params="{ appId: '{{app.id}}' }"></app-actions>
ParametersParameters
Azure API Management provides the following controls for use in the developer portal templates.
To use a control, place it in the desired location in the developer portal template. Some controls, such as theapp-actions control, have parameters, as shown in the following example:
The values for the parameters are passed in as part of the data model for the template. In most cases, youcan simply paste in the provided example for each control for it to work correctly. For more information onthe parameter values, you can see the data model section for each template in which a control may be used.
For more information about working with templates, see How to customize the API Managementdeveloper portal using templates.
app-actionsbasic-signinpaging-controlproviderssearch-controlsign-upsubscribe-buttonsubscription-cancel
The app-actions control provides a user interface for interacting with applications on the user profile pagein the developer portal.
PARAMETER DESCRIPTION
appId The id of the application.
Developer portal templatesDeveloper portal templates
basic-signin
UsageUsage
<basic-SignIn></basic-SignIn>
ParametersParameters
Developer portal templatesDeveloper portal templates
paging-control
The app-actions control may be used in the following developer portal templates:
Applications
The basic-signin control provides a control for collecting user sign-in information in the sign-in page inthe developer portal.
None.
The basic-signin control may be used in the following developer portal templates:
Sign in
The paging-control provides paging functionality on developer portal pages that display a list of items.
UsageUsage
<paging-control></paging-control>
ParametersParameters
Developer portal templatesDeveloper portal templates
providers
UsageUsage
<providers></providers>
ParametersParameters
Developer portal templatesDeveloper portal templates
search-control
None.
The paging-control control may be used in the following developer portal templates:
API list
Issue list
Product list
The providers control provides a control for selection of authentication providers in the sign-in page inthe developer portal.
None.
The providers control may be used in the following developer portal templates:
Sign in
UsageUsage
<search-control></search-control>
ParametersParameters
Developer portal templatesDeveloper portal templates
sign-up
The search-control provides search functionality on developer portal pages that display a list of items.
None.
The search-control control may be used in the following developer portal templates:
API list
Product list
The sign-up control provides a control for collecting user profile information in the sign-up page in thedeveloper portal.
UsageUsage
<sign-up></sign-up>
ParametersParameters
Developer portal templatesDeveloper portal templates
subscribe-button
None.
The sign-up control may be used in the following developer portal templates:
Sign up
The subscribe-button provides a control for subscribing a user to a product.
UsageUsage
<subscribe-button></subscribe-button>
ParametersParameters
Developer portal templatesDeveloper portal templates
subscription-cancel
UsageUsage
<subscription-cancel params="{ subscriptionId: '{{subscription.id}}', cancelUrl: '{{subscription.cancelUrl}}' }"> </subscription-cancel>
ParametersParameters
PARAMETER DESCRIPTION
subscriptionId The id of the subscription to cancel.
cancelUrl The subscription cancels URL.
Developer portal templatesDeveloper portal templates
Next steps
None.
The subscribe-button control may be used in the following developer portal templates:
Product
The subscription-cancel control provides a control for canceling a subscription to a product in the userprofile page in the developer portal.
The subscription-cancel control may be used in the following developer portal templates:
Product
For more information about working with templates, see How to customize the API Managementdeveloper portal using templates.
How to create and use groups to manage developeraccounts in Azure API Management4/9/2018 • 3 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
In API Management, groups are used to manage the visibility of products to developers. Products are first madevisible to groups, and then developers in those groups can view and subscribe to the products that are associatedwith the groups.
API Management has the following immutable system groups:
Administrators - Azure subscription administrators are members of this group. Administrators manage APIManagement service instances, creating the APIs, operations, and products that are used by developers.Developers - Authenticated developer portal users fall into this group. Developers are the customers thatbuild applications using your APIs. Developers are granted access to the developer portal and buildapplications that call the operations of an API.Guests - Unauthenticated developer portal users, such as prospective customers visiting the developer portalof an API Management instance fall into this group. They can be granted certain read-only access, such as theability to view APIs but not call them.
In addition to these system groups, administrators can create custom groups or leverage external groups inassociated Azure Active Directory tenants. Custom and external groups can be used alongside system groups ingiving developers visibility and access to API products. For example, you could create one custom group fordevelopers affiliated with a specific partner organization and allow them access to the APIs from a productcontaining relevant APIs only. A user can be a member of more than one group.
This guide shows how administrators of an API Management instance can add new groups and associate themwith products and developers.
In addition to creating and managing groups in the publisher portal, you can create and manage your groupsusing the API Management REST API Group entity.
Complete tasks in this article: Create an Azure API Management instance.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
TIPTIP
Create a group
Associate a group with a product
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
This section shows how to add a new group to your API Management account.
1. Select the Groups tab to the left of the screen.2. Click +Add.3. Enter a unique name for the group and an optional description.4. Press Create.
Once the group is created, it is added to the Groups list. To edit the Name or Description of the group, click the name of the group and Settings.To delete the group, click the name of the group and press Delete.
Now that the group is created, it can be associated with products and developers.
1. Select the Products tab to the left.2. Click the name of the desired product.
NOTENOTE
Associate groups with developers
3. Press Access control.4. Click + Add group.
5. Select the group you want to add.
To remove a group from the product, click Delete.
Once a product is associated with a group, developers in that group can view and subscribe to the product.
To add Azure Active Directory groups, see How to authorize developer accounts using Azure Active Directory in Azure APIManagement.
This section shows how to associate groups with members.
1. Select the Groups tab to the left of the screen.2. Select Members.
Next steps
4. Press Select.
3. Press +Add and select a member.
Once the association is added between the developer and the group, you can view it in the Users tab.
Once a developer is added to a group, they can view and subscribe to the products associated with that group.For more information, see How create and publish a product in Azure API Management,In addition to creating and managing groups in the publisher portal, you can create and manage your groupsusing the API Management REST API Group entity.
How to deploy an Azure API Management serviceinstance to multiple Azure regions2/5/2018 • 1 min to read • Edit Online
IMPORTANTIMPORTANT
Deploy an API Management service instance to a new region
NOTENOTE
API Management supports multi-region deployment which enables API publishers to distribute a single APImanagement service across any number of desired Azure regions. This helps reduce request latency perceived bygeographically distributed API consumers and also improves service availability if one region goes offline.
When an API Management service is created initially, it contains only one unit and resides in a single Azureregion, which is designated as the Primary Region. Additional regions can be easily added through the AzurePortal. An API Management gateway server is deployed to each region and call traffic will be routed to the closestgateway. If a region goes offline, the traffic is automatically re-directed to the next closest gateway.
Multi-region deployment is only available in the Premium tier.
If you have not yet created an API Management service instance, see Create an API Management service instance.
In the Azure Portal navigate to the Scale and pricing page for your API Management service instance.
To deploy to a new region, click on + Add region from the toolbar.
Select the location from the drop-down list and set the number of units for with the slider.
Delete an API Management service instance from a location
Click Add to place your selection in the Locations table.
Repeat this process until you have all locations configured and click Save from the toolbar to start the deploymentprocess.
In the Azure Portal navigate to the Scale and pricing page for your API Management service instance.
For the location you would like to remove open the context menu using the ... button at the right end of the table.Select the Delete option.
Confirm the deletion and click Save to apply the changes.
How to log events to Azure Event Hubs in Azure APIManagement3/16/2018 • 3 min to read • Edit Online
Create an Azure Event Hub
Create an API Management logger
{ "loggerType" : "AzureEventHub", "description" : "Sample logger description", "credentials" : { "name" : "Name of the Event Hub from the Azure Classic Portal", "connectionString" : "Endpoint=Event Hub Sender connection string" }}
Azure Event Hubs is a highly scalable data ingress service that can ingest millions of events per second so that youcan process and analyze the massive amounts of data produced by your connected devices and applications. EventHubs acts as the "front door" for an event pipeline, and once data is collected into an event hub, it can betransformed and stored using any real-time analytics provider or batching/storage adapters. Event Hubsdecouples the production of a stream of events from the consumption of those events, so that event consumerscan access the events on their own schedule.
This article is a companion to the Integrate Azure API Management with Event Hubs video and describes how tolog API Management events using Azure Event Hubs.
For detailed steps on how to create an event hub and get connection strings that you need to send and receiveevents to and from the Event Hub, see Create an Event Hubs namespace and an event hub using the Azure portal.
Now that you have an Event Hub, the next step is to configure a Logger in your API Management service so that itcan log events to the Event Hub.
API Management loggers are configured using the API Management REST API. Before using the REST API forthe first time, review the prerequisites and ensure that you have enabled access to the REST API.
To create a logger, make an HTTP PUT request using the following URL template:
https://{your service}.management.azure-api.net/loggers/{new logger name}?api-version=2017-03-01
Replace {your service} with the name of your API Management service instance.Replace {new logger name} with the desired name for your new logger. You reference this name when youconfigure the log-to-eventhub policy
Add the following headers to the request:
Content-Type : application/jsonAuthorization : SharedAccessSignature 58...
For instructions on generating the SharedAccessSignature see Azure API Management REST APIAuthentication.
Specify the request body using the following template:
NOTENOTE
Configure log-to-eventhubs policies
<log-to-eventhub logger-id ='logger-id'> @( string.Join(",", DateTime.UtcNow, context.Deployment.ServiceName, context.RequestId, context.Request.IpAddress, context.Operation.Name))</log-to-eventhub>
Next steps
loggerType must be set to AzureEventHub .description provides an optional description of the logger and can be a zero length string if desired.credentials contains the name and connectionString of your Azure Event Hub.
When you make the request, if the logger is created a status code of 201 Created is returned.
For other possible return codes and their reasons, see Create a Logger. To see how to perform other operations such as list,update, and delete, see the Logger entity documentation.
Once your logger is configured in API Management, you can configure your log-to-eventhubs policies to log thedesired events. The log-to-eventhubs policy can be used in either the inbound policy section or the outboundpolicy section.
1. Browse to your APIM instance.2. Select the API tab.3. Select the API to which you want to add the policy. In this example, we're adding a policy to the Echo API in
the Unlimited product.4. Select All operations.5. On the top of the screen, select the Design tab.6. In the Inbound or Outbound processing window, click the triangle (next to the pencil).7. Select the Code editor. For more information, see How to set or edit policies.8. Position your cursor in the inbound or outbound policy section.9. In the window on the right, select Advanced policies > Log to EventHub. This inserts the log-to-eventhub
policy statement template.
Replace logger-id with the name of the API Management logger you configured in the previous step.
You can use any expression that returns a string as the value for the log-to-eventhub element. In this example, astring containing the date and time, service name, request id, request ip address, and operation name is logged.
Click Save to save the updated policy configuration. As soon as it is saved the policy is active and events arelogged to the designated Event Hub.
Learn more about Azure Event Hubs
Learn more about API Management and Event Hubs integration
Get started with Azure Event HubsReceive messages with EventProcessorHostEvent Hubs programming guide
Logger entity referencelog-to-eventhub policy reference
Monitor your APIs with Azure API Management, Event Hubs, and Runscope
How to implement disaster recovery using service backup and restore inAzure API Management1/24/2018 • 6 min to read • Edit Online
NOTENOTE
Authenticating Azure Resource Manager requests
IMPORTANTIMPORTANT
Create an Azure Active Directory applicationCreate an Azure Active Directory application
Add an applicationAdd an application
By choosing to publish and manage your APIs via Azure API Management you are taking advantage of many fault tolerance and infrastructurecapabilities that you would otherwise have to design, implement, and manage. The Azure platform mitigates a large fraction of potential failures at afraction of the cost.
To recover from availability problems affecting the region where your API Management service is hosted, you should be ready to reconstitute yourservice in a different region at any time. Depending on your availability goals and recovery time objective, you might want to reserve a backup servicein one or more regions and try to maintain their configuration and content in sync with the active service. The service "backup and restore" featureprovides the necessary building block for implementing your disaster recovery strategy.
This guide shows how to authenticate Azure Resource Manager requests, and how to back up and restore your API Management service instances.
The process for backing up and restoring an API Management service instance for disaster recovery can also be used for replicating API Management serviceinstances for scenarios such as staging.
Each backup expires after 30 days. If you attempt to restore a backup after the 30-day expiration period has expired, the restore will fail with a Cannot restore: backup expired message.
The REST API for backup and restore uses Azure Resource Manager and has a different authentication mechanism than the REST APIs for managing your APIManagement entities. The steps in this section describe how to authenticate Azure Resource Manager requests. For more information, see Authenticating AzureResource Manager requests.
All of the tasks that you do on resources using the Azure Resource Manager must be authenticated with Azure Active Directory using the followingsteps:
Add an application to the Azure Active Directory tenant.Set permissions for the application that you added.Get the token for authenticating requests to Azure Resource Manager.
1. Sign in to the Azure portal.
NOTENOTE
4. Enter a name for the application.5. For the application type, select Native.6. Enter a placeholder URL such as http://resources for the Redirect URI, as it is a required field, but the value is not used later. Click the check box
to save the application.7. Click Create.
2. Using the subscription that contains your API Management service instance, navigate to the App registrations tab.
If the Azure Active Directory default directory is not visible to your account, contact the administrator of the Azure subscription to grant the requiredpermissions to your account.
3. Click New application registration.
The Create window appears on the right. That is where you enter the AAD app relevant information.
1. Once the application is created, click Settings.2. Click Required permissions.3. Click +Add.4. Press Select an API.5. Choose Windows Azure Service Management API.6. Press Select.
Configuring your appConfiguring your app
using Microsoft.IdentityModel.Clients.ActiveDirectory;using System;
namespace GetTokenResourceManagerRequests{ class Program { static void Main(string[] args) { var authenticationContext = new AuthenticationContext("https://login.microsoftonline.com/{tenant id}"); var result = authenticationContext.AcquireToken("https://management.azure.com/", {application id}, new Uri({redirect uri});
if (result == null) { throw new InvalidOperationException("Failed to obtain the JWT token"); }
Console.WriteLine(result.AccessToken);
Console.ReadLine(); } }}
8. Press Select.
7. Click Delegated Permissions beside the newly added application, check the box for Access Azure Service Management (preview).
Prior to invoking the APIs that generate the backup and restore it, it is necessary to get a token. The following example uses theMicrosoft.IdentityModel.Clients.ActiveDirectory NuGet package to retrieve the token.
Replace {tentand id} , {application id} , and {redirect uri} using the following instructions:
1. Replace {tenant id} with the tenant id of the Azure Active Directory application you created. You can access the id by clicking Appregistrations -> Endpoints.
Calling the backup and restore operations
request.Headers.Add(HttpRequestHeader.Authorization, "Bearer " + token);
Back up an API Management serviceBack up an API Management service
2. Replace {application id} with the value you get by navigating to the Settings page.3. Replace the URL from the Redirect URIs tab is your Azure Active Directory application.
Once the values are specified, the code example should return a token similar to the following example:
Before calling the "backup and restore" operations described in the following sections, set the authorization request header for your REST call.
To back up an API Management service issue the following HTTP request:
POSThttps://management.azure.com/subscriptions/{subscriptionId}/resourceGroups/{resourceGroupName}/providers/Microsoft.ApiManagement/service/{serviceName}/backup?api-version={api-version}
where:
subscriptionId - id of the subscription containing the API Management service you are attempting to back upresourceGroupName - a string in the form of 'Api-Default-{service-region}' where service-region identifies the Azure region where the API
Management service you are trying to backup is hosted, for example, North-Central-US
serviceName - the name of the API Management service you are making a backup of specified at the time of its creationapi-version - replace with 2014-02-14
'{ storageAccount : {storage account name for the backup}, accessKey : {access key for the account}, containerName : {backup container name}, backupName : {backup blob name} }'
Restore an API Management serviceRestore an API Management service
'{ storageAccount : {storage account name for the backup}, accessKey : {access key for the account}, containerName : {backup container name}, backupName : {backup blob name} }'
IMPORTANTIMPORTANT
Next steps
In the body of the request, specify the target Azure storage account name, access key, blob container name, and backup name:
Set the value of the Content-Type request header to application/json .
Backup is a long running operation that may take multiple minutes to complete. If the request was successful and the backup process was initiated,you receive a 202 Accepted response status code with a Location header. Make 'GET' requests to the URL in the Location header to find out thestatus of the operation. While the backup is in progress, you continue to receive a '202 Accepted' status code. A Response code of 200 OK indicatessuccessful completion of the backup operation.
Note the following constraints when making a backup request.
Container specified in the request body must exist.While backup is in progress you should not attempt any service management operations such as SKU upgrade or downgrade, domain namechange, etc.Restore of a backup is guaranteed only for 30 days since the moment of its creation.Usage data used for creating analytics reports is not included in the backup. Use Azure API Management REST API to periodically retrieveanalytics reports for safekeeping.The frequency with which you perform service backups affect your recovery point objective. To minimize it, the recommendation is implementingregular backups as well as performing on-demand backups after making important changes to your API Management service.Changes made to the service configuration (for example, APIs, policies, developer portal appearance) while backup operation is in process mightnot be included in the backup and therefore will be lost.
To restore an API Management service from a previously created backup make the following HTTP request:
POSThttps://management.azure.com/subscriptions/{subscriptionId}/resourceGroups/{resourceGroupName}/providers/Microsoft.ApiManagement/service/{serviceName}/restore?api-version={api-version}
where:
subscriptionId - id of the subscription containing the API Management service you are restoring a backup intoresourceGroupName - a string in the form of 'Api-Default-{service-region}' where service-region identifies the Azure region where the API
Management service you are restoring a backup into is hosted, for example, North-Central-US
serviceName - the name of the API Management service being restored into specified at the time of its creationapi-version - replace with 2014-02-14
In the body of the request, specify the backup file location, that is, Azure storage account name, access key, blob container name, and backup name:
Set the value of the Content-Type request header to application/json .
Restore is a long running operation that may take up to 30 or more minutes to complete. If the request was successful and the restore process wasinitiated, you receive a 202 Accepted response status code with a Location header. Make 'GET' requests to the URL in the Location header to findout the status of the operation. While the restore is in progress, you continue to receive '202 Accepted' status code. A response code of 200 OK
indicates successful completion of the restore operation.
The SKU of the service being restored into must match the SKU of the backed-up service being restored.
Changes made to the service configuration (for example, APIs, policies, developer portal appearance) while restore operation is in progress could be overwritten.
Check out the following Microsoft blogs for two different walkthroughs of the backup/restore process.
Replicate Azure API Management AccountsAzure API Management: Backing Up and Restoring Configuration
The approach detailed by Stuart does not match the official guidance but it is interesting.
How to manage user accounts in Azure APIManagement2/14/2018 • 2 min to read • Edit Online
Prerequisites
Navigate to your APIM instance
TIPTIP
Create a new developer
In API Management, developers are the users of the APIs that you expose using API Management. This guideshows to how to create and invite developers to use the APIs and products that you make available to them withyour API Management instance. For information on managing user accounts programmatically, see the User entitydocumentation in the API Management REST reference.
Complete tasks in this article: Create an Azure API Management instance.
To navigate to your APIM instance, follow these steps:
1. Sign in to the Azure portal.2. On the top-left of the screen, select All services.3. Type "api" in the search box.4. Click API Management services.
5. Select your APIM service instance.
Add API Management (APIM) to your favorites in the Azure portal by clicking the star. This adds the APIM icon to the menu on the left of the portal. To see all your APIM services, click the icon ( ).
To add a new user, follow the steps in this section:
1. Select the Users tab to the left of the screen.2. Press +Add.3. Enter appropriate information for the user.
Invite a developer
Deactivate or reactivate a developer account
Reset a user password
4. Press Add.
By default, newly created developer accounts are Active, and associated with the Developers group. Developeraccounts that are in an active state can be used to access all of the APIs for which they have subscriptions. Toassociate the newly created developer with additional groups, see How to associate groups with developers.
To invite a developer, follow the steps in this section:
1. Select the Users tab to the left of the screen.2. Press +Invite.
A confirmation message is displayed, but the newly invited developer does not appear in the list until after theyaccept the invitation.
When a developer is invited, an email is sent to the developer. This email is generated using a template and iscustomizable. For more information, see Configure email templates.
Once the invitation is accepted, the account becomes active.
By default, newly created or invited developer accounts are Active. To deactivate a developer account, click Block.To reactivate a blocked developer account, click Activate. A blocked developer account can't access the developerportal or call any APIs. To delete a user account, click Delete.
To block a user, follow the following steps.
1. Select the Users tab to the left of the screen.2. Click on the user that you want to block.3. Press Block.
To programmatically work with user accounts, see the User entity documentation in the API Management RESTreference. To reset a user account password to a specific value, you can use the Update a user operation andspecify the desired password.
Next stepsOnce a developer account is created, you can associate it with roles and subscribe it to products and APIs. Formore information, see How to create and use groups.
How to save and configure your API Managementservice configuration using Git2/6/2018 • 9 min to read • Edit Online
Each API Management service instance maintains a configuration database that contains information about theconfiguration and metadata for the service instance. Changes can be made to the service instance by changing asetting in the Azure portal, using a PowerShell cmdlet, or making a REST API call. In addition to these methods,you can also manage your service instance configuration using Git, enabling service management scenarios suchas:
Configuration versioning - download and store different versions of your service configurationBulk configuration changes - make changes to multiple parts of your service configuration in your localrepository and integrate the changes back to the server with a single operationFamiliar Git toolchain and workflow - use the Git tooling and workflows that you are already familiar with
The following diagram shows an overview of the different ways to configure your API Management serviceinstance.
When you make changes to your service using the Azure portal, PowerShell cmdlets, or the REST API, you aremanaging your service configuration database using the https://{name}.management.azure-api.net endpoint, asshown on the right side of the diagram. The left side of the diagram illustrates how you can manage your serviceconfiguration using Git and Git repository for your service located at https://{name}.scm.azure-api.net .
Access Git configuration in your service
IMPORTANTIMPORTANT
To save the service configuration to the Git repository
The following steps provide an overview of managing your API Management service instance using Git.
1. Access Git configuration in your service2. Save your service configuration database to your Git repository3. Clone the Git repo to your local machine4. Pull the latest repo down to your local machine, and commit and push changes back to your repo5. Deploy the changes from your repo into your service configuration database
This article describes how to enable and use Git to manage your service configuration and provides a reference forthe files and folders in the Git repository.
To view and configure your Git configuration settings, you can click the Security menu and navigate to theConfiguration repository tab.
Any secrets that are not defined as properties will be stored in the repository and will remain in its history until you disableand re-enable Git access. Properties provide a secure place to manage constant string values, including secrets, across all APIconfiguration and policies, so you don't have to store them directly in your policy statements. For more information, see Howto use properties in Azure API Management policies.
For information on enabling or disabling Git access using the REST API, see Enable or disable Git access using theREST API.
The first step before cloning the repository is to save the current state of the service configuration to therepository. Click Save to repository.
Make any desired changes on the confirmation screen and click Ok to save.
After a few moments the configuration is saved, and the configuration status of the repository is displayed,including the date and time of the last configuration change and the last synchronization between the serviceconfiguration and the repository.
Once the configuration is saved to the repository, it can be cloned.
To clone the repository to your local machine
IMPORTANTIMPORTANT
git clone https://bugbashdev4.scm.azure-api.net/
git clone https://username:[email protected]/
?System.NetWebUtility.UrlEncode("password from the Azure portal")
git clone https://username:url encoded [email protected]/
To update your local repository with the most current service instanceconfiguration
For information on performing this operation using the REST API, see Commit configuration snapshot using theREST API.
To clone a repository, you need the URL to your repository, a user name, and a password. To get user name andother credentials, click on Access credentials near the top of the page.
To generate a password, first ensure that the Expiry is set to the desired expiration date and time, and then clickGenerate.
Make a note of this password. Once you leave this page the password will not be displayed again.
The following examples use the Git Bash tool from Git for Windows but you can use any Git tool that you arefamiliar with.
Open your Git tool in the desired folder and run the following command to clone the git repository to your localmachine, using the command provided by the Azure portal.
Provide the user name and password when prompted.
If you receive any errors, try modifying your git clone command to include the user name and password, asshown in the following example.
If this provides an error, try URL encoding the password portion of the command. One quick way to do this is toopen Visual Studio, and issue the following command in the Immediate Window. To open the ImmediateWindow, open any solution or project in Visual Studio (or create a new empty console application), and chooseWindows, Immediate from the Debug menu.
Use the encoded password along with your user name and repository location to construct the git command.
Once the repository is cloned you can view and work with it in your local file system. For more information, seeFile and folder structure reference of local Git repository.
If you make changes to your API Management service instance in the Azure portal or using the REST API, youmust save these changes to the repository before you can update your local repository with the latest changes. Todo this, click Save configuration to repository on the Configuration repository tab in the Azure portal, andthen issue the following command in your local repository.
git pull
cd bugbashdev4.scm.azure-api.net/
To push changes from your local repo to the server repo
git add --allgit commit -m "Description of your changes"
git push
To deploy any service configuration changes to the API Managementservice instance
File and folder structure reference of local Git repository
ITEM DESCRIPTION
root api-management folder Contains top-level configuration for the service instance
apis folder Contains the configuration for the apis in the service instance
groups folder Contains the configuration for the groups in the serviceinstance
policies folder Contains the policies in the service instance
portalStyles folder Contains the configuration for the developer portalcustomizations in the service instance
products folder Contains the configuration for the products in the serviceinstance
Before running git pull ensure that you are in the folder for your local repository. If you have just completed the git clone command, then you must change the directory to your repo by running a command like the following.
To push changes from your local repository to the server repository, you must commit your changes and thenpush them to the server repository. To commit your changes, open your Git command tool, switch to the directoryof your local repository, and issue the following commands.
To push all of the commits to the server, run the following command.
Once your local changes are committed and pushed to the server repository, you can deploy them to your APIManagement service instance.
For information on performing this operation using the REST API, see Deploy Git changes to configurationdatabase using the REST API.
The files and folders in the local git repository contain the configuration information about the service instance.
templates folder Contains the configuration for the email templates in theservice instance
ITEM DESCRIPTION
FILE TYPE PURPOSE
json Configuration information about the respective entity
html Descriptions about the entity, often displayed in the developerportal
xml Policy statements
css Style sheets for developer portal customization
NOTENOTE
Root api-management folderRoot api-management folder
{ "settings": { "RegistrationEnabled": "True", "UserRegistrationTerms": null, "UserRegistrationTermsEnabled": "False", "UserRegistrationTermsConsentRequired": "False", "DelegationEnabled": "False", "DelegationUrl": "", "DelegatedSubscriptionEnabled": "False", "DelegationValidationKey": "" }, "$ref-policy": "api-management/policies/global.xml"}
IDENTITY SETTING MAPS TO
RegistrationEnabled Redirect anonymous users to sign-in page checkbox
Each folder can contain one or more files, and in some cases one or more folders, for example a folder for eachAPI, product, or group. The files within each folder are specific for the entity type described by the folder name.
These files can be created, deleted, edited, and managed on your local file system, and the changes deployed backto the your API Management service instance.
The following entities are not contained in the Git repository and cannot be configured using Git.
UsersSubscriptionsPropertiesDeveloper portal entities other than styles
The root api-management folder contains a configuration.json file that contains top-level information about theservice instance in the following format.
The first four settings ( RegistrationEnabled , UserRegistrationTerms , UserRegistrationTermsEnabled , and UserRegistrationTermsConsentRequired ) map to the following settings on the Identities tab in the Security section.
UserRegistrationTerms Terms of use on user signup textbox
UserRegistrationTermsEnabled Show terms of use on signup page checkbox
UserRegistrationTermsConsentRequired Require consent checkbox
IDENTITY SETTING MAPS TO
DELEGATION SETTING MAPS TO
DelegationEnabled Delegate sign-in & sign-up checkbox
DelegationUrl Delegation endpoint URL textbox
DelegatedSubscriptionEnabled Delegate product subscription checkbox
DelegationValidationKey Delegate Validation Key textbox
apis folderapis folder
groups foldergroups folder
policies folderpolicies folder
The next four settings ( DelegationEnabled , DelegationUrl , DelegatedSubscriptionEnabled , and DelegationValidationKey ) map to the following settings on the Delegation tab in the Security section.
The final setting, $ref-policy , maps to the global policy statements file for the service instance.
The apis folder contains a folder for each API in the service instance which contains the following items.
apis\<api name>\configuration.json - this is the configuration for the API and contains information about thebackend service URL and the operations. This is the same information that would be returned if you were to callGet a specific API with export=true in application/json format.apis\<api name>\api.description.html - this is the description of the API and corresponds to the description
property of the API entity.apis\<api name>\operations\ - this folder contains <operation name>.description.html files that map to the
operations in the API. Each file contains the description of a single operation in the API which maps to the description property of the operation entity in the REST API.
The groups folder contains a folder for each group defined in the service instance.
groups\<group name>\configuration.json - this is the configuration for the group. This is the same informationthat would be returned if you were to call the Get a specific group operation.groups\<group name>\description.html - this is the description of the group and corresponds to the description
property of the group entity.
The policies folder contains the policy statements for your service instance.
policies\global.xml - contains policies defined at global scope for your service instance.policies\apis\<api name>\ - if you have any policies defined at API scope, they are contained in this folder.policies\apis\<api name>\<operation name>\ folder - if you have any policies defined at operation scope, they
are contained in this folder in <operation name>.xml files that map to the policy statements for each operation.policies\products\ - if you have any policies defined at product scope, they are contained in this folder, which
contains <product name>.xml files that map to the policy statements for each product.
portalStyles folderportalStyles folder
products folderproducts folder
templatestemplates
Next steps
The portalStyles folder contains configuration and style sheets for developer portal customizations for theservice instance.
portalStyles\configuration.json - contains the names of the style sheets used by the developer portalportalStyles\<style name>.css - each <style name>.css file contains styles for the developer portal (Preview.css and Production.css by default).
The products folder contains a folder for each product defined in the service instance.
products\<product name>\configuration.json - this is the configuration for the product. This is the sameinformation that would be returned if you were to call the Get a specific product operation.products\<product name>\product.description.html - this is the description of the product and corresponds to
the description property of the product entity in the REST API.
The templates folder contains configuration for the email templates of the service instance.
<template name>\configuration.json - this is the configuration for the email template.<template name>\body.html - this is the body of the email template.
For information on other ways to manage your service instance, see:
Manage your service instance using the following PowerShell cmdlets
Manage your service instance using the REST API
Service deployment PowerShell cmdlet referenceService management PowerShell cmdlet reference
API Management REST API reference
How to use Role-Based Access Control in Azure APIManagement4/12/2018 • 3 min to read • Edit Online
Built-in roles
ROLE READ ACCESS WRITE ACCESS
SERVICECREATION,DELETION,SCALING, VPN,AND CUSTOMDOMAINCONFIGURATION
ACCESS TO THELEGACYPUBLISHERPORTAL DESCRIPTION
Azure APIManagementServiceContributor
✓ ✓ ✓ ✓ Super user. Hasfull CRUD accessto APIManagementservices andentities (forexample, APIsand policies). Hasaccess to thelegacy publisherportal.
Azure APIManagementService Reader
✓ Has read-onlyaccess to APIManagementservices andentities.
Azure APIManagementService Operator
✓ ✓ Can manage APIManagementservices, but notentities.
Azure API Management relies on Azure Role-Based Access Control (RBAC) to enable fine-grained accessmanagement for API Management services and entities (for example, APIs and policies). This article gives you anoverview of the built-in and custom roles in API Management. For more information on access management in theAzure portal, see Get started with access management in the Azure portal.
API Management currently provides three built-in roles and will add two more roles in the near future. These rolescan be assigned at different scopes, including subscription, resource group, and individual API Managementinstance. For instance, if you assign the "Azure API Management Service Reader" role to a user at the resource-group level, then the user has read access to all API Management instances inside the resource group.
The following table provides brief descriptions of the built-in roles. You can assign these roles by using the Azureportal or other tools, including Azure PowerShell, Azure CLI, and REST API. For details about how to assign built-in roles, see Use role assignments to manage access to your Azure subscription resources.
[1] [2]
Azure APIManagementService Editor
✓ ✓ Can manage APIManagemententities, but notservices.
Azure APIManagementContentManager
✓ ✓ Can manage thedeveloper portal.Read-only accessto services andentities.
ROLE READ ACCESS WRITE ACCESS
SERVICECREATION,DELETION,SCALING, VPN,AND CUSTOMDOMAINCONFIGURATION
ACCESS TO THELEGACYPUBLISHERPORTAL DESCRIPTION
Custom roles
$role = Get-AzureRmRoleDefinition "API Management Service Reader Role"$role.Id = $null$role.Name = 'Calculator API Contributor'$role.Description = 'Has read access to Contoso APIM instance and write access to the Calculator API.'$role.Actions.Add('Microsoft.ApiManagement/service/apis/write')$role.AssignableScopes.Clear()$role.AssignableScopes.Add('/subscriptions/<subscription ID>/resourceGroups/<resource group name>/providers/Microsoft.ApiManagement/service/<service name>/apis/<api ID>')New-AzureRmRoleDefinition -Role $roleNew-AzureRmRoleAssignment -ObjectId <object ID of the user account> -RoleDefinitionName 'Calculator API Contributor' -Scope '/subscriptions/<subscription ID>/resourceGroups/<resource group name>/providers/Microsoft.ApiManagement/service/<service name>/apis/<api ID>'
Video
*
*
[1] Read access to API Management services and entities (for example, APIs and policies).
[2] Write access to API Management services and entities except the following operations: instance creation, deletion, and scaling; VPN configuration;
and custom domain setup.
* The Service Editor role will be available after we migrate all the admin UI from the existing publisher portal to the Azure portal. The Content Manager
role will be available after the publisher portal is refactored to only contain functionality related to managing the developer portal.
If none of the built-in roles meet your specific needs, custom roles can be created to provide more granular accessmanagement for API Management entities. For example, you can create a custom role that has read-only access toan API Management service, but only has write access to one specific API. To learn more about custom roles, seeCustom roles in Azure RBAC.
When you create a custom role, it's easier to start with one of the built-in roles. Edit the attributes to add Actions,NotActions, or AssignableScopes, and then save the changes as a new role. The following example begins withthe "Azure API Management Service Reader" role and creates a custom role called "Calculator API Editor." You canassign the custom role to a specific API. Consequently, this role only has access to that API.
The Azure Resource Manager resource provider operations article contains the list of permissions that can begranted on the API Management level.
Next stepsTo learn more about Role-Based Access Control in Azure, see the following articles:
Get started with access management in the Azure portalUse role assignments to manage access to your Azure subscription resourcesCustom roles in Azure RBACAzure Resource Manager resource provider operations
Use Azure Managed Service Identity in Azure APIManagement12/4/2017 • 3 min to read • Edit Online
NOTENOTE
Create an API Management instance with an identity by using aResource Manager template
"identity" : { "type" : "SystemAssigned"}
{ "$schema": "http://schema.management.azure.com/schemas/2014-04-01-preview/deploymentTemplate.json#", "contentVersion": "0.9.0.0", "parameters": { "serviceName": { "type": "string", "minLength": 1, "metadata": { "description": "The name of the api management service" } }, "publisherEmail": { "type": "string", "minLength": 1, "defaultValue": "[email protected]", "metadata": { "description": "The email address of the owner of the service" } }, "publisherName": { "type": "string", "minLength": 1, "defaultValue": "Contoso", "metadata": { "description": "The name of the owner of the service"
Managed Service Identity for Azure API Management is currently in preview.
This article shows you how to create a managed service identity for an API Management service instance and howto access other resources. A managed service identity generated by Azure Active Directory (Azure AD) allows yourAPI Management instance to easily and securely access other Azure AD-protected resources, such as Azure KeyVault. This managed service identity is managed by Azure and does not require you to provision or rotate anysecrets. For more information about Azure Managed Service Identity, see Managed Service Identity for Azureresources.
You can create an API Management instance with an identity by including the following property in the resourcedefinition:
This property tells Azure to create and manage the identity for your API Management instance.
For example, a complete Azure Resource Manager template might look like the following:
"description": "The name of the owner of the service" } }, "sku": { "type": "string", "allowedValues": [ "Developer", "Standard", "Premium" ], "defaultValue": "Developer", "metadata": { "description": "The pricing tier of this API Management service" } }, "skuCount": { "type": "int", "defaultValue": 1, "metadata": { "description": "The instance size of this API Management service." } } }, "resources": [ { "apiVersion": "2017-03-01", "name": "[parameters('serviceName')]", "type": "Microsoft.ApiManagement/service", "location": "[resourceGroup().location]", "tags": {}, "sku": { "name": "[parameters('sku')]", "capacity": "[parameters('skuCount')]" }, "properties": { "publisherEmail": "[parameters('publisherEmail')]", "publisherName": "[parameters('publisherName')]" }, "identity": { "type": "systemAssigned" } } ]}
Obtain a certificate from Azure Key Vault
PrerequisitesPrerequisites
The following example shows how to obtain a certificate from Azure Key Vault. It contains the following steps:
1. Create an API Management instance with an identity.2. Update the access policies of an Azure Key Vault instance and allow the API Management instance to obtain
secrets from it.3. Update the API Management instance by setting a custom domain name through a certificate from the Key
Vault instance.
1. The Key Vault containing the pfx certificate must be in the same Azure subscription and the same ResourceGroup as the API Management service. This is a requirement of the Azure Resource Manager template.
2. The Content Type of the secret must be application/x-pkcs12. You can use the following script to upload thecertificate:
$pfxFilePath = "PFX_CERTIFICATE_FILE_PATH" # Change this path $pwd = "PFX_CERTIFICATE_PASSWORD" # Change this password $flag = [System.Security.Cryptography.X509Certificates.X509KeyStorageFlags]::Exportable $collection = New-Object System.Security.Cryptography.X509Certificates.X509Certificate2Collection $collection.Import($pfxFilePath, $pwd, $flag) $pkcs12ContentType = [System.Security.Cryptography.X509Certificates.X509ContentType]::Pkcs12 $clearBytes = $collection.Export($pkcs12ContentType) $fileContentEncoded = [System.Convert]::ToBase64String($clearBytes) $secret = ConvertTo-SecureString -String $fileContentEncoded -AsPlainText –Force $secretContentType = 'application/x-pkcs12' Set-AzureKeyVaultSecret -VaultName KEY_VAULT_NAME -Name KEY_VAULT_SECRET_NAME -SecretValue $Secret -ContentType $secretContentType
IMPORTANTIMPORTANT
{ "$schema": "http://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#", "contentVersion": "1.0.0.0", "parameters": { "publisherEmail": { "type": "string", "minLength": 1, "metadata": { "description": "The email address of the owner of the service" } }, "publisherName": { "type": "string", "defaultValue": "Contoso", "minLength": 1, "metadata": { "description": "The name of the owner of the service" } }, "sku": { "type": "string", "allowedValues": ["Developer", "Standard", "Premium"], "defaultValue": "Developer", "metadata": { "description": "The pricing tier of this API Management service" } }, "skuCount": { "type": "int", "defaultValue": 1, "metadata": { "description": "The instance size of this API Management service." } }, "keyVaultName": { "type": "string", "metadata": { "description": "Name of the vault" } }, "proxyCustomHostname1": { "type": "string", "metadata": { "description": "Proxy Custom hostname."
If the object version of the certificate is not provided, API Management will automatically obtain the newer version of thecertificate after it is uploaded to Key Vault.
"description": "Proxy Custom hostname." } }, "keyVaultIdToCertificate": { "type": "string", "metadata": { "description": "Reference to the KeyVault certificate." } } }, "variables": { "apiManagementServiceName": "[concat('apiservice', uniqueString(resourceGroup().id))]", "apimServiceIdentityResourceId": "[concat(resourceId('Microsoft.ApiManagement/service', variables('apiManagementServiceName')),'/providers/Microsoft.ManagedIdentity/Identities/default')]" }, "resources": [{ "apiVersion": "2017-03-01", "name": "[variables('apiManagementServiceName')]", "type": "Microsoft.ApiManagement/service", "location": "[resourceGroup().location]", "tags": {
}, "sku": { "name": "[parameters('sku')]", "capacity": "[parameters('skuCount')]" }, "properties": { "publisherEmail": "[parameters('publisherEmail')]", "publisherName": "[parameters('publisherName')]" }, "identity": { "type": "systemAssigned" } }, { "type": "Microsoft.KeyVault/vaults/accessPolicies", "name": "[concat(parameters('keyVaultName'), '/add')]", "apiVersion": "2015-06-01", "dependsOn": [ "[resourceId('Microsoft.ApiManagement/service', variables('apiManagementServiceName'))]" ], "properties": { "accessPolicies": [{ "tenantId": "[reference(variables('apimServiceIdentityResourceId'), '2015-08-31-PREVIEW').tenantId]", "objectId": "[reference(variables('apimServiceIdentityResourceId'), '2015-08-31-PREVIEW').principalId]", "permissions": { "secrets": ["get"] } }] } }, { "apiVersion": "2017-05-10", "name": "apimWithKeyVault", "type": "Microsoft.Resources/deployments", "dependsOn": [ "[resourceId('Microsoft.ApiManagement/service', variables('apiManagementServiceName'))]" ], "properties": { "mode": "incremental", "templateLink": { "uri": "https://raw.githubusercontent.com/solankisamir/arm-templates/master/basicapim.keyvault.json", "contentVersion": "1.0.0.0" }, "parameters": { "publisherEmail": { "value": "[parameters('publisherEmail')]"}, "publisherName": { "value": "[parameters('publisherName')]"},
"publisherName": { "value": "[parameters('publisherName')]"}, "sku": { "value": "[parameters('sku')]"}, "skuCount": { "value": "[parameters('skuCount')]"}, "proxyCustomHostname1": {"value" : "[parameters('proxyCustomHostname1')]"}, "keyVaultIdToCertificate": {"value" : "[parameters('keyVaultIdToCertificate')]"} } } }]}
Next stepsLearn more about Azure Managed Service Identity:
Managed Service Identity for Azure resourcesAzure Resource Manager templates
Service Fabric with Azure API Management overview11/13/2017 • 6 min to read • Edit Online
Architecture
Cloud applications typically need a front-end gateway to provide a single point of ingress for users, devices, orother applications. In Service Fabric, a gateway can be any stateless service such as an ASP.NET Core application,or another service designed for traffic ingress, such as Event Hubs, IoT Hub, or Azure API Management.
This article is an introduction to using Azure API Management as a gateway to your Service Fabric applications.API Management integrates directly with Service Fabric, allowing you to publish APIs with a rich set of routingrules to your back-end Service Fabric services.
A common Service Fabric architecture uses a single-page web application that makes HTTP calls to back-endservices that expose HTTP APIs. The Service Fabric getting-started sample application shows an example of thisarchitecture.
In this scenario, a stateless web service serves as the gateway into the Service Fabric application. This approachrequires you to write a web service that can proxy HTTP requests to back-end services, as shown in the followingdiagram:
As applications grow in complexity, so do the gateways that must present an API in front of myriad back-endservices. Azure API Management is designed to handle complex APIs with routing rules, access control, ratelimiting, monitoring, event logging, and response caching with minimal work on your part. Azure APIManagement supports Service Fabric service discovery, partition resolution, and replica selection to intelligentlyroute requests directly to back-end services in Service Fabric so you don't have to write your own stateless APIgateway.
In this scenario, the web UI is still served through a web service, while HTTP API calls are managed and routedthrough Azure API Management, as shown in the following diagram:
Application scenarios
Send traffic to a stateless service
ExampleExample
Send traffic to a stateful service
Services in Service Fabric may be either stateless or stateful, and they may be partitioned using one of threeschemes: singleton, int-64 range, and named. Service endpoint resolution requires identifying a specific partition ofa specific service instance. When resolving an endpoint of a service, both the service instance name (for example, fabric:/myapp/myservice ) as well as the specific partition of the service must be specified, except in the case of
singleton partition.
Azure API Management can be used with any combination of stateless services, stateful services, and anypartitioning scheme.
In the simplest case, traffic is forwarded to a stateless service instance. To achieve this, an API Managementoperation contains an inbound processing policy with a Service Fabric back-end that maps to a specific statelessservice instance in the Service Fabric back-end. Requests sent to that service are sent to a random replica of thestateless service instance.
In the following scenario, a Service Fabric application contains a stateless service named fabric:/app/fooservice ,that exposes an internal HTTP API. The service instance name is well known and can be hard-coded directly in theAPI Management inbound processing policy.
ExampleExample
Send traffic to multiple stateless services
ExampleExample
Similar to the stateless service scenario, traffic can be forwarded to a stateful service instance. In this case, an APIManagement operation contains an inbound processing policy with a Service Fabric back-end that maps a requestto a specific partition of a specific stateful service instance. The partition to map each request to is computed via alambda method using some input from the incoming HTTP request, such as a value in the URL path. The policymay be configured to send requests to the primary replica only, or to a random replica for read operations.
In the following scenario, a Service Fabric application contains a partitioned stateful service named fabric:/app/userservice that exposes an internal HTTP API. The service instance name is well known and can be
hard-coded directly in the API Management inbound processing policy.
The service is partitioned using the Int64 partition scheme with two partitions and a key range that spans Int64.MinValue to Int64.MaxValue . The back-end policy computes a partition key within that range by converting
the id value provided in the URL request path to a 64-bit integer, although any algorithm can be used here tocompute the partition key.
In more advanced scenarios, you can define an API Management operation that maps requests to more than oneservice instance. In this case, each operation contains a policy that maps requests to a specific service instancebased on values from the incoming HTTP request, such as the URL path or query string, and in the case of statefulservices, a partition within the service instance.
To achieve this, an API Management operation contains an inbound processing policy with a Service Fabric back-end that maps to a stateless service instance in the Service Fabric back-end based on values retrieved from theincoming HTTP request. Requests to a service instance are sent to a random replica of the service instance.
In this example, a new stateless service instance is created for each user of an application with a dynamicallygenerated name using the following formula:
fabric:/app/users/<username>
Each service has a unique name, but the names are not known up-front because the services are created inresponse to user or admin input and thus cannot be hard-coded into APIM policies or routing rules. Instead,the name of the service to which to send a request is generated in the back-end policy definition from the name value provided in the URL request path. For example:
A request to /api/users/foo is routed to service instance fabric:/app/users/foo
A request to /api/users/bar is routed to service instance fabric:/app/users/bar
Send traffic to multiple stateful services
ExampleExample
Similar to the stateless service example, an API Management operation can map requests to more than onestateful service instance, in which case you also may need to perform partition resolution for each stateful serviceinstance.
To achieve this, an API Management operation contains an inbound processing policy with a Service Fabric back-end that maps to a stateful service instance in the Service Fabric back-end based on values retrieved from theincoming HTTP request. In addition to mapping a request to specific service instance, the request can also bemapped to a specific partition within the service instance, and optionally to either the primary replica or a randomsecondary replica within the partition.
In this example, a new stateful service instance is created for each user of the application with a dynamicallygenerated name using the following formula:
fabric:/app/users/<username>
Each service has a unique name, but the names are not known up-front because the services are created inresponse to user or admin input and thus cannot be hard-coded into APIM policies or routing rules. Instead,the name of the service to which to send a request is generated in the back-end policy definition from the name value provided the URL request path. For example:
A request to /api/users/foo is routed to service instance fabric:/app/users/foo
A request to /api/users/bar is routed to service instance fabric:/app/users/bar
Each service instance is also partitioned using the Int64 partition scheme with two partitions and a key range thatspans Int64.MinValue to Int64.MaxValue . The back-end policy computes a partition key within that range byconverting the id value provided in the URL request path to a 64-bit integer, although any algorithm can be usedhere to compute the partition key.
Next stepsFollow the tutorial to set up your first Service Fabric cluster with API Management and flow requests through APIManagement to your services.
Tutorial: deploy API Management with ServiceFabric3/9/2018 • 12 min to read • Edit Online
Prerequisites
Network topology
This tutorial is part four of a series. Deploying Azure API Management with Service Fabric is an advancedscenario. API Management is useful when you need to publish APIs with a rich set of routing rules for yourback-end Service Fabric services. Cloud applications typically need a front-end gateway to provide a single pointof ingress for users, devices, or other applications. In Service Fabric, a gateway can be any stateless servicedesigned for traffic ingress such as an ASP.NET Core application, Event Hubs, IoT Hub, or Azure APIManagement.
This tutorial shows you how to set up Azure API Management with Service Fabric to route traffic to a back-endservice in Service Fabric. When you're finished, you have deployed API Management to a VNET, configured anAPI operation to send traffic to back-end stateless services. To learn more about Azure API Managementscenarios with Service Fabric, see the overview article.
In this tutorial, you learn how to:
Deploy API ManagementConfigure API ManagementCreate an API operationConfigure a backend policyAdd the API to a product
In this tutorial series you learn how to:
Create a secure Windows cluster or Linux cluster on Azure using a templateScale a cluster in or outUpgrade the runtime of a clusterDeploy API Management with Service Fabric
Before you begin this tutorial:
If you don't have an Azure subscription, create a free accountInstall the Azure Powershell module version 4.1 or higher or Azure CLI 2.0.Create a secure Windows cluster or Linux cluster on AzureIf you deploy a Windows cluster, set up a Windows development environment. Install Visual Studio 2017 andthe Azure development, ASP.NET and web development, and .NET Core cross-platformdevelopment workloads. Then set up a .NET development environment.If you deploy a Linux cluster, set up a Java development environment on Linux or MacOS. Install the ServiceFabric CLI.
Now that you have a secure Windows cluster or Linux cluster on Azure, deploy API Management to the virtualnetwork (VNET) in the subnet and NSG designated for API Management. For this tutorial, the API ManagementResource Manager template is pre-configured to use the names of the VNET, subnet, and NSG that you set up in
Sign in to Azure and select your subscription
Login-AzureRmAccountGet-AzureRmSubscriptionSet-AzureRmContext -SubscriptionId <guid>
az loginaz account set --subscription <guid>
Deploy a Service Fabric back-end service
Deploy a .NET Service Fabric serviceDeploy a .NET Service Fabric service
the previous Windows cluster tutorial or Linux cluster tutorial. This tutorial deploys the following topology toAzure in which API Management and Service Fabric are in subnets of the same Virtual Network:
Sign in to your Azure account select your subscription before you execute Azure commands.
Before configuring API Management to route traffic to a Service Fabric back-end service, first you need arunning service to accept requests. If you previously created a Windows cluster, deploy a .NET Service Fabricservice. If you previously created a Linux cluster, deploy a Java Service Fabric service.
For this tutorial, create a basic stateless ASP.NET Core Reliable Service using the default Web API projecttemplate. This creates an HTTP endpoint for your service, which you expose through Azure API Management.
Start Visual Studio as Administrator and create an ASP.NET Core service:
1. In Visual Studio, select File -> New Project.2. Select the Service Fabric Application template under Cloud and name it "ApiApplication".3. Select the stateless ASP.NET Core service template and name the project "WebApiService".4. Select the Web API ASP.NET Core 2.0 project template.5. Once the project is created, open PackageRoot\ServiceManifest.xml and remove the Port attribute from
Create a Java Service Fabric serviceCreate a Java Service Fabric service
<Resources> <Endpoints> <Endpoint Protocol="http" Name="ServiceEndpoint" Type="Input" /> </Endpoints></Resources>
["value1", "value2"]`
the endpoint resource configuration:
Removing the port allows Service Fabric to specify a port dynamically from the application port range,opened through the Network Security Group in the cluster Resource Manager template, allowing trafficto flow to it from API Management.
6. Press F5 in Visual Studio to verify the web API is available locally.
Open Service Fabric Explorer and drill down to a specific instance of the ASP.NET Core service to see thebase address the service is listening on. Add /api/values to the base address and open it in a browser,which invokes the Get method on the ValuesController in the Web API template. It returns the defaultresponse that is provided by the template, a JSON array that contains two strings:
This is the endpoint that you expose through API Management in Azure.
7. Finally, deploy the application to your cluster in Azure. In Visual Studio, right-click the Application projectand select Publish. Provide your cluster endpoint (for example, mycluster.southcentralus.cloudapp.azure.com:19000 ) to deploy the application to your Service Fabric
cluster in Azure.
An ASP.NET Core stateless service named fabric:/ApiApplication/WebApiService should now be running in yourService Fabric cluster in Azure.
For this tutorial deploy a basic web server, which echoes messages back to the user. The echo server sampleapplication contains an HTTP endpoint for your service, which you expose through Azure API Management.
git clone https://github.com/Azure-Samples/service-fabric-java-getting-started.gitcd service-fabric-java-getting-started/reliable-services-actor-sample
<Endpoint Name="WebEndpoint" Protocol="http" Port="8081" />
cd Services/EchoServer/EchoServer1.0/gradle
1. Clone the Java getting started samples.
2. Edit Services/EchoServer/EchoServer1.0/EchoServerApplication/EchoServerPkg/ServiceManifest.xml.Update the endpoint so the service listens on port 8081.
3. Save ServiceManifest.xml, then build the EchoServer1.0 application.
4. Deploy the application to the cluster.
Download and understand the Resource Manager templates
Microsoft.ApiManagement/serviceMicrosoft.ApiManagement/service
Microsoft.ApiManagement/service/certificatesMicrosoft.ApiManagement/service/certificates
Microsoft.ApiManagement/service/backendsMicrosoft.ApiManagement/service/backends
Microsoft.ApiManagement/service/productsMicrosoft.ApiManagement/service/products
cd Scriptssfctl cluster select --endpoint https://mycluster.southcentralus.cloudapp.azure.com:19080 --pem <full_path_to_pem_on_dev_machine> --no-verify./install.sh
A Java stateless service named fabric:/EchoServerApplication/EchoServerService should now be runningin your Service Fabric cluster in Azure.
5. Open a browser and type in http://mycluster.southcentralus.cloudapp.azure.com:8081/getMessage, youshould see "[version 1.0]Hello World!!!" displayed.
Download and save the following Resource Manager templates and parameters file:
network-apim.jsonnetwork-apim.parameters.jsonapim.jsonapim.parameters.json
The network-apim.json template deploys a new subnet and network security group in the virtual network wherethe Service Fabric cluster is deployed.
The following sections describe the resources being defined by the apim.json template. For more information,follow the links to the template reference documentation within each section. The configurable parametersdefined in the apim.parameters.json parameters file are set later in this article.
Microsoft.ApiManagement/service describes the API Management service instance: name, SKU or tier, resourcegroup location, publisher information, and virtual network.
Microsoft.ApiManagement/service/certificates configures API Management security. API Management mustauthenticate with your Service Fabric cluster for service discovery using a client certificate that has access toyour cluster. This tutorial uses the same certificate specified previously when creating the Windows cluster orLinux cluster, which by default can be used to access your cluster.
This tutorial uses the same certificate for client authentication and cluster node-to-node security. You may use aseparate client certificate if you have one configured to access your Service Fabric cluster. Provide the name,password, and data (base-64 encoded string) of the private key file (.pfx) of the cluster certificate that youspecified when creating your Service Fabric cluster.
Microsoft.ApiManagement/service/backends describes the backend service that traffic is forwarded to.
For Service Fabric backends, the Service Fabric cluster is the backend instead of a specific Service Fabric service.This allows a single policy to route to more than one service in the cluster. The url field here is a fully qualifiedservice name of a service in your cluster that all requests are routed to by default if no service name is specifiedin a backend policy. You may use a fake service name, such as "fabric:/fake/service" if you do not intend to have afallback service. resourceId specifies the cluster management endpoint. clientCertificateThumbprint andserverCertificateThumbprints identify certificates used to authenticate with the cluster.
Microsoft.ApiManagement/service/products creates a product. In Azure API Management, a product containsone or more APIs as well as a usage quota and the terms of use. Once a product is published, developers can
Microsoft.ApiManagement/service/apisMicrosoft.ApiManagement/service/apis
Microsoft.ApiManagement/service/apis/operationsMicrosoft.ApiManagement/service/apis/operations
Microsoft.ApiManagement/service/apis/policiesMicrosoft.ApiManagement/service/apis/policies
subscribe to the product and begin to use the product's APIs.
Enter a descriptive displayName and description for the product. For this tutorial, a subscription is requiredbut subscription approval by an admin is not. This product state is "published" and is visible to subscribers.
Microsoft.ApiManagement/service/apis creates an API. An API in API Management represents a set ofoperations that can be invoked by client applications. Once the operations are added, the API is added to aproduct and can be published. Once an API is published, it can be subscribed to and used by developers.
displayName can be any name for your API. For this tutorial, use "Service Fabric App".name provides a unique and descriptive name for the API, such as "service-fabric-app". It is displayed in thedeveloper and publisher portals.serviceUrl references the HTTP service implementing the API. API management forwards requests to thisaddress. For Service Fabric backends, this URL value is not used. You can put any value here. For this tutorial,for example "http://servicefabric".path is appended to the base URL for the API management service. The base URL is common for all APIshosted by an API Management service instance. API Management distinguishes APIs by their suffix andtherefore the suffix must be unique for every API for a given publisher.protocols determine which protocols can be used to access the API. For this tutorial, list http and https.path is a suffix for the API. For this tutorial, use "myapp".
Microsoft.ApiManagement/service/apis/operations Before an API in API Management can be used, operationsmust be added to the API. External clients use an operation to communicate with the ASP.NET Core statelessservice running in the Service Fabric cluster.
To add a front-end API operation, fill out the values:
displayName and description describe the operation. For this tutorial, use "Values".method specifies the HTTP verb. For this tutorial, specify GET.urlTemplate is appended to the base URL of the API and identifies a single HTTP operation. For this tutorial,use /api/values if you added the .NET backend service or getMessage if you added the Java backendservice. By default, the URL path specified here is the URL path sent to the backend Service Fabric service. Ifyou use the same URL path here that your service uses, such as "/api/values", then the operation workswithout further modification. You may also specify a URL path here that is different from the URL path usedby your backend Service Fabric service, in which case you also need to specify a path rewrite in youroperation policy later.
Microsoft.ApiManagement/service/apis/policies creates a backend policy, which ties everything together. This iswhere you configure the backend Service Fabric service to which requests are routed. You can apply this policyto any API operation. For more information, see Policies overview.
The backend configuration for Service Fabric provides the following request routing controls:
Service instance selection by specifying a Service Fabric service instance name, either hardcoded (forexample, "fabric:/myapp/myservice" ) or generated from the HTTP request (for example, "fabric:/myapp/users/" + context.Request.MatchedParameters["name"] ).
Partition resolution by generating a partition key using any Service Fabric partitioning scheme.Replica selection for stateful services.Resolution retry conditions that allow you to specify the conditions for re-resolving a service location andresending a request.
<policies> <inbound> <base/> <set-backend-service backend-id="servicefabric" sf-service-instance-name="service-name" sf-resolve-condition="@((int)context.Response.StatusCode != 200)" /> </inbound> <backend> <base/> </backend> <outbound> <base/> </outbound></policies>
Set parameters and deploy API Management
PARAMETER VALUE
apimInstanceName sf-apim
apimPublisherEmail [email protected]
apimSku Developer
serviceFabricCertificateName sfclustertutorialgroup320171031144217
certificatePassword q6D7nN%6ck@6
serviceFabricCertificateThumbprint C4C1E541AD512B8065280292A8BA6079C3F26F10
serviceFabricCertificate <base-64 encoded string>
url_path /api/values
clusterHttpManagementEndpoint https://mysfcluster.southcentralus.cloudapp.azure.com:19080
inbound_policy <XML string>
policyContent is the Json escaped XML contents of the policy. For this tutorial, create a backend policy to routerequests directly to the .NET or Java stateless service deployed earlier. Add a set-backend-service policy underinbound policies. Replace the sf-service-instance-name value with fabric:/ApiApplication/WebApiService if youpreviously deployed the .NET backend service, or fabric:/EchoServerApplication/EchoServerService if youdeployed the Java service. backend-id references a backend resource, in this case the Microsoft.ApiManagement/service/backends resource defined in the apim.json template. backend-id can also
reference another backend resource created using the API Management APIs. For this tutorial, set backend-id tothe value of the service_fabric_backend_name parameter.
For a full set of Service Fabric back-end policy attributes, refer to the API Management back-end documentation
Fill in the following empty parameters in the apim.parameters.json for your deployment.
certificatePassword and serviceFabricCertificateThumbprint must match the cluster certificate used to set up thecluster.
$bytes = [System.IO.File]::ReadAllBytes("C:\mycertificates\sfclustertutorialgroup220171109113527.pfx");$b64 = [System.Convert]::ToBase64String($bytes);[System.Io.File]::WriteAllText("C:\mycertificates\sfclustertutorialgroup220171109113527.txt", $b64);
<policies> <inbound> <base/> <set-backend-service backend-id="servicefabric" sf-service-instance-name="service-name" sf-resolve-condition="@((int)context.Response.StatusCode != 200)" /> </inbound> <backend> <base/> </backend> <outbound> <base/> </outbound></policies>
$groupname = "sfclustertutorialgroup"$clusterloc="southcentralus"$templatepath="C:\clustertemplates"
New-AzureRmResourceGroupDeployment -ResourceGroupName $groupname -TemplateFile "$templatepath\network-apim.json" -TemplateParameterFile "$templatepath\network-apim.parameters.json" -Verbose
New-AzureRmResourceGroupDeployment -ResourceGroupName $groupname -TemplateFile "$templatepath\apim.json" -TemplateParameterFile "$templatepath\apim.parameters.json" -Verbose
ResourceGroupName="sfclustertutorialgroup"az group deployment create --name ApiMgmtNetworkDeployment --resource-group $ResourceGroupName --template-file network-apim.json --parameters @network-apim.parameters.json
az group deployment create --name ApiMgmtDeployment --resource-group $ResourceGroupName --template-file apim.json --parameters @apim.parameters.json
Test it
serviceFabricCertificate is the certificate as a base-64 encoded string, which can be generated using thefollowing script:
In inbound_policy, replace the sf-service-instance-name value with fabric:/ApiApplication/WebApiService if youpreviously deployed the .NET backend service, or fabric:/EchoServerApplication/EchoServerService if youdeployed the Java service. backend-id references a backend resource, in this case the Microsoft.ApiManagement/service/backends resource defined in the apim.json template. backend-id can also
reference another backend resource created using the API Management APIs. For this tutorial, set backend-id tothe value of the service_fabric_backend_name parameter.
Use the following script to deploy the Resource Manager template and parameter files for API Management:
You can now try sending a request to your back-end service in Service Fabric through API Management directlyfrom the Azure portal.
1. In the API Management service, select API.2. In the Service Fabric App API you created in the previous steps, select the Test tab and then the Values
operation.
["value1", "value2"]```
Clean up resources
$ResourceGroupName = "sfclustertutorialgroup"Remove-AzureRmResourceGroup -Name $ResourceGroupName -Force
ResourceGroupName="sfclustertutorialgroup"az group delete --name $ResourceGroupName
Next steps
HTTP/1.1 200 OK
Transfer-Encoding: chunked
Content-Type: application/json; charset=utf-8
Vary: Origin
Ocp-Apim-Trace-Location: https://apimgmtstodhwklpry2xgkdj.blob.core.windows.net/apiinspectorcontainer/PWSQOq_FCDjGcaI1rdMn8w2-2?sv=2015-07-08&sr=b&sig=MhQhzk%2FEKzE5odlLXRjyVsgzltWGF8OkNzAKaf0B1P0%3D&se=2018-01-28T01%3A04%3A44Z&sp=r&traceId=9f8f1892121e445ea1ae4d2bc8449ce4
Date: Sat, 27 Jan 2018 01:04:44 GMT
3. Click the Send button to send a test request to the backend service. You should see an HTTP responsesimilar to:
A cluster is made up of other Azure resources in addition to the cluster resource itself. The simplest way to deletethe cluster and all the resources it consumes is to delete the resource group.
Log in to Azure and select the subscription ID with which you want to remove the cluster. You can find yoursubscription ID by logging in to the Azure portal. Delete the resource group and all the cluster resources usingthe Remove-AzureRMResourceGroup cmdlet.
In this tutorial, you learned how to:
Deploy API ManagementConfigure API ManagementCreate an API operationConfigure a backend policyAdd the API to a product
Azure API Management FAQs3/2/2018 • 8 min to read • Edit Online
Contact us
Frequently asked questions
How can I ask the Microsoft Azure API Management team a question?How can I ask the Microsoft Azure API Management team a question?
What does it mean when a feature is in preview?What does it mean when a feature is in preview?
How can I secure the connection between the API Management gateway and my back-end services?How can I secure the connection between the API Management gateway and my back-end services?
Get the answers to common questions, patterns, and best practices for Azure API Management.
How can I ask the Microsoft Azure API Management team a question?
What does it mean when a feature is in preview?How can I secure the connection between the API Management gateway and my back-end services?How do I copy my API Management service instance to a new instance?Can I manage my API Management instance programmatically?How do I add a user to the Administrators group?Why is the policy that I want to add unavailable in the policy editor?How do I set up multiple environments in a single API?Can I use SOAP with API Management?Is the API Management gateway IP address constant? Can I use it in firewall rules?Can I configure an OAuth 2.0 authorization server with AD FS security?What routing method does API Management use in deployments to multiple geographic locations?Can I use an Azure Resource Manager template to create an API Management service instance?Can I use a self-signed SSL certificate for a back end?Why do I get an authentication failure when I try to clone a GIT repository?Does API Management work with Azure ExpressRoute?Why do we require a dedicated subnet in Resource Manager style VNETs when API Management is deployedinto them?What is the minimum subnet size needed when deploying API Management into a VNET?Can I move an API Management service from one subscription to another?Are there restrictions on or known issues with importing my API?
You can contact us by using one of these options:
Post your questions in our API Management MSDN forum.Send an email to [email protected] us a feature request in the Azure feedback forum.
When a feature is in preview, it means that we're actively seeking feedback on how the feature is working for you. Afeature in preview is functionally complete, but it's possible that we'll make a breaking change in response tocustomer feedback. We recommend that you don't depend on a feature that is in preview in your productionenvironment. If you have any feedback on preview features, please let us know through one of the contact optionsin How can I ask the Microsoft Azure API Management team a question?.
You have several options to secure the connection between the API Management gateway and your back-end
How do I copy my API Management service instance to a new instance?How do I copy my API Management service instance to a new instance?
Can I manage my API Management instance programmatically?Can I manage my API Management instance programmatically?
How do I add a user to the Administrators group?How do I add a user to the Administrators group?
Why is the policy that I want to add unavailable in the policy editor?Why is the policy that I want to add unavailable in the policy editor?
How do I set up multiple environments in a single API?How do I set up multiple environments in a single API?
services. You can:
Use HTTP basic authentication. For more information, see Import and publish your first API.Use SSL mutual authentication as described in How to secure back-end services by using client certificateauthentication in Azure API Management.Use IP whitelisting on your back-end service. In all tiers of API Management, the IP address of the gatewayremains constant, with a few caveats. You can set your whitelist to allow this IP address. You can get the IPaddress of your API Management instance on the Dashboard in the Azure portal.Connect your API Management instance to an Azure Virtual Network.
You have several options if you want to copy an API Management instance to a new instance. You can:
Use the backup and restore function in API Management. For more information, see How to implement disasterrecovery by using service backup and restore in Azure API Management.Create your own backup and restore feature by using the API Management REST API. Use the REST API tosave and restore the entities from the service instance that you want.Download the service configuration by using Git, and then upload it to a new instance. For more information,see How to save and configure your API Management service configuration by using Git.
Yes, you can manage API Management programmatically by using:
The API Management REST API.The Microsoft Azure ApiManagement Service Management Library SDK.The Service deployment and Service management PowerShell cmdlets.
Here's how you can add a user to the Administrators group:
1. Sign in to the Azure portal.2. Go to the resource group that has the API Management instance you want to update.3. In API Management, assign the Api Management Contributor role to the user.
Now the newly added contributor can use Azure PowerShell cmdlets. Here's how to sign in as an administrator :
1. Use the Login-AzureRmAccount cmdlet to sign in.2. Set the context to the subscription that has the service by using
Set-AzureRmContext -SubscriptionID <subscriptionGUID> .3. Get a single sign-on URL by using
Get-AzureRmApiManagementSsoToken -ResourceGroupName <rgName> -Name <serviceName> .4. Use the URL to access the admin portal.
If the policy that you want to add appears dimmed or shaded in the policy editor, be sure that you are in the correctscope for the policy. Each policy statement is designed for you to use in specific scopes and policy sections. Toreview the policy sections and scopes for a policy, see the policy's Usage section in API Management policies.
To set up multiple environments, for example, a test environment and a production environment, in a single API,you have two options. You can:
Host different APIs on the same tenant.Host the same APIs on different tenants.
Can I use SOAP with API Management?Can I use SOAP with API Management?
Is the API Management gateway IP address constant? Can I use it in firewall rules?Is the API Management gateway IP address constant? Can I use it in firewall rules?
Can I configure an OAuth 2.0 authorization server with AD FS security?Can I configure an OAuth 2.0 authorization server with AD FS security?
What routing method does API Management use in deployments to multiple geographic locations?What routing method does API Management use in deployments to multiple geographic locations?
Can I use an Azure Resource Manager template to create an API Management service instance?Can I use an Azure Resource Manager template to create an API Management service instance?
Can I use a self-signed SSL certificate for a back end?Can I use a self-signed SSL certificate for a back end?
Powershell methodPowershell method
$context = New-AzureRmApiManagementContext -resourcegroup 'ContosoResourceGroup' -servicename 'ContosoAPIMService'New-AzureRmApiManagementBackend -Context $context -Url 'https://contoso.com/myapi' -Protocol http -SkipCertificateChainValidation $true
Direct API update methodDirect API update method
Why do I get an authentication failure when I try to clone a Git repository?Why do I get an authentication failure when I try to clone a Git repository?
SOAP pass-through support is now available. Administrators can import the WSDL of their SOAP service, andAzure API Management will create a SOAP front end. Developer portal documentation, test console, policies andanalytics are all available for SOAP services.
In all tiers of API Management, the public IP address (VIP) of the API Management tenant is static for the lifetimeof the tenant, with some exceptions. The IP address changes in these circumstances:
The service is deleted and then re-created.The service subscription is suspended or warned (for example, for nonpayment) and then reinstated.You add or remove Azure Virtual Network (you can use Virtual Network only at the Developer and Premiumtier).
For multi-region deployments, the regional address changes if the region is vacated and then reinstated (you canuse multi-region deployment only at the Premium tier).
Premium tier tenants that are configured for multi-region deployment are assigned one public IP address perregion.
You can get your IP address (or addresses, in a multi-region deployment) on the tenant page in the Azure portal.
To learn how to configure an OAuth 2.0 authorization server with Active Directory Federation Services (AD FS)security, see Using ADFS in API Management.
API Management uses the performance traffic routing method in deployments to multiple geographic locations.Incoming traffic is routed to the closest API gateway. If one region goes offline, incoming traffic is automaticallyrouted to the next closest gateway. Learn more about routing methods in Traffic Manager routing methods.
Yes. See the Azure API Management Service QuickStart templates.
Yes. This can be done through PowerShell or by directly submitting to the API. This will disable certificate chainvalidation and will allow you to use self-signed or privately-signed certificates when communicating from APIManagement to the back end services.
Use the New-AzureRmApiManagementBackend (for new back end) or Set-AzureRmApiManagementBackend (for existing backend) PowerShell cmdlets and set the -SkipCertificateChainValidation parameter to True .
1. Create a Backend entity by using API Management.2. Set the skipCertificateChainValidation property to true.3. If you no longer want to allow self-signed certificates, delete the Backend entity, or set the
skipCertificateChainValidation property to false.
Does API Management work with Azure ExpressRoute?Does API Management work with Azure ExpressRoute?
Why do we require a dedicated subnet in Resource Manager style VNETs when API Management is deployedWhy do we require a dedicated subnet in Resource Manager style VNETs when API Management is deployedinto them?into them?
What is the minimum subnet size needed when deploying API Management into a VNET?What is the minimum subnet size needed when deploying API Management into a VNET?
Can I move an API Management service from one subscription to another?Can I move an API Management service from one subscription to another?
Are there restrictions on or known issues with importing my API?Are there restrictions on or known issues with importing my API?
If you use Git Credential Manager, or if you're trying to clone a Git repository by using Visual Studio, you mightrun into a known issue with the Windows credentials dialog box. The dialog box limits password length to 127characters, and it truncates the Microsoft-generated password. We are working on shortening the password. Fornow, please use Git Bash to clone your Git repository.
Yes. API Management works with Azure ExpressRoute.
The dedicated subnet requirement for API Management comes from the fact, that it is built on Classic (PAAS V1layer) deployment model. While we can deploy into a Resource Manager VNET (V2 layer), there are consequencesto that. The Classic deployment model in Azure is not tightly coupled with the Resource Manager model and so ifyou create a resource in V2 layer, the V1 layer doesn't know about it and problems can happen, such as APIManagement trying to use an IP that is already allocated to a NIC (built on V2). To learn more about difference ofClassic and Resource Manager models in Azure refer to difference in deployment models.
The minimum subnet size needed to deploy API Management is /29, which is the minimum subnet size that Azuresupports.
Yes. To learn how, see Move resources to a new resource group or subscription.
Known issues and restrictions for Open API(Swagger), WSDL and WADL formats.