Freigeben über


Part Three: Become acquainted with PowerApps and Flow

Editor's note: The following post was written by Office Development and Office Servers and Services MVP Adis Jugo   as part of our Technical Tuesday series. Tony Champion of the MVP Award Blog Technical Committee served as the technical reviewer for this piece.  

This is part 3 of a 3-article series. This article explains how to extend PowerApps with custom methods and data sources.

Introduction

In the first two parts of this article series (see Part One and Part Two), we looked into the concepts, and the How-to of PowerApps and Flow. Now it’s time to dive into the custom extensibility of PowerApps. Data from legacy applications or data sources often needs to be integrated with modern application platforms, such as Azure and Office 365. PowerApps offer a good and viable solution to access such data sources through Web APIs, which are deployed in the cloud. Let’s imagine we have an SQL Server database - with a table inside - that needs to be published through PowerApps.

Create a custom data source

We can accomplish this in multiple ways, two of which I will cover here: Azure API Apps and Azure Functions. These are the most obvious ones. With Azure API Apps, we are going to build a restful Web API, which will serve as a wrapper around the database table. Next we are going to deploy it to Azure - as an API App - with swagger interface enabled. After that, we are going to import that swagger definition into PowerApps, and to build an app around it.

001

We can create an Azure API App in Microsoft Visual Studio. The project creation process will give us all the possibilities we need, plus we can create a data model from our database table and use Entity Framework to create controllers around that model. This process is fairly simple for anybody who’s experienced in creating web services on Microsoft platforms.

The complete step-by-step process which outlines how to achieve this can be found in the blog post here: https://blog.sharedove.com/adisjugo/index.php/2016/11/29/extending-powerapps-and-flow-part-1-adding-custom-data-sources-through-azure-api-apps/

It is important to remember that in order for the newly created API App service to work in the context of PowerApps, a Swagger UI needs to be created. Swagger is a service definition format, used for restful services, much like WSDL was used with SOAP. Visual Studio offers us instant enabling of a swagger UI in the SwaggerConfig.cs file.

In short, we can just uncomment the .EnableSwaggerUi part. But, it is worthwhile to take a look at that file, as much of the how swagger works with your service can be understood and changed from and there.

Once the API App has been developed, the next step is to integrate it with PowerApps.

002

In the early version of PowerApps - when the Enterprise plan was still available -  it was possible to use a wizard to generate an app from the custom API. Since that feature is not available anymore, we will have to wire the controls to our custom data source (API App) manually. A practical workaround is to create a PowerApp from any data source (for example, from a SharePoint Online list), and then to change data source and control wirings manually.

003

Security

As you have probably noticed, there is no security around this API App, and our PowerApp can get the data without any form of authentication. While API Apps - which are based on Azure App Service - can utilize Azure Active Directory authentication, PowerApps are not able to pass the authentication tokens to the  API App. So, as it is now, the only way to protect your API is to implement manual key authentication inside the API App, and to store that key in the Swagger definition uploaded to PowerApp. Although, this  is not the most optimal way. Let’s hope that PowerApps will soon be able to pass the auth tokens directly to API Apps, which would enable real Authentication and API security.

Extending the PowerApps expression language

The expression language in PowerApps is somewhat limited, and there is no possible way of building any kind of code in the background. The only way to overcome these limitations is building custom APIs.

Two recommended – and supported – ways to do this are again, Azure API Apps and Azure Functions. While Azure Functions are lighter, easier and faster to develop and deploy, it often makes sense to use API Apps for this purpose, especially if there is already an API App in place - which provides a custom data source (as shown in the previous example). In that case, it is very easy to add an additional controller to that API App, and to use that for extending the expression language.

We can do this easily by creating an additional empty values controller in the API App, and adding as many “GET” methods as we need to extend our PowerApp functionality. The methods might have as much input arguments as you need, and return a value of the desired type.

004

A “typical” use case here is a “does string contain string” method. It’s something that’s very often needed, but is not a part of PowerApps expression language. For this, we will create an empty value controller that takes two string arguments as input, and returns a Boolean. This is a very useful, but simple case. Inside the value controllers, we can put much more complex functionality, and even call external services, etc.  There are basically no limits for that. On the PowerApps side, everything that a user will see is a method they can use, and they will not have to worry about how that method is implemented.

