Creating Your First Azure PowerShell Function App

Creating Your First Azure PowerShell Function App

This article was written by June Castillote. He is a frequent contributor to the Adam the Automator (ATA) blog. If you'd like to read more from this author, check out his ATA author page. Be sure to also check out more how-to posts on cloud computing, system administration, IT, and DevOps on adamtheautomator.com!

You may have already heard the term serverless-computing. Many cloud service providers offer this service, including Microsoft. With Microsoft's Azure Functions, you can create function apps that support many languages, including Azure PowerShell.

Suppose you want to automate issuing software licenses to customers. When the customer paid, your website sends an HTTP request to your Azure Function App. The app then validates payment and automatically sends the license to the customer's email address.

That's just one scenario where an Azure Function App can be used. There are more usage scenarios from e-commerce to monitoring and reporting where Azure Function Apps can fit in.

In this article, you will learn how to create an Azure PowerShell Function App, develop, test, and execute the code. You'll also get the chance to build a mini-project where you'll create a function for getting the status of Azure VMs and display the result on the web.

Prerequisites

There are several ways to create an Azure PowerShell Function App, and in this article, you will learn the most basic way with the least requirements.

To follow along with the instructions, you need to meet these requirements below.

  • You must have a valid Azure account with an active subscription. If you don't have one yet, you can create an account for free.
  • If you do the mini-project at the end of this article, you will need one or more Azure Virtual Machines (Windows or Linux). Note that you will not use these virtual machines. They only need to exist to report their status using the Azure PowerShell Function App that you will be creating.

Creating the Azure PowerShell Function App

As you will learn in this article, creating a new Azure Function app is quick and easy as long as you are familiar with the process. The high-level steps to create a simple function app consists of:

  • Creating a new Azure Resource group where the function app will be contained.
  • Creating a new general-purpose Azure Storage account.
  • Creating a new Function app.
  • Creating a new function.

There are several ways to create an Azure PowerShell Function App. In this section, you will learn how to create a new Azure Function App using the Azure Portal and Azure PowerShell.

Creating the Function App Resource

The first step is to log in to the Azure Portal using your credentials. Once logged in, click on the Create a resource button.

Untitled-2020-10-07T151710.660.png

In the New page, click on Compute and select Function App from the list of resources.

Untitled-2020-10-07T151755.234.png

In the Create Function App page, under the Basics tab, follow these steps.

  1. Select the Azure subscription where the function app will be created.
  2. Click on the Create new link, specify the name of the new resource group such as AzFuncDemoRg.
  3. Type in the unique name for the app in the Function App box. In this example, the name AzFuncDemoApp1.
  4. There are two Publish options, select Code.
  5. In the Runtime stack dropdown box, select PowerShell Core.
  6. In the Version dropdown box, select 7.0.
  7. Lastly, in the Region, select the one closest to you. In this example, the selected region is East US.
  8. Once you're satisfied with the entries, click on the Next: Hosting button.

The steps above are shown in the screenshot below.

Untitled-2020-10-07T151904.341.png

Under the Hosting tab, you will create a new Storage Account to host the function app files using the steps below.

  1. Click on the Create new link and create the new storage account with the name azfuncdemostorage1.
  2. You'll notice that only the Windows option can be selected in Operating system selection.
  3. In the Plan selection, choose the Consumption (Serverless) option.
  4. Once you're done, click on Review + Create.

Untitled-2020-10-07T151940.792.png

You will now see the summary of the new Azure Function App. Click on the Create button to start the resource creation.

Untitled-2020-10-07T152055.195.png

At this point, wait for the deployment to complete, and you should see a similar confirmation page, as shown below. Click on the Go to resource button.

Untitled-2020-10-07T152120.594.png

Adding a New Function

In the previous section, you have created a new Azure PowerShell Function App called AzFuncDemoApp1. But, that new function app does not do anything yet. For the Function App to be useful, you must add a new function to it.

Creating a new function requires choosing a template. There are several templates to choose from with different "triggers". These triggers define when the function is triggered, such as timer-based or by an HTTP request. In this section, you will create a new function that responds to HTTP requests.

To create an HTTP Request-based function, under the Functions section of the AzFuncDemoApp1 page, click on Functions. Then, click on the Add button.

Untitled-2020-10-07T152153.071.png

Then, in the New Function fly-out, click on the HTTP trigger template option.

Untitled-2020-10-07T152220.824.png

