Blog Post

Apps on Azure Blog
5 MIN READ

Accelerating Azure Container Apps with the Azure CLI and Compose Files

steven_murawski's avatar
Jun 16, 2022

Azure Container Apps is a hosted service designed to make microservices and container-based solutions easy in a serverless model. My team (the Cloud Native Advocacy team) and I have been kicking the tires on this service since the preview was announced.

 

After working through some getting started experiences in the preview with a couple of my teammates, both of them expressed the idea that a docker-compose file should provide enough information to create an Azure Container Apps environment and microservices deployment.  The Compose specification is open source and has been used to create a variety of tools to support other deployment options, so I thought it’d be worth a try.

 

I like to build CLIs, so I spent a couple of days prototyping an example and showed it off to our team.  We polished it up a bit more and showed it to the Azure Container Apps team.  They suggested we create an Azure CLI extension and offer it up for y’all to give it a try.

 

Announcing the containerapp-compose Azure CLI extension

I’d like to introduce the containerapp-compose Azure CLI extension.  This extension adds a command group to the containerapps extension, allowing you to start with a Compose file and a resource group in Azure and end up with a deployed Azure Container Apps environment and running services. 

PowerShell terminal with az containerapp compose create command example.

 

Quick Start

To get started with this new functionality, all you need is a resource group, the Azure CLI (with the containerapp and containerapp-compose extensions), and Compose file. 

 

  • Install/update the extensions

 

 

 

az extension add --name containerapp --upgrade –yes

az extension add --name containerapp-compose --upgrade –yes

 

 

 

 

  • Create the resource group

 

 

 

az group create --name my_containerapp_sample --location eastus

 

 

 

 

  • Create a Container App Environment and Container App from a Compose spec

 

 

 

curl -O https://raw.githubusercontent.com/smurawski/docker-compose-examples/main/simple/docker-compose.yml

az containerapp compose create --environment acacompose --resource-group my_containerapp_sample

 

 

 

 

It may take a few moments to deploy as it will create a new Azure Container Apps Environment (which requires a Log Analytics workspace) if it does not exist.  Re-using that same environment would speed up future deployments.

 

More Examples

For more examples of using Compose files with Azure Container Apps, check out https://github.com/smurawski/docker-compose-examples and contribute some of your own (I'll take pull requests)!

 

How are Compose Services mapped to Azure Container Apps?

We tried to map Compose services as directly as possible to Azure Container Apps and I’m sure there are a few rough edges (please file an issue or let me know at containerapp-compose@microsoft.com).

 

For a full reference of the Compose Spec, please see https://github.com/compose-spec/compose-spec.

 

For the full reference for Azure Container Apps please see https://docs.microsoft.com/azure/container-apps/azure-resource-manager-api-spec?tabs=arm-template.

 

The Compose service name was mapped to the Container App name.

 

The ports and expose are used to determine the ingress type and port mapping.  If ports is defined, it will be used to configure an external ingress.  If expose is defined, an internal ingress is created.  Azure Container Apps only supports one port defined as the ingress, so if multiple are defined in the Compose file, you’ll be prompted to pick the one you want. (See below for details about ingress transport modes.)

 

CPU and memory settings for the Container App are pulled from deploy/resources/reservations/cpu and deploy/resources/reservations/memory.  If the settings are not valid for Azure Container Apps, then the default settings will be used.

 

If the compose file specifies entrypoint or commands, those will be used to populate the Container App’s command and args properties.

 

Compose secrets are mapped to Azure Container Apps secrets and shared with the running container as environment variables. Environment variables defined in the Compose file are also mapped into the container’s environment.

 

Considerations and Cautions

 

Azure Container Apps is a tailored serverless microservices offering – so not every compose file will map neatly in.  If there are elements of your Compose file that are not supported, the CLI will warn about those elements.

 

Network Traffic

Currently, Azure Container Apps traffic between ingresses (internal or external) is over HTTP(S).  This means that many application/database compose files are unlikely to work right away – given the ephemeral nature of storage, that makes sense and it’d be a better architecture to use one of the database services (which could be accessed from your application in Container Apps).

 

Container Apps ingress definitions support the concept of mode. The three options are auto (the default), http, and http2.  If you want to specify a transport mode for a service, the command line option --transport takes a key value pair of servicename=mode.  For example, --transport frontend=http2.

 

Private Container Registries

To specify a private registry and credentials to pull the container images in the Compose file from, there are three command line options --registry-server, --registry-user, and --registry-password.  If you do not supply the registry password as part of the command, you’ll be prompted for it.

 

Local Environment

A common pattern in Compose files is to use local environment variables to customize the use of the Compose file.  The Compose Spec defines how environment variable interpolation is to work and we follow that spec.  There are also two special environment variables available at the time of evaluation that are specific to Azure Container Apps.  AZURE_CONTAINERAPPS_ENV_DEFAULT_DOMAIN contains the default domain name for a Container Apps environment.  Individual Container Apps would use a subdomain of their Container App name for external ingress or their Container App name and .internal for internal ingress.  AZURE_CONTAINERAPPS_ENV_STATIC_IP contains the IP address for the Azure Container Apps environment ingress.

 

Common Questions

Do you support the full Compose specification?

No, the extension supports much of the service definition from the Compose spec.  We currently do not support “build” operations (though are looking into that as a future addition).  Volume mounts and configuration mounts are also not supported.

 

No volume mounts?  But doesn’t Azure Container Apps support mounting storage now?

Yes, Azure Container Apps now has some support for ephemeral files and files using Azure Files.  If this is something you are interested in, please file an issue (or tag on to an existing issue) or drop us a note at containerapps-compose@microsoft.com.

 

How do you handle secrets?

Secrets are mapped into Azure Container Apps secrets and exposed to the container as environment variables.

Updated Jun 16, 2022
Version 2.0
  • Hey steven_murawski, this is awesome! Definitely spending my learning time playing around with this extension!

     

    As I'm going through the article, I think it needs just a minor correction. The CLI extension command needs to change from --update to --upgrade.

  • Hi vienltkidl, the compose behavior was initially created as a way to rapidly take existing projects and get them started in Azure Container Apps.  I never intended it to map the full range of offerings specific to Azure Container Apps.  Support for managed identity might be interesting to add, but should be suggested via https://github.com/Azure/azure-cli-extensions (where I see you have an open issue or two already).

     

    Thanks!

  • masimalmi's avatar
    masimalmi
    Copper Contributor

    steven_murawski Does it support authenticating to ACR using Managed Identity of the Container App? I'd like to avoid having to pass the client secret 😉 

  • vienltkidl's avatar
    vienltkidl
    Brass Contributor

    Hi steven_murawski ,

     

    Would it be possible to have two options for deploying to an existing vnet/subnet and connecting to an existing Log Analytics workspace with the az containerapp compose create command line? Thank you very much!

  • vienltkidl's avatar
    vienltkidl
    Brass Contributor

    steven_murawski does it support accessing to Azure App Configuration via a System-Assigned Managed Identity? If a service connector of Container App has been created via Connection String before, there will be a new env var like ConnectionStrings__AppConfig which is created. Because the environment vars are deleted after creating with that "az containerapp compose create" command, then that service connector will be failed accordingly. It would be great if it supports to enable a Managed Identity with that command and Docker Compose file.

     
  • vienltkidl's avatar
    vienltkidl
    Brass Contributor

    Hi steven_murawski , Yes, I agreed that it was really helpful when quickly migrating an existing model like App Service with Docker Compose to Azure Container Apps. Thanks a lot for your reply! I will raise another one.