Compartilhar via


Criar uma imagem do Windows e distribuí-la para uma Galeria de Computação do Azure

Aplica-se a: ✔️ VMs do Windows

Neste artigo, você verá como usar o Construtor de Imagens de VM do Azure e o Azure PowerShell para criar uma versão de imagem em uma Galeria de Computação do Azure (antiga Galeria de Imagens Compartilhadas) e distribuir a imagem globalmente. Você também pode fazer isso usando a CLI do Azure.

Para configurar a imagem, este artigo usa um modelo JSON, que você pode encontrar em armTemplateWinSIG.json. Você baixará e editará uma versão local do modelo. Portanto, você também usará uma sessão local do PowerShell.

Para distribuir a imagem a uma Galeria de Computação do Azure, o modelo usa sharedImage como o valor da seção distribute do modelo.

O Construtor de Imagens de VM executa Sysprep automaticamente para generalizar a imagem. O comando é um comando Sysprep genérico e você pode substituí-lo se necessário.

Lembre-se do número de vezes que você coloca as personalizações em camadas. Você pode executar o comando Sysprep um número limitado de vezes em uma imagem do Windows. Depois de atingir o limite de Sysprep, você deverá recriar sua imagem do Windows. Para obter mais informações, confira Limites de quantas vezes você pode executar o Sysprep.

Registrar os provedores

Para usar o Construtor de Imagens de VM, é preciso registrar os provedores.

  1. Verifique os registros do provedor. Verifique se cada um retorna Registrado.

    Get-AzResourceProvider -ProviderNamespace Microsoft.VirtualMachineImages | Format-table -Property ResourceTypes,RegistrationState
    Get-AzResourceProvider -ProviderNamespace Microsoft.Storage | Format-table -Property ResourceTypes,RegistrationState 
    Get-AzResourceProvider -ProviderNamespace Microsoft.Compute | Format-table -Property ResourceTypes,RegistrationState
    Get-AzResourceProvider -ProviderNamespace Microsoft.KeyVault | Format-table -Property ResourceTypes,RegistrationState
    Get-AzResourceProvider -ProviderNamespace Microsoft.Network | Format-table -Property ResourceTypes,RegistrationState
    Get-AzResourceProvider -ProviderNamespace Microsoft.ContainerInstance | Format-table -Property ResourceTypes,RegistrationState
    
  2. Se eles não retornarem Registrados, registre os provedores executando os seguintes comandos:

    Register-AzResourceProvider -ProviderNamespace Microsoft.VirtualMachineImages
    Register-AzResourceProvider -ProviderNamespace Microsoft.Storage
    Register-AzResourceProvider -ProviderNamespace Microsoft.Compute
    Register-AzResourceProvider -ProviderNamespace Microsoft.KeyVault
    Register-AzResourceProvider -ProviderNamespace Microsoft.ContainerInstance
    
  3. Instalar módulos do PowerShell:

    'Az.ImageBuilder', 'Az.ManagedServiceIdentity' | ForEach-Object {Install-Module -Name $_ -AllowPrerelease}
    

Criar variáveis

Como você usará algumas informações repetidamente, crie algumas variáveis para armazená-las.

Substitua os valores das variáveis, como username e vmpassword, por suas informações.

# Get existing context
$currentAzContext = Get-AzContext

# Get your current subscription ID. 
$subscriptionID=$currentAzContext.Subscription.Id

# Destination image resource group
$imageResourceGroup="aibwinsig"

# Location
$location="westus"

# Image distribution metadata reference name
$runOutputName="aibCustWinManImg02ro"

# Image template name
$imageTemplateName="helloImageTemplateWin02ps"

# Distribution properties object name (runOutput).
# This gives you the properties of the managed image on completion.
$runOutputName="winclientR01"

# Create a resource group for the VM Image Builder template and Azure Compute Gallery
New-AzResourceGroup `
   -Name $imageResourceGroup `
   -Location $location