Then, in the Details tab, type in the name of the new function. In this example, the function name is HttpDemo1. Then, in the Authorization level, select Anonymous. There are other authorization levels, but since this function is not confidential or sensitive, anonymous should be sufficient.

Untitled-2020-10-07T152246.362.png

After the function is created, you should be redirected to the HttpDemo1 function page, as shown below.

Untitled-2020-10-07T152315.004.png

Testing the Function

After creating a new function, a PowerShell script file is automatically created with the name run.ps1. This script file contains the default code that is executed when the function is triggered. To view this run.ps1 file, go to the Code + Test under the Developer section.

Untitled-2020-10-07T152337.202.png

Below is the code that is automatically populated in the run.ps1 file using the HTTP request template.

using namespace System.Net

Input bindings are passed in via param block.

param($Request, $TriggerMetadata)

Write to the Azure Functions log stream.

Write-Host "PowerShell HTTP trigger function processed a request."

Interact with query parameters or the body of the request.

$name = $Request.Query.Name if (-not $name) { $name = $Request.Body.Name }

$body = "This HTTP triggered function executed successfully. Pass a name in the query string or in the request body for a personalized response."

if ($name) { $body = "Hello, $name. This HTTP triggered function executed successfully." }

Associate values to output bindings by calling 'Push-OutputBinding'.

Push-OutputBinding -Name Response -Value ([HttpResponseContext]@{ StatusCode = [HttpStatusCode]::OK Body = $body })

The expected action of the code above is to display a message based on the logic below.

If the function is triggered without the Name parameter, the message to be returned is:

This HTTP triggered function executed successfully. Pass a name in the query string or in the request body for a personalized response.

If the function is triggered with the Name parameter, the message to be returned is:

Hello, <NAME>. This HTTP triggered function executed successfully.

Now, to test the code, click on the Test/Run button.

Untitled-2020-10-07T152540.926.png

Once the test fly-out shows up, leave the the Input tab's default values, then click on Run.

Untitled-2020-10-07T152607.859.png

Wait for the test to complete, and you should see the HTTP response, as shown below.

Untitled-2020-10-07T152633.451.png

Executing the Function

Now that you've tested the function and confirmed that it is working, the next step is to execute the code the way it was designed for - by issuing an HTTP request.

To execute the function, you first need to get the function's URL. To do so, click on the Get function URL button.

Untitled-2020-10-07T152702.314.png

Next, copy the URL to the clipboard.

Untitled-2020-10-07T152731.607.png

Now that you have the function URL, you can use your browser to navigate to that URL, as shown below. In this example, the URL is https://azfuncdemoapp1.azurewebsites.net/api/HttpDemo1

Untitled-2020-10-07T152803.901.png

The output above is what's expected if the function was triggered without the name parameter value. To execute the function with the name parameter, append the parameter and its value to the URL. Below is the example of the URL with the name parameter.

<https://azfuncdemoapp1.azurewebsites.net/api/HttpDemo1?name=June>

The result below shows the output when the name parameter is used with the HTTP request.

Untitled-2020-10-07T152837.068.png

Mini-Project: Azure PowerShell Function to Get Virtual Machine Status

It is now time to put your knowledge into practice. In this project, you will create a new function that is triggered by HTTP requests. Once the function is triggered, the code will get the status of the Azure VMs and return the information in the browser.

Note that you do not need to create a new Azure PowerShell Function App as you will reuse the AzFuncDemoApp1 you've created previously.

Enabling Managed Identity

Since this project involves accessing Azure resources, you'll need to modify the AzFuncDemoApp1 to use a Managed Identity. A Managed Identity is essentially an Azure Service Principal that enables your function to authenticate to Azure and access resources. In this case, you'll be using a managed identity to read the Azure VM status.

There are two types of managed identity that you can assign to the Azure Function App; System assigned and User assigned. For simplicity, you will enable the System assigned identity in this project.

To enable the System assigned identity, follow these steps.

  1. In the Function app AzFuncDemoApp1, go to the Identity menu blade.
  2. You will see two tabs; System assigned and User assigned. Stay in the System assigned tab.
  3. Next, click on the Status switch to turn on the System assigned identity.
  4. Finally, click on the Save button.
  5. You will be asked to confirm your choice. Click on Yes.

Untitled-2020-10-07T152909.358.png

Confirm to enable the identityConfirm to enable the identity

Assigning an Azure Role (Permission)

