Deploy Azure FunctionApp container to App Service as linuxFxVersion - azure

I am working on deploy isolated Azure Function App container on Azure App Service.
I have created App Service Plan:
"sku": {
"name": "P1v2",
"tier": "PremiumV2",
"size": "P1v2",
"family": "Pv2",
"capacity": 1
},
"kind": "linux",
with App Service:
"kind": "functionapp,linux,container"
I am using AzureWebAppContainer#1 task:
- task: AzureWebAppContainer#1
displayName: Deploy to app service
inputs:
azureSubscription: ${{ parameters.azureSubscription }}
appName: my-web-app0name
imageName: myacr01.azurecr.io/myregistryname:tag01
configurationSettings: -linuxFxVersion DOCKER|myacr01.azurecr.io/myregistryname:tag01"
appSettings: ${{ parameters.appSettings }}
resourceGroupName: my-resource-group
When the task is executed by Azure DevOps yaml pipeline in the logs there is info that:
Trying to update App Service Configuration settings. Data: {"appCommandLine":null,"windowsFxVersion":"DOCKER|myacr01.azurecr.io/myregistryname:tag01"}
I do not understand why the windowsFxVersion is used instead of linuxFxVersion.
On resource level in Azure Portal I can also see that I have windowsFxVersion set instead of linuxFxVersion.
Worth to mention that when you are clicking thought the wizard on Azure Portal with default Function App it is set as linuxFxVersion.

This is not a valid value:
-linuxFxVersion DOCKER|myacr01.azurecr.io/myregistryname:tag01"
Please find available values by executing:
az webapp list-runtimes --os linux
Result:
[
"DOTNETCORE:7.0",
"DOTNETCORE:6.0",
"DOTNETCORE:3.1",
"NODE:16-lts",
"NODE:14-lts",
"PYTHON:3.9",
"PYTHON:3.8",
"PYTHON:3.7",
"PHP:8.0",
"PHP:7.4",
"RUBY:2.7",
"JAVA:17-java17",
"JAVA:11-java11",
"JAVA:8-jre8",
"JBOSSEAP:7-java11",
"JBOSSEAP:7-java8",
"TOMCAT:10.0-java17",
"TOMCAT:10.0-java11",
"TOMCAT:10.0-jre8",
"TOMCAT:9.0-java17",
"TOMCAT:9.0-java11",
"TOMCAT:9.0-jre8",
"TOMCAT:8.5-java11",
"TOMCAT:8.5-jre8"
]
I'm using in my current project:
linuxFxVersion: 'DOTNET|6.0'
netFrameworkVersion: 'v6.0'
kind: 'functionapp,linux'
Bicep for creating the app:
resource hostingPlan 'Microsoft.Web/serverfarms#2020-10-01' = {
name: hostingPlanName
location: location
kind: 'linux'
sku: {
name: hostingPlanNameSkuName
}
properties: {
reserved: true
}
}
resource myApp 'Microsoft.Web/sites#2020-06-01' = {
name: myAppName
location: location
kind: 'functionapp,linux'
identity: {
type: 'SystemAssigned'
}
properties: {
httpsOnly: true
serverFarmId: hostingPlan.id
clientAffinityEnabled: true
siteConfig: {
alwaysOn: true
netFrameworkVersion: 'v6.0'
linuxFxVersion: 'DOTNET|6.0'
ftpsState: 'Disabled'
cors: {
allowedOrigins: [
'*'
]
}
}
}
}

Related

`apiRevision` flag isn't working in Bicep template

I am using Bicep to deploy open api json into Azure API Management. The snippet looks like this.
resource fuseintegrationsapi 'Microsoft.ApiManagement/service/apis#2021-08-01' = {
name: '${apim.name}/integrations-api-${environment_name}'
properties: {
description: 'Contains integrations apis used to control the platform.'
type: 'http'
apiRevision: '1234'
isCurrent: true
subscriptionRequired: false
displayName: 'Integrations Api'
serviceUrl: '${api_backend_url}/api/test/v1/integrations'
path: '${environment_name}/api/test/v1/integrations'
protocols: [
protocol
]
value: api_link
format: 'openapi+json-link'
apiType: 'http'
}
dependsOn: [
api2
]
resource symbolicname 'policies' = {
name: 'policy'
properties: {
value: anonymous_operation_policy
format: 'rawxml'
}
}
}
Even though revision is hardcoded to 1234 it's always using default 1 and the API is not updating with latest open api specification.
I had the same problem and figured out that you have to put the revision in the name also.
name: '${apim.name}/integrations-api-${environment_name};rev=1234'

