Azure Logic Apps access to Function App with Managed Identity

Azure Logic Apps is a workflow platform that enables the user to design a workflow almost without coding in most cases. Users can quickly implement business logic by integrating different services through the connectors, especially since it supports the Pay-as-you-go charging model (Consumption plan). However, one downside of the Consumption plan is that it doesn’t support VNET integration. The consumption plan logic app is hosted on a multi-tenant environment, which means you are sharing the host server with many other logic app users. You may set up Integration Service Environment (ISE) for the logic apps to get the VNET integration. Still, the cost of ISE is a factor to consider.

Suppose your logic app wants access data from your VNET. In that case, you may consider using an Azure Function app with VNET integration as a workaround. The function app works as a gatekeeper to control what data or APIs can be accessed from the external network. The logic app has an official connector to call the function app, making the integration extremely easy. Since the function app works as a gatekeeper, you may want a secure way to protect the APIs rather than just a function/app key.

In this scenario, Managed Identity may help.

Below is my proof-of-concept study.

Warning: Before you do/plan anything, you should always check with your organization’s IT administrators & security consultants on security matters.

Basic Setup

Virtual Network

I have created a VNET with 10.0.0.0/16, and defined 2 subnets: default (10.0.0.0/24) & storage-subnet (10.0.1.0/24)

Storage

I have created a storage account, disabled the public access, and set a private endpoint for enabling the access from VNET. A private endpoint is assigned to “storage-subnet”.

And I have created a container called “text-container” and uploaded a text file “hello.txt” to it. The content of the text file is simply “Quick brown fox jumps over the lazy dog.”

Function App

I have created a function app named “poc-fx-app”. I have set the VNET integration and assigned it to use the “default” subnet.

Then I have coded a simple function app as below:https://medium.com/media/124ca8ee0111fe5e4f76b543551612ec

The “GetMessage” and “GetMessage2” methods are 99% the same, as they both run the same base method. Both methods access the storage via the private endpoint, get the content of the hello.txt, and return it.

The only difference between them is the authorization level. The authorization level of GetMessage is “Function”, which means a function key is needed for calling, and GetMessage2 is “Anonymous”, which means anyone can call it. You will see why we need them later.

And if you open the function app URL by browser, you should see the below screen as the default page:

The Logic App

The logic app is straightforward: It’s triggered by an HTTP request, then it accesses the Azure Function App to get the message, and finally returns the content retrieved from the function app. Please note that the logic app is currently set to call the “GetMessage” with the function key.

And below is the result of calling the HTTP trigger of the logic app:

So far, so good.

Now we start the process of making use of Managed Identity to enhance the security.

Setup Managed Identity

Click “Identity” from your logic app page to enable Managed Identity. Then turn “On” the status of system assigned managed identity and click “Save”. Once completed, you should see something like the below. Copy down the “Object (principal) ID”, as you will need this later.

Get your tenant ID

You may ask your IT / Azure administrator to find your tenant ID. Or you may find it on the front page of Azure Active Directory. Copy down the tenant ID.

Enable AAD Authentication for the Function App

On your function app’s blade, click “Authentication”.

Then click “Add identity provider”.

Select “Microsoft” as the identity provider.

Then the page asks you to create a new app registration, pick an existing one from your directory, or enter the details yourself. The “app registration” means registering an app to enable the trust relationship between your application and Microsoft Identify Platform. You may find the details here.

Since the logic app is not under your single tenant (Consumption plan means multi-tenant), so you can only enter the details manually.

Fill the app registration as:

Application (client) ID: “Object (principal) ID” of your logic app

Client secret (recommended): Any secret string that your client app uses. In this case, we can ignore it because the logic app doesn’t need it. If you enter a secret string here, your function app can get the value from the environment variable “MICROSOFT_PROVIDER_AUTHENTICATION_SECRET”.

Issuer URL: https://sts.windows.net/{Your-Tenant-ID}

Allowed token audience: https://management.azure.com

We use “HTTP 401 Unauthorized” for the App Service authentication settings and keep others as default values.

Click “Add” to save the settings.

After the authentication is enabled, you should see an error message if you visit the function app URL by a browser. This is because the function app is registered to your logic app now, and you don’t have the authorization to access it.

And even if your call the API with the function key, the app responds with a 401 Unauthorized message.

Update the Logic App

Now we update the logic app to use managed identity to access the function app.

First, we remove the step of “GetMessage”. Then we add a new action of Azure Functions, then select “poc-fx-app”, and select “GetMessage”.

Instead of using the function key in the request header, add the Authentication option by clicking “Add new parameter” and selecting “Authentication”.

We then select the “Authentication type” as “Managed identify”. And set the “Managed identity” as “System-assigned managed identity”. We then set the audience as “https://management.azure.com“. Please note that the audience must be exactly the same as the one you entered in the app registration.

Then, if you try to save it, you will see the error message:

The message informed us that if you want to use Managed Service Identity, the authentication type of your function app (API) must be set as “anonymous”. This is why I have prepared “GetMessage2”, which is already set to use “anonymous” authentication (which means no authentication)

We then remove the “GetMessage” again and repeat the steps to add Azure Functions, but this time we use “GetMessage2”.

We also need to update the Response step as it should return the “Body” of “GetMessage2” now.

Now the whole logic app should be like this:

Save the changes. Now, if the call the HTTP trigger of the logic app, it should return the message as expected:

Some considerations

In this study, I have made the logic app call the function app with managed identify. However, after the changes, the function app can only be accessed by the logic app. So, if your original function app is currently serving other applications, you may need to create another function app to serve as a “proxy” for the logic app. And app security should always be treated with care; therefore, you should discuss with your organization’s security expert when you do the plan.

This blog featured as part of Azure Week. Find more great Azure content here.

About the Author:

Hello, I am Wilson Yeung, currently working as a system integration consultant to design the architecture for multiple enterprise applications. I am interested in new technologies, especially in Cloud, Data & automation areas, and I am also a scrum master.

Reference:

Yeung, W. (2022). Azure Logic Apps access to Function App with Managed Identity. Available at: https://medium.com/@wilsonyeung_41612/azure-logic-apps-access-to-function-app-with-managed-identity-12081e290535 [Accessed: 8th July 2022].

Share this on...

Rate this Post:

Share: