Azure Functions 2.0: Create, debug and deploy to Azure Kubernetes Service (AKS)

Azure Functions is a serverless compute service that enables you to run code on-demand without having to explicitly provision or manage infrastructure. You can read about Azure Functions 2.0 general availability @ Introducing Azure Functions 2.0.  Runtime 2.0 runs on .NET Core 2, which means it can run on all platforms supported by .NET Core, including macOS and Linux. This enables cross-platform development and hosting scenarios.

In this article I am going to

  • Create Azure Functions triggered by Azure Blob storage and Event hub in Visual Studio Code
  • Debug locally in Visual Studio Code
  • Deploy Azure Functions to Azure Kubernetes Service

Dev tools used to develop these components are Visual Studio Code for macOS, Docker, AKS Dashboard and kubectl.

Development environment

The steps needed to configure development environment (Azure Function 2.0 on macOS) are

  • Install Visual Studio Code, if it's not already installed

  • Install 'Azure Functions for Visual Studio Code' extension

  • Use Homebrew to install the Core Tools on macOS

    • Install .NET Core 2.1 for macOS, if it's not already installed
    • Install Homebrew, if it's not already installed.
    • Install the Core Tools package:
      • Run command brew tap azure/functions
      • Before running the next command to install core tools, grant write access by running command
        sudo chown -R $(whoami) /usr/local/share/man/man5 /usr/local/share/man/man7
      • Run command brew install azure-functions-core-tools

Azure Kubernetes Service (AKS) Cluster

In case you don’t have AKS cluster up and running, please go through this article to Create AKS Cluster.

Azure Blob Storage

AzureWebJobsStorage: The Azure Functions runtime uses storage account connection string for all functions except for HTTP triggered functions. The storage account must be a general-purpose one that supports blobs, queues, and tables. Create a storage account which is going to be used by Azure Functions runtime. Please follow steps listed in this article to create a storage account.

AzureBlobStorage: Instead of creating a blob container in previously created storage account, I created a separate storage account and created a blob container namely 'testblob'. If you specify a different container name, you will need to update blob container name in TestBlobStorageFunc class. Container name and storage connection string will be specified in Azure function triggered by blog storage as we are going to see shortly.

Keep a note of Storage connection strings for both accounts as these need to be updated in 'local.settings.json' and 'DockerFile' files.

Event Hub

I created an Event hub and Event Hub name I have specified in sample solution is 'testeventhub'. If you select a different name, update event hub name in TestEventHubFunc class. Please follow steps listed in this article to create an Event Hub.

Keep a note of Event hub connection string as this needs to be updated in 'local.settings.json' and 'DockerFile' files.

Create Azure Functions 2.0

The next step is to create Azure Functions project in Visual Studio Code. Open the folder in integrated terminal of Visual Studio Code and

  • Run command func init --docker to create Function 2.0 project and docker file as displayed below
  • If you open host.json file you will see "version": "2.0" which is required for a function app that targets V2 runtime.
  • Run command func new to create a new function and select BlobTrigger option and provide function name
  • Run command func new to create a new function and select EventHubTrigger and provide function name

Debug Azure Functions 2.0 locally in Visual Studio Code:

Before debugging locally, 'local.settings.json' file needs to be updated with connection strings of Storage accounts and Event Hub. { "IsEncrypted": false, "Values": { "AzureWebJobsStorage": "{BLOB_STORAGE_CONNECTION_STRING}", "AzureBlobStorage": "{BLOB_STORAGE_CONNECTION_STRING_OF_CONTAINER_HAVING_TRIGGER}", "AzureEventHubConnectionString":"{EVENT_HUB_CONNECTION_STRING}", "FUNCTIONS_WORKER_RUNTIME": "dotnet" } }

Update BlobTrigger function and specify container name and connection e.g.
public static void Run([BlobTrigger("testblob/{name}", Connection = "AzureBlobStorage")]Stream myBlob, string name, ILogger log)

Update EventHubTrigger function and specify event hub name and connection e.g.
public static void Run([EventHubTrigger("testeventhub", Connection = "AzureEventHubConnectionString")]string myEventHubMessage, ILogger log)

Start debugging in Visual Studio Code and Functions will get triggered once you send a few messages to Event hub and upload a few blobs.

 Deploy Azure Functions 2.0 to AKS

The Values defined in 'local.settings.json' are used only for debugging locally. Thus, we need to specify Values before deploying to AKS. In order to do that DockerFile needs to be updated so that we can pass connection strings through environment variables. Add environment variables listed below to DockerFile and update placeholders with your connection strings.


Finally, it's time to deploy functions to AKS and command is func deploy --platform kubernetes --name {DockerHubRepositoryName} --registry {DockerHubRegistry}.  Update placeholders with your Docker hub repository name and account.

Once deployment is complete, you can open the endpoint to verify the deployment. You can also open AKS dashboard to view deployed resources under namespace 'azure-functions'.

You will find that Horizontal Pod Autoscaler resource is created which automatically scales the number of pods in a replication controller, deployment or replica set based on observed CPU utilization.

Send a few messages to Event Hub and upload a few blobs. You can view logs of functions deployed to AKS by running command func logs --name {DockerHubRepositoryName} --platform kubernetes. Update DockerHubRepositoryName placeholder with the name you specified in previous step.

This completes the article about deploying Functions 2.0 to Kubernetes. You can download the source code for this article from GitHub.