ADF Shared Self Hosted VM deployment - adfs

I have Self hosted VM IR running on my SIT ADF and this is shared across DEV/UAT.
From DEV(master branch)when i publish it below Attributes are available in my RELEASE and BUILD pipeline
"vm_name": {
"value": "[concat(parameters('factoryName'), '/bi-vm')]"
},
"vm_type": {
"value": "Microsoft.DataFactory/factories/integrationRuntimes"
},
"vm_apiVersion": {
"value": "2018-06-01"
},
"vm_properties": {
"value": {
"type": "SelfHosted",
"typeProperties": {
"linkedInfo": {
"resourceId": "/subscriptions/xxx/resourcegroups/xx/providers/Microsoft.DataFactory/factories/xx/integrationruntimes/vm",
"authorizationType": "Rbac"
}
}
}
},
"vm_dependsOn": {
"value": [
"[variables('factoryId')]"
]
},
Now I wanted to add variable to these 4 parameter(vm_name,vm_apiVersion,vm_properties,vm_dependsOn) in Library and link them in BUILD Override template parameters.
but it fails at very beginning giving error
##[error]The request content was invalid and could not be deserialized: 'Error converting value "[parameters('vm_dependsOn')]" to type 'Azure.Deployments.Core.Entities.TemplateGenericProperty`1[System.String][]'. Path 'properties.template.resources[71].dependsOn', line 1, position 254524.'.
how to fix this?how can i pass these 4 variable to Override template parameters

Related

ARM template deployment error for Appinsights roleassignments

We are using below ARM template for role assignement in Appinsights with ADO pipelines, where the template parameters are replacing from ADO pipelines paramters. This worked for one resource deployment and when we tried for multiple resources, ARM template deployment failing with below error.
{
"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"RoleDefinitionId": {
"type": "string"
},
"principalId": {
"type": "string"
},
"AppInsightName": {
"type": "string"
}
},
"resources":[
{
"type": "Microsoft.Insights/components/providers/roleAssignments",
"apiVersion": "2017-05-01",
"name": "[concat(parameters('AppInsightName'),'/Microsoft.Authorization/',guid('AppInsightName'))]",
"properties": {
"roleDefinitionId": "[resourceId('Microsoft.Authorization/roleDefinitions', parameters('RoleDefinitionId'))]",
"principalId": "[parameters('principalId')]"
}
}
]
}
Parameters.json
{
"$schema": "https://schema.management.azure.com/schemas/2015-01-01/deploymentParameters.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"RoleDefinitionId": {
"value": "#{roleDefinitionId}#"
},
"principalId": {
"value": "#{principalId}#"
},
"AppInsightName": {
"value": "#{appInsightName}#"
}
}
}
Input to devops pipeline yaml
parameters:
roleList:
- rolesname: reader_Appinsight_group1
environment: development
principalType: Group
principalid: xxxxxxxxxxxxxxxxxxxxxxxxxxxxx
roleDefinitionId: acdd72axxxxxxxxxxxxxxxxxxxxx
appInsightName: myappinsight1
resourceGroup: myappinsight1-rg
- rolesname: reader_Appinsight_group2
environment: development
principalType: Group
principalid: xxxxxxxxxxxxxxxxxxxxxxxxxx
roleDefinitionId: acdd72axxxxxxxxxxxxxxxxxxxxxxxx
appInsightName: myappinsight1
resourceGroup: myappinsight1-rg
ERROR:
{"status":"Failed","error":{"code":"DeploymentFailed","message":"At least one resource deployment operation failed. Please list deployment operations for details. Please see https://aka.ms/DeployOperations for usage details.","details":[{"code":"BadRequest","message":"{\r\n \"error\": {\r\n \"code\": \"RoleAssignmentUpdateNotPermitted\",\r\n \"message\": \"Tenant ID, application ID, principal ID, and scope are not allowed to be updated.\"\r\n }\r\n}"}]}}
Again I tried with multiple option for the role definition name to be unique, but got different errors
eg:
"resources":[
{
"type": "Microsoft.Insights/components/providers/roleAssignments",
"apiVersion": "2017-05-01",
"name": "[guid(resourceGroup().id, parameters('RoleDefinitionId'), parameters('principalId'))]",
"properties": {
"roleDefinitionId": "[resourceId('Microsoft.Authorization/roleDefinitions', parameters('RoleDefinitionId'))]",
"principalId": "[parameters('principalId')]"
}
}
]
}
Error for the above
The template resource 'xxxxxxxxxxxxxxxxxxxxxxxx for type 'Microsoft.Insights/components/providers/roleAssignments' at line '18' and column '71' has incorrect segment lengths
The name of a roleAssignment needs to be a function of the principal, role and scope. Once a role exists for a given principal, role & scope under a given name, nothing can be changed on that role assignment.
In your template your roleAssignment name is just a function of the appInsights resource name, which means you can have exactly one of those roleAssignments. Your guid() function in the name needs to be:
guid(parameters('RoleDefinitionId'), parameters('principalId'), parameters('AppInsightName'))
Note that you may have to remove some previously created roleAssignments (for the given principal, role and scope) if they were not created with the same naming algorithm before that template will successfully deploy.