A complete walk-through for creating API Apps value controllers for extending PowerApps expression language can be found here:

https://blog.sharedove.com/adisjugo/index.php/2016/12/01/extending-powerapps-and-flow-part-2-extending-powerapps-expression-language-with-azure-api-apps/

Extending PowerApps Expression Language with Azure Functions

In the previous two chapters, we have seen how to utilize Azure API Apps to connect to external data sources, and how to use the same API app to extend the PowerApps expression language with additional methods, using value controllers. 005

But if we really want to do something simple, an Azure API App can be an overkill. If we think of that “does string contain a string” use case from above, it is literally one line of code in C#. Deploying an API App, just for that purpose, is clearly too much - and in cases like this, Azure Functions might be the right way to go.

Azure Functions are a great platform for hosting small, single-tasked pieces of code. Anybody can create Azure Functions – all one needs to do is log into Azure portal, or go to functions.azure.com and start writing the code in a web editor. There are a number of programing languages available. If somebody is not the fan of writing code inside web editors, Azure Functions can be integrated with GitHub or VSTS. Visual Studio Tools for Azure Functions are also recently available. Those Visual Studio tools are still in preview and they require VS2015 Update3 with Azure SDK installed.

After choosing the programming language, select the function type. What we need here is the “HttpTrigger” function trigger, which basically means that the function will be triggered only by HTTP calls. Note that functions can be triggered many different ways – we have webhooks, queues, integration with Azure Service Bus, and timers, among other.  But for PowerApps, HttpTrigger is what we need.

006

We will also need to choose the Authorization level - anonymous, function, or admin. In the case of later two, we will need to create function or master admin keys. Furthermore, since Azure Functions are based on Azure App Service platform, we could also choose some of the supported Authentication mechanisms there, like AAD, Microsoft Account, Facebook, etc. But this is not an option here, since PowerApps are not (yet) able to pass authentication tokens.

Once we’re done with the function setup, we will need to code the function. We get a code template, and start writing the code.

The complete Azure Functions walk-through in this scenario can be found here: https://blog.sharedove.com/adisjugo/index.php/2016/12/14/extending-powerapps-language-with-azure-functions/

Once the function has been created, we will need to create the swagger definition for our function (our function is just a RESTfull API, after all). And as we have seen before, PowerApps want swagger definitions. My preferred swagger creation tool is ttp://editor.swagger.io/

If we have used a key-based authorization (Function, Admin), we will have to pass another parameter in the swagger GETter operation. This will pass the key with every GET request made from PowerApps towards Azure Function.

 {
“name”: “code”,
“in”: “query”,
“description”: “code”,
“default”: “[enter function/admin code]”,
“type”: “string”
}

Once the swagger definition has been created, the process of integrating Azure Function into PowerApps (with or without key) is the same as with API Apps. We upload the swagger definition into the PowerApps management page, and we are good to go.

Summary

In this article, we saw just two of the standard ways of extending PowerApps with custom data sources and custom logic. Since PowerApps are based on Microsoft’s Cloud Platform, it is fairly easy to integrate it with the rest of the stack. Some things, especially from the authentication or security perspective, are still missing but we can be fairly optimistic that this great platform will continue to evolve.


adisjugo-profile-largeAdis Jugo is a software architect and trusted advisor, with over 25 years of solution delivery and IT consulting experience. Adis is Microsoft MVP for Office Development and for Office Servers and Services. He is a Director of Product Technology at skybow, company that makes platforms for rapid business solutions development on SharePoint. He first became acquainted with SharePoint (and Microsoft CMS server) back in 2002, and since 2006 his focus was completely shifted towards architecture and development of solutions based on SharePoint, Office 365 and Azure. Adis is an internationally recognized speaker with over 15 years of speaker experience, presenting at various Microsoft and community events worldwide. He likes to keep his free time very free, since there isn't much of it. He prefers spending it with his family, and he tries to reach for his guitar (which he loves almost as much as software development) as often as he can. Follow him on Twitter @adisjugo.