Once the identity is enabled, you would see that the Object ID has been created for the identity. At this point, the identity does not have any role assignment or permission yet. In this section, you will assign the Reader role to the identity.

To assign the role, first, click on the Azure role assignments button. It will take you to the Azure role assignments page.

Untitled-2020-10-07T153003.777.png

In the Azure role assignments page, choose the Azure Subscription (if you have more than one). Then, click on Add role assignment.

Untitled-2020-10-07T153030.964.png

Next, in the Scope, choose Subscription then choose the right subscription name. In the Role, select Reader. Lastly, click on Save.

Untitled-2020-10-07T153108.983.png

After saving the role assignment, you should see that the new role has been assigned.

Untitled-2020-10-07T153141.397.png

Editing the Function and Adding the New Code

The identity has been enabled, and permission has been assigned. What's left now is to update the function code. By now, you should already know where to go to edit the function code. Once you are in the Code + Test page of the function, update the existing code using the code below.

using namespace System.Net

Input bindings are passed in via param block.

param($Request, $TriggerMetadata)

Write to the Azure Functions log stream.

Write-Host "Getting the Azure Virtual Machine Status."

Get the Azure VM status

$vmList = (Get-AzVM -Status | Select-Object Name, PowerState)

Associate values to output bindings by calling 'Push-OutputBinding'.

Push-OutputBinding -Name Response -Value ([HttpResponseContext]@{ StatusCode = [HttpStatusCode]::OK Body = $vmList headers = @{ "content-type" = "application/json" } })

Once you've updated the code, save it, and execute the function URL in your browser. The example below shows that the function could get the Azure VM status and returned the information as expected.

Untitled-2020-10-07T153214.441.png

You now have a working function that gets and returns the Azure VM status. However, the output is in JSON format and looks ugly. Remember, you control how you want the information is displayed; you just need to modify your code.

Suppose you want the function to return a more presentable output. In that case, you can modify the code to return the result as HTML with custom formatting. Using the code below, you can make the function return the same information but in a table with style.

using namespace System.Net

Input bindings are passed in via param block.

param($Request, $TriggerMetadata)

Write to the Azure Functions log stream.

Write-Host "Getting the Azure Virtual Machine Status."

$head = @' <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Frameset//EN" "<http://www.w3.org/TR/html4/frameset.dtd>"> <html><head><title>Virtual Machine Status</title> <style type="text/css"> table { font-family: Verdana, Geneva, sans-serif; border: 1px solid #1C6EA4; background-color: #EEEEEE; text-align: left; border-collapse: collapse; } table td, table th { border: 1px solid #AAAAAA; padding: 3px 2px; } table tbody td { font-size: 13px; } table tr:nth-child(even) { background: #D0E4F5; } table thead { background: #1C6EA4; border-bottom: 2px solid #444444; } table thead th { font-size: 15px; font-weight: bold; color: #FFFFFF; text-align: left; border-left: 2px solid #D0E4F5; } table thead th:first-child { border-left: none; } </style> '@

Get the Azure VM status

$vmList = (Get-AzVM -Status | Select-Object Name, PowerState | ConvertTo-Html -Head $head)

Associate values to output bindings by calling 'Push-OutputBinding'.

Push-OutputBinding -Name Response -Value ([HttpResponseContext]@{ StatusCode = [HttpStatusCode]::OK Body = [string]$vmList headers = @{ "content-type" = "text/html" } })

Once you update the function code using the code above, save it, and then execute the function URL again. This time, you should see a similar output, as shown in the image below.

Untitled-2020-10-07T153252.239.png

Summary

Azure Functions is a quick way to create apps that can be a new system or a part of an already existing workflow to complement and automate some processes. It is reasonably priced (cheap), and there's even a monthly grant. You may potentially run functions at no additional cost!

Additionally, with Azure Functions, you do not need to worry about server maintenance. That way, you can keep your focus on maintaining your application.

In this article, you've learned how to create a new Azure PowerShell Function App. You've learned how to create a function triggered by HTTP requests and accept parameters in queries. You've also learned how to enable managed identities to allow your Function Apps to access Azure resources without embedding the authentication in your code.

What you've learned here are just the basics. There are other ways to create Azure Function apps that include using the command-line or Visual Studio Code. The code provided in the examples here can be improved and integrated with other Azure resources.

Hopefully, the knowledge you gained in this article helps you get started with using Azure Functions in your job, including development, monitoring, or even reporting, to name a few.

Further Reading