Azure Functions on Kubernetes

My favorite part about Azure Functions is the ability to host and run them almost anywhere. From providing an out of the box experience in Azure to running in a container on a hosted service or even on an IoT device, the Functions v2 runtime continues to surprise me with its affinity for various platforms and infrastructures.

To add to this mix, today, we’re excited to share that deploying Azure Functions to Kubernetes is easier than ever before! We’re combining the power of two open source technologies in the hope that it will expand the possibilities and options for our users. This post will walk you through a simple Function application built locally and deployed to a K8s cluster on Azure Kubernetes Service. Using the same workflow, you can also publish to any K8s 1.7+ cluster running on a Linux host in the cloud.

Step 01. Install all you need to start

This is the list of requirements you need to install:

Step 02. Start a local Functions project

To get started, you first need to create a functions project. This is the equivalent of an application in Azure and can contain multiple functions that share the same local and hosting configuration.

To initiate the project, run the command below in your terminal and pick the desired runtime for your project. I’ll build my example using node but you can also pick dotnet.

> func init MyFunctionProj --docker 
Select a worker runtime:
1. dotnet
2. node
3. java
> Choose option: 2
node
Writing .gitignore
Writing host.json
Writing local.settings.json
Writing /Users/asavaritayal/MyFunctionProj/.vscode/extensions.json
/Users/asavaritayal/.git
Directory already a git repository.
Writing Dockerfile

Change directory to the MyFunctionProj folder. You will notice that along with some basic config files, the core tools also generated a Dockerfile that describes the environment required to run your app. For this post, we will directly leverage this file for the containers in our cluster but you can also customize and extend the base image for your specific scenario.

> cd MyFunctionProj

Step 03. Create a function

Run the func newcommand and pick a template and name for your function when prompted. We’ll use the Http trigger template for our simple example.

> func new
Select a language: Select a template:
1. Blob trigger
2. Cosmos DB trigger
3. Event Grid trigger
4. HTTP trigger
5. Queue trigger
6. SendGrid
7. Service Bus Queue trigger
8. Service Bus Topic trigger
9. Timer trigger
> Choose option: 4
HTTP trigger
> Function name: [HttpTriggerJS] Func1
Writing /Users/asavaritayal/MyFunctionProj/Func1/index.js
Writing /Users/asavaritayal/MyFunctionProj/Func1/sample.dat
Writing /Users/asavaritayal/MyFunctionProj/Func1/function.json

Function code is generated in a subfolder with the provided function name.

Step 04. Create an AKS cluster

Next order of business is to create the Kubernetes cluster in Azure. Before you proceed, make sure that you’re logged in to Azure and have created a resource group for your cluster.

Once you’re ready, use the following command to provision the AKS instance.

> az aks create \
--name FunctionsCluster \
--resource-group <resource-group-name>\
--node-count 3\
--generate-ssh-keys

After several minutes, the deployment completes, and returns JSON-formatted information about the AKS deployment.

Step 05. Connect with kubectl

kubectl is a command-line tool to deploy and manage applications on Kubernetes. To make kubectl run in the context of your cluster, configure a connection using the command below.

> az aks get-credentials \
--name FunctionsCluster \
--resource-group <resource-group-name>

To verify the connection to your cluster, you can also run the following command and compare output.

> kubectl get nodes
Output:
NAME STATUS ROLES AGE VERSION
aks-nodepool1-66427764-0 Ready agent 9m v1.9.6

Step 06. Deploy to Kubernetes

Finally, to deploy your function app to the the kubernetes platform, run the func deploy command as shown below along with a name for your application and a Docker Hub id.

func deploy 
--platform kubernetes
--name MyFunctionProject
--registry <docker-hub-id or registry-server>

This command will trigger the Core Tools to build a docker image that contains the Azure Functions runtime as described by the Dockerfile and the functions you created earlier. It’ll also publish this image to the given Docker registry and create corresponding Deployment, Service and Horizontal Pod Auto-scaler objects in AKS.

For greater control over the deployment configuration, you can also provide the --min and --max number of pods to be created in the cluster or a path to the kubeconfig file using the --config flag.

func deploy 
--platform kubernetes
--name MyFunctionProject
--registry <docker-hub-id or registry-server>
--config /mypath/config

If the deployment is successful, you should see this:

Function deployed successfully!
Function IP: 40.121.21.192

The Function IP is the publicly accessible IP of your function. All functions are deployed to a dedicated azure-functions namespace. You can create a Kubernetes LimitRange to decide exactly how much resources you want to allocate to Azure Functions running in your cluster.

Hopefully this blogpost has been helpful in outlining how you can get up and running quickly using Azure Functions and Kubernetes. With this understanding you should be able to take advantage of a highly sophisticated platform layer like Kubernetes to manage your functions together with the rest of your containerized apps without having to compromise on the event driven scale and Serverless experience.

We’ll continue to expand in this area and provide more information about the available features on our GiHub repo here — https://github.com/Azure/azure-functions-core-tools#getting-started-on-kubernetes. Feel free to reach out to us on Twitter @AzureFunctions for any questions.

Lastly and most importantly, huge shout out to Yaron Schneider for his great work on this project and getting us all excited about the range of possibilities with open source and Kubernetes!