Thumbnail Quick tip: how to deploy to web app subfolders

Quick tip: how to deploy to web app subfolders

Can you deploy files to a specific subfolder of an Azure web app, using Azure DevOps pipelines? The short answer is: of course you can…but it does depend on the type of web app you are running! Azure offers multiple options for launching web apps. Let’s look at a few:

First off, the Azure App Service. This well known type of web app is available running on Windows or Linux OS.

When creating an Azure DevOps pipeline, you can add the Azure App Service deploy task to deploy to such a web app.

The default yaml configuration of this deployment task looks more or less as follows.

- task: AzureRmWebAppDeployment@4
  inputs:
    ConnectionType: 'AzureRM'
    azureSubscription: 'some-subscription-or-service-connection'    
    appType: 'webApp'
    WebAppName: ''
    VirtualApplication: '' #Only on windows
    packageForLinux: '$(Build.ArtifactStagingDirectory)/SomeZip.zip'

There is no option on the yaml task to designate a specific subfolder to deploy to. But, for App Services running on Windows, you can select a Virtual Application or directory using the VirtualApplication property. Virtual directories are an older concept coming from Internet Information Services. I won’t go into it, but suffice to say you can use this functionality to achieve the purpose of this post. The only drawback is that you would need to create this virtual application upfront in Azure. So it’s not a very dynamic thing. You can find the setting on your web app in Configuration > Path Mappings.

If your web app is running on Linux, or you just do not want to use virtual applications, there is an alternative. You can use an Azure CLI task. Azure CLI is a great commandline tool to manage Azure resources, and it offers functionality to deploy web apps. The yaml for that looks as follows:

- task: AzureCLI@2
  inputs:
    azureSubscription: 'some-subscription-or-service-connection'
    scriptType: 'bash'
    scriptLocation: 'inlineScript'
    inlineScript: "az webapp deploy --resource-group 'some-resource-group' --name 'some-webapp' --src-path '$(Build.ArtifactStagingDirectory)/SomeZip.zip' --type zip --clean false --target-path some-subfolder" 

What the script above does, is deploy a zip artifact to the subfolder of the web app. Using the --target-path property, you can choose which folder you want to deploy to. The folder will be created for you if it does not exist. You also need the --clean false property to avoid deleting all the other files on the web app.

So what if you are running a Static Website on an Azure Storage account?

This simple type of static web app is usually deployed with the Azure File Copy task. In this task you can deploy to a subfolder by using the BlobPrefix property. It is called BlobPrefix because Blobs do not really have folders. They do offer a visual hierarchy that looks like a folder structure. And when serving these blobs in a Static Website, they behave like a regular folder structure as well. You create this visual hierarchy by prefixing the blobs with a folder name and a slash. Hence the word BlobPrefix. So, deploying to a blob ‘subfolder’ will look as follows:

- task: AzureFileCopy@4
  inputs:
    SourcePath: '$(Build.ArtifactStagingDirectory)/*'
    azureSubscription: 'some-subscription-or-service-connection'
    Destination: 'AzureBlob'
    storage: 'somestorageaccount'
    ContainerName: '$web'
    BlobPrefix: 'somesubfolder'

Or if you want, you can use an Azure CLI task as well. At the moment of writing the necessary commands are still in preview, but you can configure the Azure Pipeline Agent to install the necessary tooling by first running az config. The complete yaml looks as follows:

- task: AzureCLI@2
  inputs:
    ... #omitted for brevity
    inlineScript: "az config set extension.use_dynamic_install=yes_without_prompt" 
- task: AzureCLI@2
  inputs:
    ... #omitted for brevity
    inlineScript: "az storage blob directory upload -c '$web' --account-name 'somestorageaccount' -s '$(Build.ArtifactStagingDirectory)/*' -d 'somesubfolder' --recursive"

Last but not least, the latest and greatest type of web app Azure offers: the Static Web App. Not to be confused with the Static Website on a Storage account, these web apps are much more flexible. Publishing to a Static Web App uses the (in preview) Deploy Azure Static Web App task The yaml looks as follows:

- task: AzureStaticWebApp@0
    inputs:
      app_location: ''
      api_location: ''
      output_location: ''
      azure_static_web_apps_api_token: ''  

Don’t mistake the output_location property for what we need though. This property designates the folder where the build output of the static site generator is located, respective to the app_location.

So unfortunately, it does look like you currently cannot deploy to a static web app subfolder. The Azure CLI also offers no alternative here. It’s all quite new yet. Who knows, the functionality might be added with time.

That’s it for now. Any tips and additions are welcome.


pipelines azuredevops tips
Support me by sharing this

More

More blogs

Quick tip: PowerShell performance
Quick tip: PowerShell performance

I regularly use PowerShell scripting to achieve my ends. I find them airy and easy to use. But when dealing with large amounts of data, performance is key.

Read more
Deploying SPFx apps with Azure DevOps pipelines - all YAML variant
Deploying SPFx apps with Azure DevOps pipelines - all YAML variant

In this blog post I will show you how you can deploy SPFx apps using Azure DevOps pipelines with an all YAML build & release definition.

Read more
Deploying SPFx apps with Azure DevOps pipelines - Classic variant
Deploying SPFx apps with Azure DevOps pipelines - Classic variant

In this blog post I will show you how you can deploy SPFx apps using Azure DevOps pipelines with a classic release pipeline.

Read more

Thanks

Thanks for reading

Thanks for reading my blog, I hope you got what you came for. Blogs of others have been super important during my work. This site is me returning the favor. If you read anything you do not understand because I failed to clarify it enough, please drop me a post using my socials.


Warm regards,
Martin

Microsoft MVP | Microsoft 365 Architect

Microsoft MVP horizontal