Put Azure Key Vault value in parameter array

I am trying to deploy a App service webapp via ARM template and need to put a secret from a key vault into an app setting (env variable).
I have always simply used an array of values from a parameters file to populate these app settings, but now I am struggling to get a keyvault value into that array. Something like shown below in an ARM parameter file.
{
"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"someStringParam": {
"value": "stringLiteralValueHere"
},
"envVars": {
"value": [
{
"name": "envVarKeyName",
"value": "stringLiteralValueHere"
},
{
"name": "KVsecret1",
"value": ##KEY VAULT SECRET HERE##
}
]
}
}
}
I have tried using a reference to the keyvault for the value but that errors on deployment.
{
"name": "KVsecret1",
"reference": {
"keyVault": {
"id": "/subscriptions/<subscription_id>/resourceGroups/<resource_group>/providers/Microsoft.KeyVault/vaults/<vault_name>"
},
"secretName": "secret1"
}
}
I have also tried using a parameter inside of the parameter file, but that just used the literal string for the value.
"parameters": {
"KVsecret1": {
"reference": {
"keyVault": {
"id": "/subscriptions/<subscription_id>/resourceGroups/<resource_group>/providers/Microsoft.KeyVault/vaults/<vault_name>"
},
"secretName": "KVsecret1"
}
},
"envVars": {
"value": [
{
"name": "envVarKeyName",
"value": "stringLiteralValueHere"
},
{
"name": "KVsecret1",
"value": "[parameters('KVsecret1')]"
}
]
}
}
Is this possible??
EDIT: Adding some detail here.
I am also trying to shoe horn a reference to another resource to get put the app insights instrumentation key into an app setting. Below is what I would like to do, but the copy function needs to use the name of the property and that is dynamic in this case as it changes with the each member of the array from the parameter file.
{
"type": "Microsoft.Web/sites/config",
"apiVersion": "2022-03-01",
"name": "[concat(parameters('backEndwebAppName'),'/appsettings')]",
"kind": "string",
"properties": {
"APPINSIGHTS_INSTRUMENTATIONKEY": "[reference(concat('microsoft.insights/components/',parameters('appInsightsName')),'2020-02-02').InstrumentationKey]",
"secret1FromKeyvault": "[parameters('secret1FromKeyvault')]",
"copy": [
{
"name": "envVarsFromParams",
"count": "[length(parameters('backEndEnvVariables'))]",
"input": {
"name": "[parameters('backEndEnvVariables')[copyIndex('envVarsFromParams').name]]",
"value": "[parameters('backEndEnvVariables')[copyIndex('envVarsFromParams').value]]"
}
}
]
},
"dependsOn": [
"[resourceId('Microsoft.Web/sites', parameters('backEndwebAppName'))]"
]
},
This isn't possible today within the param file, but in your scenario (if it's as simple as your OP example) you can just union the two in your template. So in your parameter file, you have 2 params kvSecret (the reference) and envVars (all your other env vars) and then in the template use:
"variables": {
"keySecretObj": {
"name": "kvSecret",
"value": "[parameters('kvSecret')]"
},
"envVarsFinal": "[union(parameters(variables('kvSecretObj`), parameters(`envVars`))]"
That help?

Exception in function does not return exceptions on functions in function monitor

The azure function is a .net core class library that will receive the message based on the namespace of the model being sent (in the filter as eventType) as an . All deployments are being done using arm templates, which is where this struggle is originating from. The function and eventgrid are deployed fine, but I don't know what i'm doing wrong with the subscription. If I create the subscription in the portal then the handler receives the message and displays traffic on the monitor. If I create the subscription as below then it appears exactly the same in the portal as the portal created one but nothing shows up in the monitor. Am I missing a resource or connection that still needs to be created? I read about system topics and how they're made implicitly in some instances but can be made explicitly, is that what I'm missing? This would be easier to debug if there was a place to export the template for those subscriptions but I don't see them.
Function handler
[FunctionName("FunctionName")]
public async Task Run([EventGridTrigger]EventGridEvent eventGridEvent)
{
...
}
}
eventgrid creation
{
"type": "Microsoft.EventGrid/topics",
"apiVersion": "2020-06-01",
"name": "[variables('EventGridName')]",
"location": "[resourceGroup().location]"
}
subscription creations
{
"name": "[concat(variables('eventSubscriptions')[copyIndex()].eventGridName, '/Microsoft.EventGrid/', variables('eventSubscriptions')[copyIndex()].name)]",
"type": "Microsoft.EventGrid/topics/providers/eventSubscriptions",
"apiVersion": "2020-01-01-preview",
"location": "[resourceGroup().location]",
"copy": {
"name": "subscriptionCopy",
"count": "[length(variables('eventSubscriptions'))]"
},
"properties": {
"topic": "[concat('/subscriptions/', subscription().subscriptionId,'/resourcegroups/', resourceGroup().name, '/providers/Microsoft.EventGrid/topics/', variables('eventSubscriptions')[copyIndex()].eventGridName)]",
"destination": {
"endpointType": "AzureFunction",
"properties": {
"resourceId": "[concat('/subscriptions/', subscription().subscriptionId,'/resourcegroups/', resourceGroup().name, '/providers/Microsoft.Web/sites/', variables('eventSubscriptions')[copyIndex()].functionApp, '/functions/' , variables('eventSubscriptions')[copyIndex()].functionName)]",
"maxEventsPerBatch": 1,
"preferredBatchSizeInKilobytes": 64
}
},
"filter": {
"includedEventTypes": [
"[variables('eventSubscriptions')[copyIndex()].eventType]"
]
},
"labels": [],
"eventDeliverySchema": "EventGridSchema"
},
"dependsOn": [
]
}