Azure App Service Problem in DevOps Pipeline

Hi does anyone have any idea on why im getting this error:
Got service connection details for Azure App Service:'nsclassroomstudent-dgyn27h2dfoyo'
##[debug][POST]https://login.windows.net/***/oauth2/token/
##[debug][GET]https://management.azure.com/subscriptions/237bc9da-22ad-49ea-8411-6cf6a190c18f/resourceGroups/ClassroomInTheCloud/providers/Microsoft.Web/sites/nsclassroomstudent-dgyn27h2dfoyo/?api-version=2016-08-01
##[debug]Correlation ID from ARM api call response : c3eefa7c-9088-44f1-8dc8-dccd7a9f8c4c
##[debug]Processed: ##vso[task.logissue type=error;code=ResourceNotFound;]
##[debug]Deployment Failed with Error: Error: Failed to fetch App Service 'nsclassroomstudent-dgyn27h2dfoyo' details. Error: The Resource 'Microsoft.Web/sites/nsclassroomstudent-dgyn27h2dfoyo' under resource group 'ClassroomInTheCloud' was not found. For more details please go to https://aka.ms/ARMResourceNotFoundFix (CODE: 404)
##[debug]task result: Failed
My code is attached, I have been through the microsoft Site: https://learn.microsoft.com/en-us/azure/devops/pipelines/tasks/deploy/azure-app-service-settings?view=azure-devops
I have added the Connected Service Name to my YAML but I still get the error and im not sure what else it wants.
Thanks
#pool:
# vmImage: windows-latest
resources:
repositories:
- repository: Student
name: Classroom In The Cloud/Student
path:
- include: /Student/Student
type: git
ref: master #branch name
variables:
System.Debug: true
azureSubscription: 'azuresubscription'
RG: 'ClassroomInTheCloud'
Location: West Europe
containername: 'private'
appconnectionname: 'RunPipelinesInOtherSubscription'
jobs:
- job: job1
displayName: Create And Publish Artifact
pool:
vmImage: vs2017-win2016
steps:
- checkout: Student
clean: true
- task: DotNetCoreCLI#2
displayName: dotnet restore
inputs:
command: restore
projects: '**/*.csproj'
- task: DotNetCoreCLI#2
displayName: dotnet build
inputs:
projects: '**/*.csproj'
workingDirectory: Student
- task: DotNetCoreCLI#2
displayName: dotnet publish
inputs:
command: publish
projects: '**/*.csproj'
arguments: --output "$(Build.ArtifactStagingDirectory)"
zipAfterPublish: true
modifyOutputPath: false
workingDirectory: Student
- task: PublishPipelineArtifact#1
displayName: Publish Pipeline Artifact
inputs:
targetPath: '$(Build.ArtifactStagingDirectory)'
artifact: 'Student'
publishLocation: 'pipeline'
- job: job2
displayName: 'Get Variable Value for Student Env'
dependsOn: job1
steps:
- task: AzureCLI#1
displayName: 'Azure CLI '
inputs:
azureSubscription: $(azureSubscription)
scriptLocation: inlineScript
inlineScript: |
mkdir $(Pipeline.Workspace)\BlobFile
az storage blob download --container-name $(containername) --file '$(Pipeline.Workspace)/s/student.json' --name 'student.json' --connection-string 'DefaultEndpointsProtocol=https;EndpointSuffix=core.windows.net;AccountName=devscriptstorage;AccountKeyMY VALUE HERE'
- pwsh: |
cd '/home/vsts/work/1/s/'
ls
$armOutput = Get-Content '/home/vsts/work/1/s/student.json' | convertfrom-json
$student = $armOutput.studentvalue #use student not studentvalue
$type = $armOutput.type
$appServicePlanName = $armOutput.appServiceValue
Write-Host "The value of [$student] is [$appServicePlanName]"
Write-Host "##vso[task.setvariable variable=studentvalue;isOutput=true]$student" #use studentvalue not $studentvalue
Write-Host "##vso[task.setvariable variable=appServiceValue;isOutput=true]$appServicePlanName" #use appServiceValue not $appServicePlanName
name: setvarStep
- script: echo $(setvarStep.studentvalue)
- script: echo $(sevarStep.appServiceValue)
name: echovar
- job: job3
displayName: Create Web App
dependsOn: job2
variables:
webappname: $[ dependencies.job2.outputs['setvarStep.studentvalue'] ]
appservice: $[ dependencies.job2.outputs['setvarStep.appServicevalue'] ]
# Download Artifact File
steps:
- download: none
- task: DownloadPipelineArtifact#2
displayName: 'Download Build Artifacts'
inputs:
patterns: '**/*.zip'
path: '$(Build.ArtifactStagingDirectory)'
# deploy to Azure Web App
- task: AzureWebApp#1
inputs:
package: $(Build.ArtifactStagingDirectory)/**/*.zip
azureSubscription: $(azureSubscription)
appName: '$(webappname)'
ResourceGroupName: $(RG)
- task: AzureAppServiceSettings#1
inputs:
azureSubscription: $(azureSubscription)
ConnectedServiceName: $(appconnectionname)
appName: '$(webappname)'
resourceGroupName: $(RG)
# To deploy the settings on a slot, provide slot name as below. By default, the settings would be applied to the actual Web App (Production slot)
# slotName: staging
appSettings: |
{
"name": "DIAGNOSTICS_AZUREBLOBCONTAINERSASURL",
"value": "VALUEINHERE",
"slotSetting": false
},
{
"name": "DIAGNOSTICS_AZUREBLOBRETENTIONINDAYS",
"value": "365",
"slotSetting": false
},
{
"name": "OEM",
"value": "netsupport",
"slotSetting": false
},
{
"name": "SCM_REPOSITORY_PATH",
"value": "d:\\home\\respository",
"slotSetting": false
},
{
"name": "VIDEO_CLIENT_URL",
"value": "https://signal-uks.classroom.cloud",
"slotSetting": false
},
{
"name": "WEBSITE_NODE_DEFAULT_VERSION",
"value": "10.15.2",
"slotSetting": false
}
I ended up fixing this, when changing app settings on an app you have to put in the app name in the displayname area in the code like so:
- task: AzureAppServiceSettings#1
displayName: 'Azure Web App Deploy: $(webappname)'
inputs:
azureSubscription: $(azureSubscription)
ConnectedServiceName: $(appconnectionname)
appName: '$(webappname)'
resourceGroupName: $(RG)
# To deploy the settings on a slot, provide slot name as below. By default, the settings would be applied to the actual Web App (Production slot)
# slotName: staging
appSettings: |
{
"name": "DIAGNOSTICS_AZUREBLOBCONTAINERSASURL",
"value": "VALUEINHERE",
"slotSetting": false
},
{
"name": "DIAGNOSTICS_AZUREBLOBRETENTIONINDAYS",
"value": "365",
"slotSetting": false
},
{
"name": "OEM",
"value": "netsupport",
"slotSetting": false
},
{
"name": "SCM_REPOSITORY_PATH",
"value": "d:\\home\\respository",
"slotSetting": false
},
{
"name": "VIDEO_CLIENT_URL",
"value": "https://signal-uks.classroom.cloud",
"slotSetting": false
},
{
"name": "WEBSITE_NODE_DEFAULT_VERSION",
"value": "10.15.2",
"slotSetting": false
}
I got to this conclusion after playing around with the classic pipeline editor and watching what it would do to the YAML code.