Criar uma identidade atribuída pelo usuário e definir permissões no grupo de recursos

O Construtor de Imagens de VM usa a identidade do usuário fornecida para injetar a imagem em uma Galeria de Computação do Azure. Neste exemplo, você cria uma definição de regra do Azure com ações específicas para distribuir a imagem. A definição de função será atribuída à identidade do usuário.

# setup role def names, these need to be unique
$timeInt=$(get-date -UFormat "%s")
$imageRoleDefName="Azure Image Builder Image Def"+$timeInt
$identityName="aibIdentity"+$timeInt

## Add an Azure PowerShell module to support AzUserAssignedIdentity
Install-Module -Name Az.ManagedServiceIdentity

# Create an identity
New-AzUserAssignedIdentity -ResourceGroupName $imageResourceGroup -Name $identityName

$identityNameResourceId=$(Get-AzUserAssignedIdentity -ResourceGroupName $imageResourceGroup -Name $identityName).Id
$identityNamePrincipalId=$(Get-AzUserAssignedIdentity -ResourceGroupName $imageResourceGroup -Name $identityName).PrincipalId

Atribuir permissões para que a identidade distribua as imagens

Use esse comando para baixar um modelo de definição de função do Azure e atualizá-lo com os parâmetros especificados anteriormente.

$aibRoleImageCreationUrl="https://raw.githubusercontent.com/azure/azvmimagebuilder/master/solutions/12_Creating_AIB_Security_Roles/aibRoleImageCreation.json"
$aibRoleImageCreationPath = "aibRoleImageCreation.json"

# Download the configuration
Invoke-WebRequest -Uri $aibRoleImageCreationUrl -OutFile $aibRoleImageCreationPath -UseBasicParsing

((Get-Content -path $aibRoleImageCreationPath -Raw) -replace '<subscriptionID>',$subscriptionID) | Set-Content -Path $aibRoleImageCreationPath
((Get-Content -path $aibRoleImageCreationPath -Raw) -replace '<rgName>', $imageResourceGroup) | Set-Content -Path $aibRoleImageCreationPath
((Get-Content -path $aibRoleImageCreationPath -Raw) -replace 'Azure Image Builder Service Image Creation Role', $imageRoleDefName) | Set-Content -Path $aibRoleImageCreationPath

# Create a role definition
New-AzRoleDefinition -InputFile  ./aibRoleImageCreation.json

# Grant the role definition to the VM Image Builder service principal
New-AzRoleAssignment -ObjectId $identityNamePrincipalId -RoleDefinitionName $imageRoleDefName -Scope "/subscriptions/$subscriptionID/resourceGroups/$imageResourceGroup"

Observação

Se você vir este erro: "New-AzRoleDefinition: limite de definição de Função excedido. Não é possível criar mais definições de função", consulte Solucionar problemas de RBAC do Azure (controle de acesso baseado em função).

Para usar o Construtor de Imagens de VM com uma Galeria de Computação do Azure, você precisa ter uma definição de imagem e de galeria. O Construtor de Imagens de VM cria a definição de imagem e de galeria para você.

Se você ainda não tiver uma definição de imagem e a definição de galeria para usar, comece criando-as.

# Gallery name
$sigGalleryName= "myIBSIG"

# Image definition name
$imageDefName ="winSvrimage"

# Additional replication region
$replRegion2="eastus"

# Create the gallery
New-AzGallery `
   -GalleryName $sigGalleryName `
   -ResourceGroupName $imageResourceGroup  `
   -Location $location

# Create the image definition
New-AzGalleryImageDefinition `
   -GalleryName $sigGalleryName `
   -ResourceGroupName $imageResourceGroup `
   -Location $location `
   -Name $imageDefName `
   -OsState generalized `
   -OsType Windows `
   -Publisher 'myCompany' `
   -Offer 'WindowsServer' `
   -Sku 'WinSrv2019'

Baixar e configurar o modelo

Baixe o modelo JSON e configure-o com suas variáveis.


