Reputation: 750
I need a bare minimum Bicep file to create an EMPTY Python 3.11 Function App in Azure via Infrastructure as Code (IaC). I do not want App Insights support. I should be able to deploy to a preexisting resource group named rg-py-func-tst via this one line command:
az deployment group create --resource-group rg-py-func-tst --template-file main.bicep
I've looked at samples on Git, tried exporting templates directly out of Azure, and even briefly attempted to use Azure Resource Manager (ARM) templates. Through all of that, this Bicep seems most reasonable to me:
// Created by Microsoft Copilot and Google Gemini
// This Bicep script deploys an EMPTY Python 3.11 Function App named
// 'shawnopyFuncTest' without App Insights, at service level Y1.
// It creates a storage account named 'pyfunctest100', an app service
// plan named 'pyfunctestAppService', and the function app itself.
//
// I do not have the Python code yet. The Python code will be
// deployed in a separate project. I just want to create an
// empty Python Function App
@description('Name of the storage account')
param storageAccountName string = 'pyfunctest100'
@description('Name of the app service plan')
param appServicePlanName string = 'pyfunctestAppService'
@description('Name of the function app')
param functionAppName string = 'shawnopyFuncTest'
@description('Location for all resources')
param location string = resourceGroup().location
// Define the storage account resource
resource storageAccount 'Microsoft.Storage/storageAccounts@2022-09-01' = {
name: storageAccountName
location: location
sku: {
name: 'Standard_LRS'
}
kind: 'StorageV2'
}
// Define the app service plan resource
resource appServicePlan 'Microsoft.Web/serverfarms@2022-03-01' = {
name: appServicePlanName
location: location
kind: 'linux'
sku: {
name: 'Y1'
tier: 'Dynamic'
}
properties:{
reserved: true
}
}
// Define the function app resource (Updated API version)
resource functionApp 'Microsoft.Web/sites@2022-09-01' = {
name: functionAppName
location: location
kind: 'functionapp,linux'
properties: {
serverFarmId: appServicePlan.id
siteConfig: {
linuxFxVersion: 'Python|3.11'
appSettings: [
{
name: 'FUNCTIONS_WORKER_RUNTIME'
value: 'python'
}
{
name: 'AzureWebJobsStorage'
value: storageAccount.properties.primaryEndpoints.blob
}
]
}
}
}
output storageAccountName string = storageAccount.name
output appServicePlanName string = appServicePlan.name
output functionAppName string = functionApp.name
I've ran the above deployment in two completely separate Azure tenants and the result is always the same. My resource group rg-py-func-tst is populated with: a Storage Account named pyfunctest100; an App Service Plan named pyfunctestAppService; and, a Function App named shawnopyFuncTest. That's what I want; unfortunately, that isn't the end of the story.
When I open my newly deployed empty Function App shawnopyFuncTest, I see the text "Error" in the Runtime Version field:
But what I expect to see for an empty Python function app is this:
Can someone please help me correct the Bicep that MS Copilot and Gemini created? If not, can you provide a simpler, more clean template that still does what I need?
Upvotes: 0
Views: 79
Reputation: 1170
According to the docs you can (should) target specific runtime version by passing FUNCTIONS_EXTENSION_VERSION
value via appSettings
. See modifed example below.
// Created by Microsoft Copilot and Google Gemini
// This Bicep script deploys an EMPTY Python 3.11 Function App named
// 'shawnopyFuncTest' without App Insights, at service level Y1.
// It creates a storage account named 'pyfunctest100', an app service
// plan named 'pyfunctestAppService', and the function app itself.
//
// I do not have the Python code yet. The Python code will be
// deployed in a separate project. I just want to create an
// empty Python Function App
@description('Name of the storage account')
param storageAccountName string = 'pyfunctest100'
@description('Name of the app service plan')
param appServicePlanName string = 'pyfunctestAppService'
@description('Name of the function app')
param functionAppName string = 'shawnopyFuncTest'
@description('Location for all resources')
param location string = resourceGroup().location
// Define the storage account resource
resource storageAccount 'Microsoft.Storage/storageAccounts@2022-09-01' = {
name: storageAccountName
location: location
sku: {
name: 'Standard_LRS'
}
kind: 'StorageV2'
}
// Define the app service plan resource
resource appServicePlan 'Microsoft.Web/serverfarms@2022-03-01' = {
name: appServicePlanName
location: location
kind: 'linux'
sku: {
name: 'Y1'
tier: 'Dynamic'
}
properties:{
reserved: true
}
}
// Define the function app resource (Updated API version)
resource functionApp 'Microsoft.Web/sites@2022-09-01' = {
name: functionAppName
location: location
kind: 'functionapp,linux'
properties: {
serverFarmId: appServicePlan.id
siteConfig: {
linuxFxVersion: 'Python|3.11'
appSettings: [
{
name: 'FUNCTIONS_WORKER_RUNTIME'
value: 'python'
}
{
name: 'AzureWebJobsStorage'
value: storageAccount.properties.primaryEndpoints.blob
}
{
name: 'FUNCTIONS_EXTENSION_VERSION'
value: '~4'
}
]
}
}
}
output storageAccountName string = storageAccount.name
output appServicePlanName string = appServicePlan.name
output functionAppName string = functionApp.name
Upvotes: 1