"The parameter LinuxFxVersion has an invalid value" when creating WebApp resource from Node.js

I am trying to create a simple WebApp using the Azure SDK for JS in a Node.js environment, but I keep getting the response:
{
"Code":"BadRequest",
"Message":"The parameter LinuxFxVersion has an invalid value.",
"Target":null,
"Details":[
{"Message":"The parameter LinuxFxVersion has an invalid value."},
{"Code":"BadRequest"},
{"ErrorEntity": {
"ExtendedCode":"01007",
"MessageTemplate":"The parameter {0} has an invalid value.",
"Parameters":["LinuxFxVersion"],
"Code":"BadRequest",
"Message":"The parameter LinuxFxVersion has an invalid value."}
}],
"Innererror":null
}
I've tried a variety of different sets of properties and environments with no success. I always get this error. Here's a snippet of the TypeScript code I am using:
const wsmClient: WebSiteManagementClient...
const webAppName: string...
const servicePlanId: string...
const rgName: string...
const envelope: Site = {
name: webAppName,
location: 'westus2',
kind: 'app,linux',
serverFarmId: servicePlanId,
siteConfig: {
linuxFxVersion: 'JAVA|11-java11'
}
};
const appResp = await wsmClient.webApps.createOrUpdate(
rgName,
webAppName,
envelope
);
What am I doing wrong?
Reason:
Your app service plan is not Linux, actually it's Windows. Windows host doesn't have parameter LinuxFxVersion.
If we create a site without explicitly configuring the host as Linux, it will be a Windows host/serverFarm/app service plan by default. Using {"kind":"linux"} is not enough.
Solution:
Explicitly define the app service plan in Linux, and make sure {"reserved": true} to set it as a Linux host (See documentation)
{
"type": "Microsoft.Web/serverfarms",
"apiVersion": "2019-08-01",
"name": "[parameters('hostingPlanName')]",
"location": "[parameters('location')]",
"kind": "app,linux",
"properties": {
"reserved": true
},
"sku": {
"Tier": "[parameters('hostingPlanSkuTier')]",
"Name": "[parameters('hostingPlanSkuName')]"
}
}
I test your json data, it's caused your properties. Your json data has no "properties" property. If you want to create web with the json property check this web app Rest API request body:Web Apps - Create Or Update.
The correct format should be like the below sample:
{
"location": "CentralUS",
"kind":"app,linux",
"properties":{
"serverFarmId":"your Resource ID",
"siteConfig":{
"linuxFxVersion":"JAVA|11-java11"
}
}
}
#imwenyz answer helped me.
I am running as Azure DevOps pipeline, which has AzureWebApp#1 task. And the app service on Azure that I configured is windows based.
I am getting the error at this task as follows.
##[error]Error: Failed to patch App Service 'BasicReactApp' configuration. Error: BadRequest - The parameter LinuxFxVersion has an invalid value. (CODE: 400)
So I had to modify the task as follows.
- task: AzureWebApp#1
displayName: 'Azure Web App Deploy: '
inputs:
azureSubscription: $(azureSubscription)
#appType: webAppLinux # this is the cause for the error in my case.
appType: webApp
appName: $(webAppName)
runtimeStack: 'NODE|14.x'
package: $(Pipeline.Workspace)/drop/$(Build.BuildId).zip
startUpCommand: 'npm run start'
Basically, as you can see, changed the appType from webAppLinux to webApp
I had the similar issue while deploying the webapp using Terraform.
resource "azurerm_linux_web_app" "app_service" {
name = "app-name"
location = azurerm_resource_group.resourcegroup.location
resource_group_name = azurerm_resource_group.resourcegroup.name
service_plan_id = azurerm_service_plan.plan.id
site_config {
application_stack {
docker_image = "<image-registry>"
docker_image_tag = var.GIT_VERSION
}
}
}
In my case, docker_image_tag version was not populated correctly. After providing the correct value, Terraform deployed successfully.

