Skip to content

Function App Zipped Deployment

David Ebbo edited this page Jan 3, 2017 · 6 revisions

Runtime behavior

When using zipped deployment, a single file named webcontent.zip (named to be finalized) is dropped into d:\home\site\wwwroot. This zipped file contains everything that would normally exist under the wwwroot folder.

The App Service Infrastructure does all the unzip magic, and points the Function Runtime to a temp local folder that has the unzipped file. The files are only unzipped on demand, which can greatly minimize the startup cost.

Is an App Setting required?

Ideally, the simple presence of this file will trigger zipped mode. If for some reason that is not feasible efficiently (because of the extra check), we can go with a new App Setting, e.g. WEBSITE_ZIPPED_DEPLOYMENT=1.

Compressed vs Uncompressed zip file

The initial prototype requires the zip file to be uncompressed. This is just a point in time limitation, and it is important to support regular zip files. The reason is not so much about reducing the file size, but is primarily about making deployment simple and accessible: everyone knows how to create a regular zipped file, while creating an uncompressed zip file is a very obscure thing. We need to make the publishing bar very low and frictionless.

Effect on the Function Runtime

The Function Runtime should be minimally affected by the use of this feature, because all the magic is abstracted in a layer below it. From the Function Runtime's point of view, it gets pointed a some function folder, and that folder contains normal Function files.

The main difference is that this folder is no longer writable. That means that function files can no longer be added/deleted/modified. Though the Function Runtime itself never does those things anyway (Kudu does), so it shouldn't affect it.

What happens when the zip is updated

When the zip file is updated with a newer version, the right magic needs to happen to make the Function Runtime start using the new zip. Ideally, this happens with no downtime to the Function Runtime, allowing a smooth deployment workflow even without the use of site slots (though those can still be used for more advanced scenarios that require staging).

Here is a possible implementation:

  • The App Service Infrastructure (the logic that unzips files into a local folder) listens for changes to the zip file.
  • When a change is detected, it sets up a new temporary local folder for the new zip file. At this point, the Function Runtime is still happily running on the original local folder.
  • When the new folder is ready, the infrastructure signals the function runtime. One possible way is to create a special marker file (in local space) that the Function Runtime is listening for.
  • When the Function Runtime detects that, it resets itself to point to the new folder. Note that doing this is quite analogous to the switcheroo that happens is the 'Functions Placeholder Sites' feature, where it goes from pointing to dummy files to the real files. A lot of the same logic can be shared between the two scenarios.
  • When the switch is complete, the App Service Infrastructure deletes the old local folder.

Deployment

The previous section discusses how the runtime handles a deployed zip file. This section discusses the various ways that this zip file can make it there.

Manual deployment

Since the design builds on very simple concepts, deploying can easily be done manually. e.g. a user can zip up a function folder they have locally (e.g. using the standard Windows shell), and upload it to wwwroot using good old FTP. Everything will work perfectly fine. This goes back to the need to support regular zip files as discussed above.

'Function App Packager' tool to build an optimized zipped file from a function folder

While it's possible to build the zip file simply by zipping up a source function folder, there are additional steps that can be taken to optimize it. In particular, C# functions can be precompiled into assembly to avoid the need to have to do that at runtime. The tool can also restore npm/NuGet packages.

In order to make these steps easily usable from a variety of scenarios, they can be abstracted into a command line tool (as well as a library). That tool (let's call it the Function App Packager) takes a source function folder as input, and produces the optimized zip file. The callers doesn't need to be aware of all the transformations/optimizations that come into play.

This tool will be made available on NuGet. The following sections discuss some of the scenarios in which it is used.

Continuous deployment using Kudu

Generally, the way Kudu deploys things is by taking a sequence of steps that turn whatever files are in the repo into files that end up in wwwroot.

For our zipped Functions scenario, that makes it a perfect use case for the Function App Packager tool. Basically, the Kudu deployment script becomes as simple as invoking the tool, passing it %DEPLOYMENT_SOURCE% as input folder, and %DEPLOYMENT_TARGET% as output folder. Note that there is no need to using kudusync in this scenario.

In order to do this, Kudu will need to either include the Function App Packager tool, or obtain it dynamically using NuGet.

Deployment from a dev Function app

When using a Function App in 'dev mode', the user directly edits function files using the portal, and tests them in the dev app. When they're ready to push to a production (or staging) app, they hit a publish button, which works as follows:

  • When the user sets up publishing from the dev app to another app (or slot), an app setting is created on the dev site, containing the publishing URL of the target app. e.g. it might look like AzureWebJobsPublishingUrl=https://$MyProdApp:SiteCredPassword@MyProdApp.scm.azurewebsites.net/.
  • When the publish button is clicked, the Portal calls a new Kudu function publishing API.
  • The API first uses the Function App Packager tool to create a zip file from the function files. This is similar to what Kudu does during continuous deployment except that here wwwroot is the source instead of the target.
  • It then calls the Kudu vfs API on the target app to copy the zip file. Then the target app's runtime takes it from there.

Deployment from VS Function tooling

The standard way the VS deploys to Web Apps is using msdeploy, and this can also be the case here. VS needs to add the right msbuild target files that do the magic of calling the Function App Packager tool to create the zip file. The zip file then becomes what it deploys using msdeploy, just like it would deploy anything else.

Deployment from VSTS, Octopus, ...

The fact that the Function App Packager logic is abstracted by msbuild target files means that everything related to deployment works using completely standard msbuild commands. This allows all those other msbuild-based workflows to just work without needing much special knowledge about Azure Functions (they just need the right target files).

Learn

Azure Functions Basics

Advanced Concepts

Dotnet Functions

Java Functions

Node.js Functions

Python Functions

Host API's

Bindings

V2 Runtime

Contribute

Functions host

Language workers

Get Help

Other

Clone this wiki locally