Getting "parent resource not found" during ARM template deployment

I have private DNS zone zone.private which is already deployed in resource group and I'm trying to add A record to it with ARM template below which fails with Status Message: Can not perform requested operation on nested resource. Parent resource 'zone.private' not found. (Code:ParentResourceNotFound)
I'm supposed to be able to refer to refer to resources deployed in the same resource group to deploy nested resources but it fails for whatever reason. I have another zone called zone.domain.com deployed to the same resource group and deploying to that succeeds with no issues.
{
"type": "Microsoft.Network/dnsZones/A",
"apiVersion": "2018-05-01",
"name": "[concat('zone.private', '/', 'webexport-lb')]",
"properties": {
"TTL": 3600,
"ARecords": [
{
"ipv4Address": "1.1.1.1"
}
]
}
},
If you have a private DNS zone, you could use Microsoft.Network/privateDnsZones/A instead of Microsoft.Network/dnsZones/A.
So change it like this:
{
"type": "Microsoft.Network/privateDnsZones/A",
"apiVersion": "2018-09-01",
"name": "[concat('zone.private', '/', 'webexport-lb')]",
"properties": {
"ttl": 3600,
"aRecords": [
{
"ipv4Address": "1.1.1.1"
}
]
}
}

Passing Parameter Values to DSC Configuration from ARM Template

I have a simple DSC Config file that contains a credential and string input parameter. I want this DSC configuration deployed with a VM deployed in an ARM template but am missing the concept of how to pass these two parameters securely. How do I accomplish this?
I was receiving the same error but, after some shenanigans, it is working for me. The important part is the settings/Properties/SqlAgentCred/password reference to protectedSettings/Items/AgentPassword. Below is the properties node under my Powershell.DSC extension resource in my template.
"properties": {
"publisher": "Microsoft.Powershell",
"type": "DSC",
"typeHandlerVersion": "2.17",
"autoUpgradeMinorVersion": false,
"settings": {
"ModulesUrl": "https://blobstore.blob.core.windows.net/windows-powershell-dsc/DBServer.ps1.zip",
"ConfigurationFunction": "DBServer.ps1\\DBServer",
"Properties": {
"SqlAgentCred": {
"userName": "user#domain.com",
"password": "PrivateSettingsRef:AgentPassword"
}
},
"WmfVersion": "latest",
"Privacy": {
"DataCollection": "Disable"
}
},
"protectedSettings": {
"Items": {
"AgentPassword": "Pa$$word"
},
"DataBlobUri": ""
}
}
You will specify protected settings under protectedsettings section. Anything under ProtectedSettings are sent encrypted. Check https://blogs.msdn.microsoft.com/powershell/2016/02/26/arm-dsc-extension-settings/ for details.

Resources