I developed the habit to unlock Azure App Services using so-called Gateway Services. As the name implies, Gateway Services are nothing more than gatekeepers. They have a fixed set of responsibilities: Give customers authorized access using basic authentication, store the posted entity in original format (Azure Storage tables for XML/Json, blobs for file attachments) and send an event message to a queue to kick off the process in a decoupled way.
I first implemented the Gateway Services via custom coding. I created a separate Web App for each customer. One customer, one Gateway. After a while I realized I could implement the Gateway Service via a Logic App using out-of-the-box API’s (so without any custom coding): Request, Azure Storage Tables and Blobs (with looping for attachments), Azure Storage Queue, Response. Fair enough. The only remaining responsibility for the Web App was to call the Logic App and apply basic authentication. The next step was to call the Logic App from Azure API Management. You can’t miss the option to import a new API from a Logic App. Nice. Now there was only one problem left. How to perform basic authentication?
When using Azure Active Directory and ADFS 3.0 you need to define an Authorization Server. You can also use a OAuth 2.0 bearer token for external identity providers like Microsoft and Google. But the Security section is not what we need here. For basic authenication, you can use an inbound policy: check-header.
The Authorization header looks quite complicated, but you can use an on-line tool
to generate the header. The basic authentication header is a base64 encoded string with format username:password.
When testing the API Management call to the logic app with the above policy applied, I received a rather cryptic error:
“message”: “The request must be authenticated only by Shared Access scheme.”
Using this excellent blog
, I found out that was due to the fact that Logic Apps are not able to handle the Authorization HTTP header. So, I had to find a way to remove the Authorization header after authentication/authorization. Luckily enough that’s easy. You need to add another policy to the inbound section:
<set-header name=”Authorization” exists-action=”delete”/>