$templateFilePath = "armTemplateWinSIG.json"

Invoke-WebRequest `
   -Uri "https://raw.githubusercontent.com/azure/azvmimagebuilder/master/quickquickstarts/1_Creating_a_Custom_Win_Shared_Image_Gallery_Image/armTemplateWinSIG.json" `
   -OutFile $templateFilePath `
   -UseBasicParsing

(Get-Content -path $templateFilePath -Raw ) `
   -replace '<subscriptionID>',$subscriptionID | Set-Content -Path $templateFilePath
(Get-Content -path $templateFilePath -Raw ) `
   -replace '<rgName>',$imageResourceGroup | Set-Content -Path $templateFilePath
(Get-Content -path $templateFilePath -Raw ) `
   -replace '<runOutputName>',$runOutputName | Set-Content -Path $templateFilePath
(Get-Content -path $templateFilePath -Raw ) `
   -replace '<imageDefName>',$imageDefName | Set-Content -Path $templateFilePath
(Get-Content -path $templateFilePath -Raw ) `
   -replace '<sharedImageGalName>',$sigGalleryName | Set-Content -Path $templateFilePath
(Get-Content -path $templateFilePath -Raw ) `
   -replace '<region1>',$location | Set-Content -Path $templateFilePath
(Get-Content -path $templateFilePath -Raw ) `
   -replace '<region2>',$replRegion2 | Set-Content -Path $templateFilePath
((Get-Content -path $templateFilePath -Raw) -replace '<imgBuilderId>',$identityNameResourceId) | Set-Content -Path $templateFilePath

Criar a versão da imagem

Seu modelo deve ser enviado ao serviço. Os comandos a seguir baixarão artefatos dependentes, como scripts, e os armazenarão no grupo de recursos de preparo, que é prefixado com IT_.

New-AzResourceGroupDeployment `
   -ResourceGroupName $imageResourceGroup `
   -TemplateFile $templateFilePath `
   -ApiVersion "2022-02-14" `
   -imageTemplateName $imageTemplateName `
   -svclocation $location

Para criar a imagem, invoque 'Run' no modelo.

Invoke-AzResourceAction `
   -ResourceName $imageTemplateName `
   -ResourceGroupName $imageResourceGroup `
   -ResourceType Microsoft.VirtualMachineImages/imageTemplates `
   -ApiVersion "2022-02-14" `
   -Action Run

Criar a imagem e replicá-la para ambas as regiões pode levar algum tempo. Antes de começar a criar uma VM, aguarde até que essa parte seja concluída.

Get-AzImageBuilderTemplate -ImageTemplateName $imageTemplateName -ResourceGroupName $imageResourceGroup |
  Select-Object -Property Name, LastRunStatusRunState, LastRunStatusMessage, ProvisioningState

Criar a VM

