Esercizio - Aggiungere parametri agli script di distribuzione
Ora che è stato usato uno script di distribuzione per eseguire la migrazione di alcune operazioni manuali nel modello di Azure Resource Manager, un altro team di applicazioni partner dell'organizzazione chiede aiuto.
Il processo del team ha requisiti simili, ma il team deve distribuire più file nel proprio account di archiviazione. Il team ha uno script di PowerShell che può accettare un elenco di file come parametro e caricarli, in modo simile allo script già in uso nel modello.
In questo esercizio si userà il modello precedente come punto di partenza e si aggiornerà lo script di PowerShell per usare quello del team partner. Si aggiungerà quindi un modo per consentire alla persona che distribuisce il modello di specificare uno o più file di configurazione da distribuire.
Durante il processo, si eseguiranno queste operazioni:
- Aggiornare lo script di distribuzione.
- Aggiungere una variabile di ambiente e un parametro del modello e passarli allo script di distribuzione.
- Aggiungere un output allo script di distribuzione.
- Aggiungere un file di parametri.
- Distribuire il modello e verificare il risultato.
Creare il modello iniziale
Si inizia con il modello creato nell'ultimo esercizio.
Aprire Visual Studio Code e creare un nuovo file denominato azuredeploy.json.
Copiare il modello iniziale seguente in azuredeploy.json.
{ "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#", "contentVersion": "1.0.0.1", "apiProfile": "", "parameters": {}, "variables": { "storageAccountName": "[concat('storage', uniqueString(resourceGroup().id))]", "storageBlobContainerName": "config", "userAssignedIdentityName": "configDeployer", "roleAssignmentName": "[guid(concat(resourceGroup().id, 'contributor'))]", "contributorRoleDefinitionId": "[resourceId('Microsoft.Authorization/roleDefinitions', 'b24988ac-6180-42a0-ab88-20f7382dd24c')]", "deploymentScriptName": "CopyConfigScript" }, "functions": [], "resources": [ { "name": "[variables('storageAccountName')]", "type": "Microsoft.Storage/storageAccounts", "apiVersion": "2023-01-01", "tags": { "displayName": "[variables('storageAccountName')]" }, "location": "[resourceGroup().location]", "kind": "StorageV2", "sku": { "name": "Standard_LRS", "tier": "Standard" }, "properties": { "allowBlobPublicAccess": true, "encryption": { "services": { "blob": { "enabled": true } }, "keySource": "Microsoft.Storage" }, "supportsHttpsTrafficOnly": true } }, { "type": "Microsoft.Storage/storageAccounts/blobServices", "apiVersion": "2019-04-01", "name": "[concat(variables('storageAccountName'), '/default')]", "dependsOn": [ "[resourceId('Microsoft.Storage/storageAccounts', variables('storageAccountName'))]" ] }, { "type": "Microsoft.Storage/storageAccounts/blobServices/containers", "apiVersion": "2019-04-01", "name": "[concat(variables('storageAccountName'),'/default/',variables('storageBlobContainerName'))]", "dependsOn": [ "[resourceId('Microsoft.Storage/storageAccounts/blobServices', variables('storageAccountName'), 'default')]", "[resourceId('Microsoft.Storage/storageAccounts', variables('storageAccountName'))]" ], "properties": { "publicAccess": "Blob" } }, { "type": "Microsoft.ManagedIdentity/userAssignedIdentities", "apiVersion": "2018-11-30", "name": "[variables('userAssignedIdentityName')]", "location": "[resourceGroup().location]" }, { "type": "Microsoft.Authorization/roleAssignments", "apiVersion": "2020-04-01-preview", "name": "[variables('roleAssignmentName')]", "dependsOn": [ "[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', variables('userAssignedIdentityName'))]" ], "properties": { "roleDefinitionId": "[variables('contributorRoleDefinitionId')]", "principalId": "[reference(resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', variables('userAssignedIdentityName')), '2015-08-31-preview').principalId]", "scope": "[resourceGroup().id]", "principalType": "ServicePrincipal" } }, { "type": "Microsoft.Resources/deploymentScripts", "apiVersion": "2020-10-01", "name": "[variables('deploymentScriptName')]", "location": "[resourceGroup().location]", "kind": "AzurePowerShell", "dependsOn": [ "[resourceId('Microsoft.Authorization/roleAssignments', variables('roleAssignmentName'))]", "[resourceId('Microsoft.Storage/storageAccounts/blobServices/containers', variables('storageAccountName'), 'default', variables('storageBlobContainerName'))]" ], "identity": { "type": "UserAssigned", "userAssignedIdentities": { "[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities',variables('userAssignedIdentityName'))]": {} } }, "properties": { "azPowerShellVersion": "3.0", "scriptContent": " Invoke-RestMethod -Uri 'https://raw.githubusercontent.com/Azure/azure-docs-json-samples/master/mslearn-arm-deploymentscripts-sample/appsettings.json' -OutFile 'appsettings.json' $storageAccount = Get-AzStorageAccount -ResourceGroupName 'learndeploymentscript_exercise_1' | Where-Object { $_.StorageAccountName -like 'storage*' } $blob = Set-AzStorageBlobContent -File 'appsettings.json' -Container 'config' -Blob 'appsettings.json' -Context $StorageAccount.Context $DeploymentScriptOutputs = @{} $DeploymentScriptOutputs['Uri'] = $blob.ICloudBlob.Uri $DeploymentScriptOutputs['StorageUri'] = $blob.ICloudBlob.StorageUri ", "retentionInterval": "P1D" } } ], "outputs": { "fileUri": { "type": "string", "value": "[reference(variables('deploymentScriptName')).outputs.Uri]" } } }
Scegliere Salva per salvare il modello.
Aprire Visual Studio Code e creare un nuovo file denominato main.bicep.
Copiare il modello iniziale seguente in main.bicep.
var storageAccountName = 'storage${uniqueString(resourceGroup().id)}' var storageBlobContainerName = 'config' var userAssignedIdentityName = 'configDeployer' var roleAssignmentName = guid(resourceGroup().id, 'contributor') var contributorRoleDefinitionId = resourceId('Microsoft.Authorization/roleDefinitions', 'b24988ac-6180-42a0-ab88-20f7382dd24c') var deploymentScriptName = 'CopyConfigScript' resource storageAccount 'Microsoft.Storage/storageAccounts@2023-01-01' = { name: storageAccountName tags: { displayName: storageAccountName } location: resourceGroup().location kind: 'StorageV2' sku: { name: 'Standard_LRS' tier: 'Standard' } properties: { allowBlobPublicAccess: true encryption: { services: { blob: { enabled: true } } keySource: 'Microsoft.Storage' } supportsHttpsTrafficOnly: true } resource blobService 'blobServices' existing = { name: 'default' } } resource blobContainer 'Microsoft.Storage/storageAccounts/blobServices/containers@2019-04-01' = { parent: storageAccount::blobService name: storageBlobContainerName properties: { publicAccess: 'Blob' } } resource userAssignedIdentity 'Microsoft.ManagedIdentity/userAssignedIdentities@2018-11-30' = { name: userAssignedIdentityName location: resourceGroup().location } resource roleAssignment 'Microsoft.Authorization/roleAssignments@2020-04-01-preview' = { name: roleAssignmentName properties: { roleDefinitionId: contributorRoleDefinitionId principalId: userAssignedIdentity.properties.principalId principalType: 'ServicePrincipal' } } resource deploymentScript 'Microsoft.Resources/deploymentScripts@2020-10-01' = { name: deploymentScriptName location: resourceGroup().location kind: 'AzurePowerShell' identity: { type: 'UserAssigned' userAssignedIdentities: { '${userAssignedIdentity.id}': {} } } properties: { azPowerShellVersion: '3.0' scriptContent: ''' Invoke-RestMethod -Uri 'https://raw.githubusercontent.com/Azure/azure-docs-json-samples/master/mslearn-arm-deploymentscripts-sample/appsettings.json' -OutFile 'appsettings.json' $storageAccount = Get-AzStorageAccount -ResourceGroupName 'learndeploymentscript_exercise_1' | Where-Object { $_.StorageAccountName -like 'storage*' } $blob = Set-AzStorageBlobContent -File 'appsettings.json' -Container 'config' -Blob 'appsettings.json' -Context $storageAccount.Context $DeploymentScriptOutputs = @{} $DeploymentScriptOutputs['Uri'] = $blob.ICloudBlob.Uri $DeploymentScriptOutputs['StorageUri'] = $blob.ICloudBlob.StorageUri ''' retentionInterval: 'P1D' } dependsOn: [ roleAssignment blobContainer ] } output fileUri string = deploymentScript.properties.outputs.Uri
Scegliere Salva per salvare il modello.
Aggiornare lo script di PowerShell
Poiché l'altro team ha già svolto le operazioni necessarie per creare uno script di PowerShell per copiare più file, si decide di usare tale script nel modello.
Modificare scriptContent
nella sezione properties
per includere lo script fornito dal team partner.
param([string]$File)
$fileList = $File -replace '(\[|\])' -split ',' | ForEach-Object { $_.trim() }
$storageAccount = Get-AzStorageAccount -ResourceGroupName $env:ResourceGroupName -Name $env:StorageAccountName -Verbose
$count = 0
$DeploymentScriptOutputs = @{}
foreach ($fileName in $fileList) {
Write-Host \"Copying $fileName to $env:StorageContainerName in $env:StorageAccountName.\"
Invoke-RestMethod -Uri \"https://raw.githubusercontent.com/Azure/azure-docs-json-samples/master/mslearn-arm-deploymentscripts-sample/$fileName\" -OutFile $fileName
$blob = Set-AzStorageBlobContent -File $fileName -Container $env:StorageContainerName -Blob $fileName -Context $storageAccount.Context
$DeploymentScriptOutputs[$fileName] = @{}
$DeploymentScriptOutputs[$fileName]['Uri'] = $blob.ICloudBlob.Uri
$DeploymentScriptOutputs[$fileName]['StorageUri'] =$blob.ICloudBlob.StorageUri
$count++
}
Write-Host \"Finished copying $count files.\"
param([string]$File)
$fileList = $File -replace '(\[|\])' -split ',' | ForEach-Object { $_.trim() }
$storageAccount = Get-AzStorageAccount -ResourceGroupName $env:ResourceGroupName -Name $env:StorageAccountName -Verbose
$count = 0
$DeploymentScriptOutputs = @{}
foreach ($fileName in $fileList) {
Write-Host "Copying $fileName to $env:StorageContainerName in $env:StorageAccountName."
Invoke-RestMethod -Uri "https://raw.githubusercontent.com/Azure/azure-docs-json-samples/master/mslearn-arm-deploymentscripts-sample/$fileName" -OutFile $fileName
$blob = Set-AzStorageBlobContent -File $fileName -Container $env:StorageContainerName -Blob $fileName -Context $storageAccount.Context
$DeploymentScriptOutputs[$fileName] = @{}
$DeploymentScriptOutputs[$fileName]['Uri'] = $blob.ICloudBlob.Uri
$DeploymentScriptOutputs[$fileName]['StorageUri'] = $blob.ICloudBlob.StorageUri
$count++
}
Write-Host "Finished copying $count files."
Aggiungere una variabile di ambiente
Lo script adottato richiede alcune variabili di ambiente. È possibile specificarle direttamente nel modello, ma risulta più flessibile usare le funzioni del modello per ottenere alcuni dei valori.
Aggiungere una proprietà
environmentVariables
alla sezioneproperties
dello script di distribuzione."environmentVariables": [ ],
Aggiungere una variabile di ambiente per
ResourceGroupName
."environmentVariables": [ { "name": "ResourceGroupName", "value": "[resourceGroup().name]" } ],
Aggiungere una variabile di ambiente per
StorageAccountName
."environmentVariables": [ { "name": "ResourceGroupName", "value": "[resourceGroup().name]" }, { "name": "StorageAccountName", "value": "[variables('storageAccountName')]" } ],
Aggiungere una variabile di ambiente per
StorageContainerName
."environmentVariables": [ { "name": "ResourceGroupName", "value": "[resourceGroup().name]" }, { "name": "StorageAccountName", "value": "[variables('storageAccountName')]" }, { "name": "StorageContainerName", "value": "[variables('storageBlobContainerName')]" } ],
Suggerimento
Usare le funzioni del modello per accedere a valori comuni come e [resourceGroup().name]
[variables()]
.
Lo script adottato richiede alcune variabili di ambiente. È possibile specificarle direttamente nel modello, ma risulta più flessibile usare variabili di Bicep per ottenere alcuni dei valori.
Aggiungere una proprietà
environmentVariables
alla sezioneproperties
dello script di distribuzione.environmentVariables: [ ]
Aggiungere una variabile di ambiente per
ResourceGroupName
.environmentVariables: [ { name: 'ResourceGroupName' value: resourceGroup().name } ]
Aggiungere una variabile di ambiente per
StorageAccountName
.environmentVariables: [ { name: 'ResourceGroupName' value: resourceGroup().name } { name: 'StorageAccountName' value: storageAccountName } ]
Aggiungere una variabile di ambiente per
StorageContainerName
.environmentVariables: [ { name: 'ResourceGroupName' value: resourceGroup().name } { name: 'StorageAccountName' value: storageAccountName } { name: 'StorageContainerName' value: storageBlobContainerName } ]
Aggiungere un parametro del modello
Per semplificare l'uso del modello da parte dei due team, è possibile aggiungervi un parametro in modo che ogni team possa specificare i file da copiare.
Aggiungere un parametro al modello per accettare una matrice di nomi file.
"parameters": {
"filesToCopy": {
"type": "array",
"metadata": {
"description": "List of files to copy to application storage account."
}
}
},
Come extra, specificare un valore predefinito in modo che il modello continui a funzionare per il team senza apportare modifiche al processo di distribuzione. Anche se non obbligatoria, l'immissione di un nuovo valore predefinito consente di comprendere l'attività di rendere più semplice per i team l'adozione di nuove versioni di modelli se continuano a comportarsi come in precedenza, e la nuova funzionalità rappresenta la ricompensa. In altre parole, questo passaggio illustra come mantenere il comportamento esistente apportando le modifiche per supportare il lavoro futuro.
Aggiungere un parametro al modello per accettare una matrice di nomi file.
@description('List of files to copy to application storage account.')
param filesToCopy array
Come extra, specificare un valore predefinito in modo che il modello continui a funzionare per il team senza apportare modifiche al processo di distribuzione. Anche se non obbligatoria, l'immissione di un nuovo valore predefinito consente di comprendere l'attività di rendere più semplice per i team l'adozione di nuove versioni di modelli se continuano a comportarsi come in precedenza, e la nuova funzionalità rappresenta la ricompensa. In altre parole, questo passaggio illustra come mantenere il comportamento esistente apportando le modifiche per supportare il lavoro futuro.
Aggiungere un argomento da passare nei file da copiare
Successivamente, è possibile passare il parametro appena definito allo script di distribuzione. Il passaggio di argomenti della riga di comando può essere complicato, perché le stringhe vengono valutate a più livelli. L'aggiunta di virgolette di escape corrette e la selezione delle virgolette giuste sono essenziali per il successo dell'operazione.
Suggerimento
Usare le funzioni del modello per accedere a funzioni comuni come [string()]
per convertire i valori di un tipo in una stringa.
Aggiungere una proprietà
arguments
allo script di distribuzione. Lo script di PowerShell accetta un parametro denominatoFile
, ovvero una stringa di nomi file che devono derivare dal parametro del modellofilesToCopy
. Assicurarsi che siano presenti virgolette intorno all'intero argomento in modo che venga passato correttamente.Attenzione
La proprietà
arguments
non è valida. Se si usa l'estensione Azure Resource Manager in Visual Studio Code, questa riga potrebbe essere contrassegnata. Questo problema verrà risolto nei passaggi successivi."arguments": "[concat( '-File '', string(parameters('filesToCopy')), ''' )]",
Suggerimento
L'aggiunta di virgolette in JSON può essere difficile, soprattutto quando si passano argomenti della riga di comando. È possibile usare una variabile modello per rappresentare un carattere di cui è difficile eseguire l'escape.
Aggiungere una variabile modello per rappresentare il carattere virgoletta singola.
"variables": { "singleQuote": "'", "storageAccountName": "[concat('storage', uniqueString(resourceGroup().id))]", "storageBlobContainerName": "config", "userAssignedIdentityName": "configDeployer", "roleAssignmentName": "[guid(concat(resourceGroup().id, 'contributor'))]", "contributorRoleDefinitionId": "[resourceId('Microsoft.Authorization/roleDefinitions', 'b24988ac-6180-42a0-ab88-20f7382dd24c')]", "deploymentScriptName": "CopyConfigScript" },
Sostituire le virgolette singole nella proprietà
arguments
con la variabile appena definita."arguments": "[concat( '-File ', variables('singleQuote'), string(parameters('filesToCopy')), variables('singleQuote'))]",
Successivamente, è possibile passare il parametro appena definito allo script di distribuzione. Il passaggio di argomenti della riga di comando può essere complicato, perché le stringhe vengono valutate a più livelli. L'aggiunta di virgolette di escape corrette e la selezione delle virgolette giuste sono essenziali per il successo dell'operazione.
Aggiungere una proprietà arguments
allo script di distribuzione. Lo script di PowerShell accetta un parametro denominato File
, ovvero una stringa di nomi file che devono derivare dal parametro del modello filesToCopy
.
arguments: '-File \'${string(filesToCopy)}\''
Si noti che si usano diverse funzionalità di Bicep:
- Interpolazione di stringhe, per combinare le stringhe.
- Si usa il carattere di escape
\
per consentire di includere un carattere virgoletta singola ('
) all'interno della stringa, perché tale carattere è in genere riservato in Bicep. - Si usa la funzione
string()
per convertire la matricefilesToCopy
in una stringa.
Aggiornare l'output del modello
Poiché si sta modificando lo script di distribuzione per distribuire uno o più file, è necessario aggiornare l'output del modello per fornire tutte le informazioni necessarie.
Aggiornare
outputs
nel modello per restituire l'intero oggetto, che avrà un URI per ogni file.$DeploymentScriptOutputs = @{} foreach ($fileName in $fileList) { Write-Host \"Copying $fileName to $env:StorageContainerName in $env:StorageAccountName.\" Invoke-RestMethod -Uri \"https://raw.githubusercontent.com/Azure/azure-docs-json-samples/master/mslearn-arm-deploymentscripts-sample/$fileName\" -OutFile $fileName $blob = Set-AzStorageBlobContent -File $fileName -Container $env:StorageContainerName -Blob $fileName -Context $storageAccount.Context $DeploymentScriptOutputs[$fileName] = @{} $DeploymentScriptOutputs[$fileName]['Uri'] = $blob.ICloudBlob.Uri $DeploymentScriptOutputs[$fileName]['StorageUri'] =$blob.ICloudBlob.StorageUri $count++ }
Aggiungere un altro output con il nome dell'account di archiviazione (che ha un identificatore casuale). Verrà utilizzato in seguito per verificare che lo script di distribuzione abbia eseguito le attività previste.
$DeploymentScriptOutputs = @{} foreach ($fileName in $fileList) { Write-Host \"Copying $fileName to $env:StorageContainerName in $env:StorageAccountName.\" Invoke-RestMethod -Uri \"https://raw.githubusercontent.com/Azure/azure-docs-json-samples/master/mslearn-arm-deploymentscripts-sample/$fileName\" -OutFile $fileName $blob = Set-AzStorageBlobContent -File $fileName -Container $env:StorageContainerName -Blob $fileName -Context $storageAccount.Context $DeploymentScriptOutputs[$fileName] = @{} $DeploymentScriptOutputs[$fileName]['Uri'] = $blob.ICloudBlob.Uri $DeploymentScriptOutputs[$fileName]['StorageUri'] =$blob.ICloudBlob.StorageUri $count++ }
Aggiornare gli output nel modello per restituire l'intero oggetto, che avrà un URI per ogni file.
output fileUri object = deploymentScript.properties.outputs
Aggiungere un altro output con il nome dell'account di archiviazione (che ha un identificatore casuale). Verrà utilizzato in seguito per verificare che lo script di distribuzione abbia eseguito le attività previste.
output storageAccountName string = storageAccountName
Verificare il modello
Il modello deve avere un aspetto analogo al seguente:
{
"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.1",
"apiProfile": "",
"parameters": {
"filesToCopy": {
"type": "array",
"defaultValue": [ "appsettings.json" ],
"metadata": {
"description": "List of files to copy to application storage account."
}
}
},
"variables": {
"singleQuote": "'",
"storageAccountName": "[concat('storage', uniqueString(resourceGroup().id))]",
"storageBlobContainerName": "config",
"userAssignedIdentityName": "configDeployer",
"roleAssignmentName": "[guid(concat(resourceGroup().id, 'contributor'))]",
"contributorRoleDefinitionId": "[resourceId('Microsoft.Authorization/roleDefinitions', 'b24988ac-6180-42a0-ab88-20f7382dd24c')]",
"deploymentScriptName": "CopyConfigScript"
},
"functions": [],
"resources": [
{
"name": "[variables('storageAccountName')]",
"type": "Microsoft.Storage/storageAccounts",
"apiVersion": "2023-01-01",
"tags": {
"displayName": "[variables('storageAccountName')]"
},
"location": "[resourceGroup().location]",
"kind": "StorageV2",
"sku": {
"name": "Standard_LRS",
"tier": "Standard"
},
"properties": {
"allowBlobPublicAccess": true,
"encryption": {
"services": {
"blob": {
"enabled": true
}
},
"keySource": "Microsoft.Storage"
},
"supportsHttpsTrafficOnly": true
}
},
{
"type": "Microsoft.Storage/storageAccounts/blobServices",
"apiVersion": "2019-04-01",
"name": "[concat(variables('storageAccountName'), '/default')]",
"dependsOn": [
"[resourceId('Microsoft.Storage/storageAccounts', variables('storageAccountName'))]"
]
},
{
"type": "Microsoft.Storage/storageAccounts/blobServices/containers",
"apiVersion": "2019-04-01",
"name": "[concat(variables('storageAccountName'),'/default/',variables('storageBlobContainerName'))]",
"dependsOn": [
"[resourceId('Microsoft.Storage/storageAccounts/blobServices', variables('storageAccountName'), 'default')]",
"[resourceId('Microsoft.Storage/storageAccounts', variables('storageAccountName'))]"
],
"properties": {
"publicAccess": "Blob"
}
},
{
"type": "Microsoft.ManagedIdentity/userAssignedIdentities",
"apiVersion": "2018-11-30",
"name": "[variables('userAssignedIdentityName')]",
"location": "[resourceGroup().location]"
},
{
"type": "Microsoft.Authorization/roleAssignments",
"apiVersion": "2020-04-01-preview",
"name": "[variables('roleAssignmentName')]",
"dependsOn": [ "[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', variables('userAssignedIdentityName'))]" ],
"properties": {
"roleDefinitionId": "[variables('contributorRoleDefinitionId')]",
"principalId": "[reference(resourceId('Microsoft.ManagedIdentity/userAssignedIdentities', variables('userAssignedIdentityName')), '2015-08-31-preview').principalId]",
"scope": "[resourceGroup().id]",
"principalType": "ServicePrincipal"
}
},
{
"type": "Microsoft.Resources/deploymentScripts",
"apiVersion": "2020-10-01",
"name": "[variables('deploymentScriptName')]",
"location": "[resourceGroup().location]",
"kind": "AzurePowerShell",
"dependsOn": [
"[resourceId('Microsoft.Authorization/roleAssignments', variables('roleAssignmentName'))]",
"[resourceId('Microsoft.Storage/storageAccounts/blobServices/containers', variables('storageAccountName'), 'default', variables('storageBlobContainerName'))]"
],
"identity": {
"type": "UserAssigned",
"userAssignedIdentities": {
"[resourceId('Microsoft.ManagedIdentity/userAssignedIdentities',variables('userAssignedIdentityName'))]": {}
}
},
"properties": {
"arguments": "[concat( '-File ', variables('singleQuote'), string(parameters('filesToCopy')), variables('singleQuote'))]",
"environmentVariables": [
{
"name": "ResourceGroupName",
"value": "[resourceGroup().name]"
},
{
"name": "StorageAccountName",
"value": "[variables('storageAccountName')]"
},
{
"name": "StorageContainerName",
"value": "[variables('storageBlobContainerName')]"
}
],
"azPowerShellVersion": "3.0",
"scriptContent": "
param([string]$File)
$fileList = $File -replace '(\[|\])' -split ',' | ForEach-Object { $_.trim() }
$storageAccount = Get-AzStorageAccount -ResourceGroupName $env:ResourceGroupName -Name $env:StorageAccountName -Verbose
$count = 0
$DeploymentScriptOutputs = @{}
foreach ($fileName in $fileList) {
Write-Host \"Copying $fileName to $env:StorageContainerName in $env:StorageAccountName.\"
Invoke-RestMethod -Uri \"https://raw.githubusercontent.com/Azure/azure-docs-json-samples/master/mslearn-arm-deploymentscripts-sample/$fileName\" -OutFile $fileName
$blob = Set-AzStorageBlobContent -File $fileName -Container $env:StorageContainerName -Blob $fileName -Context $storageAccount.Context
$DeploymentScriptOutputs[$fileName] = @{}
$DeploymentScriptOutputs[$fileName]['Uri'] = $blob.ICloudBlob.Uri
$DeploymentScriptOutputs[$fileName]['StorageUri'] =$blob.ICloudBlob.StorageUri
$count++
}
Write-Host \"Finished copying $count files.\"
",
"retentionInterval": "P1D"
}
}
],
"outputs": {
"fileUri": {
"type": "object",
"value": "[reference(variables('deploymentScriptName')).outputs]"
},
"storageAccountName": {
"type": "string",
"value": "[variables('storageAccountName')]"
}
}
}
@description('List of files to copy to application storage account.')
param filesToCopy array = [
'appsettings.json'
]
var storageAccountName = 'storage${uniqueString(resourceGroup().id)}'
var storageBlobContainerName = 'config'
var userAssignedIdentityName = 'configDeployer'
var roleAssignmentName = guid(resourceGroup().id, 'contributor')
var contributorRoleDefinitionId = resourceId('Microsoft.Authorization/roleDefinitions', 'b24988ac-6180-42a0-ab88-20f7382dd24c')
var deploymentScriptName = 'CopyConfigScript'
resource storageAccount 'Microsoft.Storage/storageAccounts@2023-01-01' = {
name: storageAccountName
tags: {
displayName: storageAccountName
}
location: resourceGroup().location
kind: 'StorageV2'
sku: {
name: 'Standard_LRS'
tier: 'Standard'
}
properties: {
allowBlobPublicAccess: true
encryption: {
services: {
blob: {
enabled: true
}
}
keySource: 'Microsoft.Storage'
}
supportsHttpsTrafficOnly: true
}
resource blobService 'blobServices' existing = {
name: 'default'
}
}
resource blobContainer 'Microsoft.Storage/storageAccounts/blobServices/containers@2019-04-01' = {
parent: storageAccount::blobService
name: storageBlobContainerName
properties: {
publicAccess: 'Blob'
}
}
resource userAssignedIdentity 'Microsoft.ManagedIdentity/userAssignedIdentities@2018-11-30' = {
name: userAssignedIdentityName
location: resourceGroup().location
}
resource roleAssignment 'Microsoft.Authorization/roleAssignments@2020-04-01-preview' = {
name: roleAssignmentName
properties: {
roleDefinitionId: contributorRoleDefinitionId
principalId: userAssignedIdentity.properties.principalId
principalType: 'ServicePrincipal'
}
}
resource deploymentScript 'Microsoft.Resources/deploymentScripts@2020-10-01' = {
name: deploymentScriptName
location: resourceGroup().location
kind: 'AzurePowerShell'
identity: {
type: 'UserAssigned'
userAssignedIdentities: {
'${userAssignedIdentity.id}': {}
}
}
properties: {
arguments: '-File \'${string(filesToCopy)}\''
environmentVariables: [
{
name: 'ResourceGroupName'
value: resourceGroup().name
}
{
name: 'StorageAccountName'
value: storageAccountName
}
{
name: 'StorageContainerName'
value: storageBlobContainerName
}
]
azPowerShellVersion: '3.0'
scriptContent: '''
param([string]$File)
$fileList = $File -replace '(\[|\])' -split ',' | ForEach-Object { $_.trim() }
$storageAccount = Get-AzStorageAccount -ResourceGroupName $env:ResourceGroupName -Name $env:StorageAccountName -Verbose
$count = 0
$DeploymentScriptOutputs = @{}
foreach ($fileName in $fileList) {
Write-Host "Copying $fileName to $env:StorageContainerName in $env:StorageAccountName."
Invoke-RestMethod -Uri "https://raw.githubusercontent.com/Azure/azure-docs-json-samples/master/mslearn-arm-deploymentscripts-sample/$fileName" -OutFile $fileName
$blob = Set-AzStorageBlobContent -File $fileName -Container $env:StorageContainerName -Blob $fileName -Context $storageAccount.Context
$DeploymentScriptOutputs[$fileName] = @{}
$DeploymentScriptOutputs[$fileName]['Uri'] = $blob.ICloudBlob.Uri
$DeploymentScriptOutputs[$fileName]['StorageUri'] = $blob.ICloudBlob.StorageUri
$count++
}
Write-Host "Finished copying $count files."
'''
retentionInterval: 'P1D'
}
dependsOn: [
roleAssignment
blobContainer
]
}
output fileUri object = deploymentScript.properties.outputs
output storageAccountName string = storageAccountName
In caso contrario, copiare l'esempio oppure modificare il modello in modo che corrisponda all'esempio.
Creare un file di parametri
Dopo aver impostato il modello, è possibile convalidare il nuovo script di distribuzione usando un file di parametri con i nuovi file specificati.
A questo scopo, creare manualmente un file azuredeploy.parameters.json oppure usare l'estensione VS Code.
Modificare il file in modo da avere due
filesToCopy
specificati:{ "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentParameters.json#", "contentVersion": "1.0.0.0", "parameters": { "filesToCopy": { "value": [ "swagger.Staging.json", "appsettings.Staging.json" ] } } }
Creare un file azuredeploy.parameters.json.
Modificare il file in modo da avere due
filesToCopy
specificati:{ "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentParameters.json#", "contentVersion": "1.0.0.0", "parameters": { "filesToCopy": { "value": [ "swagger.Staging.json", "appsettings.Staging.json" ] } } }
Distribuire il modello
Creare un gruppo di risorse per l'esercizio
È necessario creare un gruppo di risorse in cui contenere le risorse create in questo esercizio. Usando un nuovo gruppo di risorse, la pulizia dopo l'esercizio risulterà molto più semplice.
Nel terminale di Visual Studio Code eseguire questo comando per creare il gruppo di risorse per questo esercizio.
resourceGroupName="learndeploymentscript_exercise_2"
az group create --location eastus --name $resourceGroupName
$resourceGroupName = 'learndeploymentscript_exercise_2'
New-AzResourceGroup -Location eastus -Name $resourceGroupName
Distribuire il modello in Azure
Distribuire il modello usando i comandi dell'interfaccia della riga di comando di Azure nel terminale di Visual Studio Code.
templateFile="azuredeploy.json"
templateParameterFile="azuredeploy.parameters.json"
today=$(date +"%d-%b-%Y")
deploymentName="deploymentscript-"$today
az deployment group create \
--resource-group $resourceGroupName \
--name $deploymentName \
--template-file $templateFile \
--parameters $templateParameterFile
Distribuire il modello in Azure
Distribuire il modello usando i comandi di Azure PowerShell nel terminale.
$templateFile = 'azuredeploy.json'
$templateParameterFile = 'azuredeploy.parameters.json'
$today = Get-Date -Format 'MM-dd-yyyy'
$deploymentName = "deploymentscript-$today"
New-AzResourceGroupDeployment `
-ResourceGroupName $resourceGroupName `
-Name $deploymentName `
-TemplateFile $templateFile `
-TemplateParameterFile $templateParameterFile
Distribuire il modello in Azure
Distribuire il modello usando i comandi dell'interfaccia della riga di comando di Azure nel terminale di Visual Studio Code.
templateFile="main.bicep"
templateParameterFile="azuredeploy.parameters.json"
today=$(date +"%d-%b-%Y")
deploymentName="deploymentscript-"$today
az deployment group create \
--resource-group $resourceGroupName \
--name $deploymentName \
--template-file $templateFile \
--parameters $templateParameterFile
Distribuire il modello in Azure
Distribuire il modello usando i comandi di Azure PowerShell nel terminale.
$templateFile = 'main.bicep'
$templateParameterFile = 'azuredeploy.parameters.json'
$today = Get-Date -Format 'MM-dd-yyyy'
$deploymentName = "deploymentscript-$today"
New-AzResourceGroupDeployment `
-ResourceGroupName $resourceGroupName `
-Name $deploymentName `
-TemplateFile $templateFile `
-TemplateParameterFile $templateParameterFile
Esaminare il risultato del modello
Al termine della distribuzione, è possibile verificare che entrambi i file sono stati copiati nell'account di archiviazione elencando il contenuto del contenitore BLOB.
Elencare il contenuto del contenitore BLOB.
storageAccountName=$(az deployment group show --resource-group $resourceGroupName --name $deploymentName --query 'properties.outputs.storageAccountName.value' --output tsv) az storage blob list --account-name $storageAccountName --container-name config --query '[].name'
Il comando restituisce il codice seguente:
[ "swagger.Staging.json", "appsettings.Staging.json" ]
È anche possibile esaminare i log (e altri dettagli sulla distribuzione) nel portale di Azure o usando il comando seguente.
az deployment-scripts show-log --resource-group $resourceGroupName --name CopyConfigScript
Elencare il contenuto del contenitore BLOB.
$storageAccountName = (Get-AzResourceGroupDeployment -ResourceGroupName $resourceGroupName -Name $deploymentName).Outputs.storageAccountName.Value $storageAccount = Get-AzStorageAccount -ResourceGroupName $resourceGroupName Get-AzStorageBlob -Context $storageAccount.Context -Container config | Select-Object Name
Il comando restituisce il codice seguente:
Name ---- swagger.Staging.json appsettings.Staging.json
È anche possibile esaminare i log (e altri dettagli sulla distribuzione) nel portale di Azure o usando il comando seguente.
Get-AzDeploymentScriptLog -ResourceGroupName $resourceGroupName -Name CopyConfigScript
Pulire il gruppo di risorse
È stato distribuito un modello di ARM con uno script di distribuzione e sono stati usati metodi diversi per passare i dati e personalizzarne il comportamento. È possibile rimuovere il gruppo di risorse che contiene tutte le risorse e le assegnazioni di ruolo create.
az group delete --name $resourceGroupName
Remove-AzResourceGroup -Name $resourceGroupName