Sending .Net Core application settings to kubernetes pods as environment variables

I'm hosting some stuff as an AppService in Azure and use environment variables to differentiate settings for different slots (test, dev etc).
If the AppSettings.json file contains a structure like:
{
"ConnectionString": {
"MyDb": "SomeConnectionString"
}
}
I can set the environment variable "ConnectionString:MyDb" to "SomeConnectionString" and .Net Core will understand that the : means child level.
But in Kubernetes I cannot use : as part of the environment key. Is there another way to handle hierarchy or do I need to switch to flat settings?
I believe you are referring to the env in the container definition for a Pod. From the YAML/JSON perspective, I don't see a problem with specifying a : in a key for an environment variable. You can also put it within quotes and should be valid JSON/YAML:
# convert.yaml
apiVersion: v1
kind: Pod
metadata:
name: envar-demo
labels:
purpose: demonstrate-envars
spec:
containers:
- name: envar-demo-container
image: dotnetapp
env:
- name: ConnectionString:Mydb
value: ConnectionString
Same in JSON:
$ kubectl convert -f convert.yaml -o=json
{
"kind": "Pod",
"apiVersion": "v1",
"metadata": {
"name": "envar-demo",
"creationTimestamp": null,
"labels": {
"purpose": "demonstrate-envars"
}
},
"spec": {
"containers": [
{
"name": "envar-demo-container",
"image": "dotnetapp",
"env": [
{
"name": "ConnectionString:Mydb",
"value": "ConnectionString"
}
],
"resources": {},
"terminationMessagePath": "/dev/termination-log",
"terminationMessagePolicy": "File",
"imagePullPolicy": "Always"
}
],
"restartPolicy": "Always",
"terminationGracePeriodSeconds": 30,
"dnsPolicy": "ClusterFirst",
"securityContext": {},
"schedulerName": "default-scheduler"
},
"status": {}
}
However, looks like this was a known issue with Windows/.NET applications. An attempt to fix it has been tried and ditched due to the fact the this is not valid in Bash. But looks like they settled to use the __ instead of : workaround
Yes, example
In the Appsettings.json
"ConnectionStrings": {
"Azure": "Server=tcp:uw2qdisa
In the manifest.yml
env:
- name: ConnectionStrings__Azure
valueFrom:
configMapKeyRef:
name: config-disa
key: ConnectionStrings
Explanation on Kubernetes
Some .Net Core applications expect environment variables with a colon (:) in the name. Kubernetes currently does not allow this. Replace colon (:) with double underscore (__) as documented here.

Ansible: How to use an Azure RM template in `azure_rm_deployment` module?

I have a virtual machine ARM template built in the following way: refernce
{
"$schema": "http://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json",
"contentVersion": "1.0.0.0",
"parameters": { },
"variables": { },
"resources": [ ],
"outputs": { }
}
with parameters.json:
{
"$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json",
"contentVersion": "1.0.0.0",
"parameters": {
"adminUserName": { "value": "mytestacct1" },
"adminPassword": { "value": "mytestpass1" }
}
}
I can successfully deploy the machine using this template in PowerShell:
New-AzureRmResourceGroupDeployment -ResourceGroupName $rgName -TemplateFile VirtualMachineTemplate.json -TemplateParameterFile Parameters.json
However, if I try to use the same template for Ansible azure_rm_deployment module in the following task:
- name: Ensure the VM is deployed to Azure
azure_rm_deployment:
state: present
resource_group_name: "{{ resource_group_name }}"
template: "{{ lookup('file', 'VirtualMachineTemplate.json') }}"
parameters: "{{ lookup('file', 'Parameters.json') }}"
I get an error:
fatal: [localhost]: FAILED! => {"changed": false, "failed": true, "failed_deployment_operations": [], "msg": "Deployment failed with status code: 400 and message: The request content was invalid and could not be deserialized: 'Error converting value \"https://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json\" to type 'Microsoft.WindowsAzure.ResourceStack.Frontdoor.Data.Definitions.DeploymentParameterDefinition'. Path 'properties.parameters.$schema', line 1, position 142.'."}
The error is caused by parameters.json. If I define the parameters directly in the task:
- name: Ensure the VM is deployed to Azure
azure_rm_deployment:
state: present
resource_group_name: "{{ resource_group_name }}"
template: "{{ lookup('file', 'VirtualMachineTemplate.json') }}"
parameters:
adminUserName:
value: mytestacct1
adminPassword:
value: mytestpass1
It deploys the machine.
I'm at loss here. Is there a modification required to the template for the Ansible module?
Notes:
At the same time I can provision resources and VMs using azure_rm_storageaccount, azure_rm_virtualmachine, etc. modules, so I guess it's not a library problem; at least not the Microsoft Azure SDK for Python, which is 2.0.0rc5 per requirements.
Just to make sure I also tried with template_link and parameters_link and the error message is the same.
I see this is rather old question, but I note that there's own field parameters in the parameters file, so the right call should be:
- name: Ensure the VM is deployed to Azure
azure_rm_deployment:
state: present
resource_group_name: "{{ resource_group_name }}"
template: "{{ lookup('file', 'VirtualMachineTemplate.json') }}"
parameters: "{{ (lookup('file', 'Parameters.json') | from_json).parameters }}"

Resources