Crie uma VM com base na versão da imagem criada pelo Construtor de Imagens de VM.

  1. Obtenha a versão da imagem que você criou:

    $imageVersion = Get-AzGalleryImageVersion `
    -ResourceGroupName $imageResourceGroup `
    -GalleryName $sigGalleryName `
    -GalleryImageDefinitionName $imageDefName
    $imageVersionId = $imageVersion.Id
    
  2. Crie a VM na segunda região em que a imagem foi replicada:

    $vmResourceGroup = "myResourceGroup"
    $vmName = "myVMfromImage"
    
    # Create user object
    $cred = Get-Credential -Message "Enter a username and password for the virtual machine."
    
    # Create a resource group
    New-AzResourceGroup -Name $vmResourceGroup -Location $replRegion2
    
    # Network pieces
    $subnetConfig = New-AzVirtualNetworkSubnetConfig -Name mySubnet -AddressPrefix 192.168.1.0/24
    $vnet = New-AzVirtualNetwork -ResourceGroupName $vmResourceGroup -Location $replRegion2 `
    -Name MYvNET -AddressPrefix 192.168.0.0/16 -Subnet $subnetConfig
    $pip = New-AzPublicIpAddress -ResourceGroupName $vmResourceGroup -Location $replRegion2 `
    -Name "mypublicdns$(Get-Random)" -AllocationMethod Static -IdleTimeoutInMinutes 4
    $nsgRuleRDP = New-AzNetworkSecurityRuleConfig -Name myNetworkSecurityGroupRuleRDP  -Protocol Tcp `
    -Direction Inbound -Priority 1000 -SourceAddressPrefix * -SourcePortRange * -DestinationAddressPrefix * `
    -DestinationPortRange 3389 -Access Deny
    $nsg = New-AzNetworkSecurityGroup -ResourceGroupName $vmResourceGroup -Location $replRegion2 `
    -Name myNetworkSecurityGroup -SecurityRules $nsgRuleRDP
    $nic = New-AzNetworkInterface -Name myNic -ResourceGroupName $vmResourceGroup -Location $replRegion2 `
    -SubnetId $vnet.Subnets[0].Id -PublicIpAddressId $pip.Id -NetworkSecurityGroupId $nsg.Id
    
    # Create a virtual machine configuration using $imageVersion.Id to specify the image
    $vmConfig = New-AzVMConfig -VMName $vmName -VMSize Standard_D1_v2 | `
    Set-AzVMOperatingSystem -Windows -ComputerName $vmName -Credential $cred | `
    Set-AzVMSourceImage -Id $imageVersion.Id | `
    Add-AzVMNetworkInterface -Id $nic.Id
    
    # Create a virtual machine
    New-AzVM -ResourceGroupName $vmResourceGroup -Location $replRegion2 -VM $vmConfig
    

Verificar a personalização

Crie uma conexão de Área de Trabalho Remota com a VM usando o nome de usuário e a senha que você definiu quando criou a VM. Na VM, abra uma janela do prompt de comando e execute o seguinte comando:

dir c:\

Você deve ver um diretório chamado buildActions que foi criado durante a personalização da imagem.

Limpar os recursos

Observação

Caso deseje tentar personalizar novamente a versão da imagem para criar uma nova versão dessa mesma imagem, ignore as próximas etapas e acesse Usar o Construtor de Imagens de VM para criar outra versão de imagem.

Se os recursos criados não forem mais necessários na sequência do processo descrito neste artigo, você poderá excluí-los.

O processo a seguir exclui a imagem que você criou e todos os outros arquivos de recurso. Verifique se você concluiu essa implantação antes de excluir os recursos.

Exclua primeiro o modelo de grupo de recursos. Caso contrário, o grupo de recursos de preparo (IT_) usado pelo Construtor de Imagens de VM não será limpo.

  1. Obtenha ResourceID do modelo de imagem.

    $resTemplateId = Get-AzResource -ResourceName $imageTemplateName -ResourceGroupName $imageResourceGroup -ResourceType Microsoft.VirtualMachineImages/imageTemplates -ApiVersion "2022-02-14"
    
  2. Excluir modelo de imagem.

    Remove-AzResource -ResourceId $resTemplateId.ResourceId -Force
    
  3. Exclua a atribuição de função.

    Remove-AzRoleAssignment -ObjectId $identityNamePrincipalId -RoleDefinitionName $imageRoleDefName -Scope "/subscriptions/$subscriptionID/resourceGroups/$imageResourceGroup"
    
  4. Remova as definições.

    Remove-AzRoleDefinition -Name "$identityNamePrincipalId" -Force -Scope "/subscriptions/$subscriptionID/resourceGroups/$imageResourceGroup"
    
  5. Exclua a identidade.

    Remove-AzUserAssignedIdentity -ResourceGroupName $imageResourceGroup -Name $identityName -Force
    
  6. Exclua o grupo de recursos.

    Remove-AzResourceGroup $imageResourceGroup -Force
    

Próximas etapas

Para atualizar a versão de imagem que você criou neste artigo, confira Usar o Construtor de Imagens de VM para criar outra versão de imagem.