你当前正在访问 Microsoft Azure Global Edition 技术文档网站。 如果需要访问由世纪互联运营的 Microsoft Azure 中国技术文档网站,请访问 https://docs.azure.cn

管理前脚本和后脚本

操作前脚本和操作后脚本是在执行更新部署之前(执行任务前)和之后(执行任务后)要在 Azure 自动化帐户中运行的 runbook。 操作前脚本和操作后脚本在 Azure 上下文中运行,而不是在本地运行。 操作前脚本在更新部署开始时运行。 在 Windows 上,后脚本在部署结束时和任何配置的重新启动后运行。 对于 Linux,后脚本在部署结束后(而不是在计算机重新启动后)运行。

操作前脚本和操作后脚本要求

若要将某个 runbook 用作操作前脚本或操作后脚本,必须将其导入到自动化帐户中并发布 runbook

目前仅支持将 PowerShell 和 Python 2 runbook 作为前期/后期脚本。 目前不支持将其他 runbook 类型(如 Python 3、图形、PowerShell 工作流和图形 PowerShell 工作流)作为前期/后期脚本。

操作前脚本和操作后脚本参数

配置操作前脚本和操作后脚本时,可以像计划 runbook 时一样传入参数。 参数是在创建更新部署时定义的。 操作前脚本和操作后脚本支持以下类型:

  • [char]
  • [byte]
  • [int]
  • [long]
  • [decimal]
  • [single]
  • [double]
  • [DateTime]
  • [string]

操作前脚本和操作后脚本 runbook 参数不支持布尔值、对象或数组类型。 这些值会导致 runbook 失败。

如果需要其他对象类型,可以在 runbook 中使用自己的逻辑将它强制转换为其他类型。

除标准 runbook 参数外,还提供 SoftwareUpdateConfigurationRunContext 参数(类型为 JSON 字符串)。 如果在操作前脚本或操作后脚本 runbook 中定义该参数,更新部署会自动传入该参数。 该参数包含有关更新部署的信息,这是 SoftwareUpdateconfigurations API 返回的信息的子集。 以下部分定义关联的属性。

SoftwareUpdateConfigurationRunContext 属性

属性 类型 说明
SoftwareUpdateConfigurationName 字符串 软件更新配置的名称。
SoftwareUpdateConfigurationRunId GUID 运行的唯一 ID。
SoftwareUpdateConfigurationSettings 与软件更新配置相关的属性的集合。
SoftwareUpdateConfigurationSettings.OperatingSystem int 面向更新部署的操作系统。 1 = Windows,2 = Linux
SoftwareUpdateConfigurationSettings.Duration 时间跨度 (HH:MM:SS) 符合 ISO8601 的更新部署运行的最长持续时间,格式为 PT[n]H[n]M[n]S;也称为“维护时段”。
示例:02:00:00
SoftwareUpdateConfigurationSettings.WindowsConfiguration 与 Windows 计算机相关的属性的集合。
SoftwareUpdateConfigurationSettings.WindowsConfiguration.excludedKbNumbers 字符串 从更新部署中排除的知识库的空格分隔列表。
SoftwareUpdateConfigurationSettings.WindowsConfiguration.includedKbNumbers 字符串 更新部署中包含的知识库的空格分隔列表。
SoftwareUpdateConfigurationSettings.WindowsConfiguration.UpdateCategories 整数 1 =“关键”;
2 =“安全”
4 =“更新汇总”
8 =“功能包”
16 =“服务包”
32 =“定义”
64 =“工具”
128 =“更新”
SoftwareUpdateConfigurationSettings.WindowsConfiguration.rebootSetting 字符串 更新部署的重新启动设置。 值为 IfRequiredNeverAlways
SoftwareUpdateConfigurationSettings.LinuxConfiguration 与 Linux 计算机相关的属性集合。
SoftwareUpdateConfigurationSettings.LinuxConfiguration.IncludedPackageClassifications 整数 0 =“未分类”
1 =“关键”
2 =“安全”
4 =“其他”
SoftwareUpdateConfigurationSettings.LinuxConfiguration.IncludedPackageNameMasks 字符串 更新部署中包含的包名称的空格分隔列表。
SoftwareUpdateConfigurationSettings.LinuxConfiguration.ExcludedPackageNameMasks 字符串 从更新部署中排除的包名称的空格分隔列表。
SoftwareUpdateConfigurationSettings.LinuxConfiguration.RebootSetting 字符串 更新部署的重新启动设置。 值为 IfRequiredNeverAlways
SoftwareUpdateConfiguationSettings.AzureVirtualMachines 字符串数组 更新部署中 Azure VM 的 resourceId 的列表。
SoftwareUpdateConfigurationSettings.NonAzureComputerNames 字符串数组 更新部署中的非 Azure 计算机 FQDN 的列表。

以下示例是传递给 Linux 计算机的 SoftwareUpdateConfigurationSettings 属性的 JSON 字符串:

"SoftwareUpdateConfigurationSettings": {
     "OperatingSystem": 2,
     "WindowsConfiguration": null,
     "LinuxConfiguration": {
         "IncludedPackageClassifications": 7,
         "ExcludedPackageNameMasks": "fgh xyz",
         "IncludedPackageNameMasks": "abc bin*",
         "RebootSetting": "IfRequired"
     },
     "Targets": {
         "azureQueries": null,
         "nonAzureQueries": ""
     },
     "NonAzureComputerNames": [
        "box1.contoso.com",
        "box2.contoso.com"
     ],
     "AzureVirtualMachines": [
        "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/resourceGroupName/providers/Microsoft.Compute/virtualMachines/vm-01"
     ],
     "Duration": "02:00:00",
     "PSComputerName": "localhost",
     "PSShowComputerName": true,
     "PSSourceJobInstanceId": "2477a37b-5262-4f4f-b636-3a70152901e9"
 }

以下示例是传递给 Windows 计算机的 SoftwareUpdateConfigurationSettings 属性的 JSON 字符串:

"SoftwareUpdateConfigurationRunContext": {
    "SoftwareUpdateConfigurationName": "sampleConfiguration",
    "SoftwareUpdateConfigurationRunId": "00000000-0000-0000-0000-000000000000",
    "SoftwareUpdateConfigurationSettings": {
      "operatingSystem": "Windows",
      "duration": "02:00:00",
      "windows": {
        "excludedKbNumbers": [
          "168934",
          "168973"
        ],
        "includedUpdateClassifications": "Critical",
        "rebootSetting": "IfRequired"
      },
      "azureVirtualMachines": [
        "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/myResourceGroup/providers/Microsoft.Compute/virtualMachines/vm-01",
        "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/myResourceGroup/providers/Microsoft.Compute/virtualMachines/vm-02",
        "/subscriptions/00000000-0000-0000-0000-000000000000/resourceGroups/myResourceGroup/providers/Microsoft.Compute/virtualMachines/vm-03"
      ],
      "nonAzureComputerNames": [
        "box1.contoso.com",
        "box2.contoso.com"
      ]
    }
  }

可以在以下位置找到包含所有属性的完整示例:按名称获取软件更新配置

注意

SoftwareUpdateConfigurationRunContext 对象可以包含计算机的重复项。 这可能导致操作前脚本和操作后脚本在同一计算机上多次运行。 若要解决此问题,请使用 Sort-Object -Unique 仅选择唯一 VM 名称。

在部署中使用操作前脚本或操作后脚本

若要在更新部署中使用操作前脚本或操作后脚本,请先创建一个更新部署。 选择“操作前脚本 + 操作后脚本”。 此操作会打开“选择前脚本 + 后脚本”页面。

选择脚本

选择要使用的脚本。 在此示例中,我们使用 UpdateManagement-TurnOnVms runbook。 选择 runbook 后,“配置脚本”页会打开。 选择“操作前脚本”,然后选择“确定”。

针对 UpdateManagement-TurnOffVms 脚本重复此过程。 但是,选择“脚本类型”时,请选择“操作后脚本”。

“选定项”部分现在显示选择的两个脚本。 一个是操作前脚本,另一个是操作后脚本:

选定的项

完成更新部署的配置。

更新部署完成后,可以转到“更新部署”查看结果。 可以看到,此处提供了操作前脚本和操作后脚本的状态:

更新结果

通过选择更新部署运行,系统将显示操作前脚本和操作后脚本的其他详细信息。 此时会提供运行时的脚本源的链接。

部署运行结果

停止部署

如果要停止基于操作前脚本的部署,则必须引发异常。 否则,仍将运行部署和操作后脚本。 以下代码片段演示如何使用 PowerShell 引发异常。

#In this case, we want to terminate the patch job if any run fails.
#This logic might not hold for all cases - you might want to allow success as long as at least 1 run succeeds
foreach($summary in $finalStatus)
{
    if ($summary.Type -eq "Error")
    {
        #We must throw in order to fail the patch deployment.
        throw $summary.Summary
    }
}

在 Python 2 中,异常处理是在 try 块中进行管理的。

与计算机交互

前期脚本和后期脚本在自动化帐户中作为 Runbook 运行,而不是直接在部署中的计算机上运行。 执行前任务和执行后任务也在 Azure 上下文中运行,并且无权访问非 Azure 计算机。 以下部分演示如何直接与计算机交互,而无论它们是 Azure VM 还是非 Azure 计算机。

与 Azure 计算机交互

执行前任务和执行后任务作为 runbook 运行,而不是在部署中的 Azure VM 本机上运行。 若要与 Azure VM 交互,必须具有以下各项:

若要与 Azure 计算机交互,应使用 Invoke-AzVMRunCommand cmdlet 与 Azure VM 进行交互。 有关如何执行此操作的示例,请参阅 runbook 示例更新管理 - 使用 Run 命令运行脚本

与非 Azure 计算机交互

执行前任务和执行后任务在 Azure 上下文中运行,并且无权访问非 Azure 计算机。 若要与非 Azure 计算机交互,必须具有以下项:

  • 托管标识或运行方式帐户
  • 在计算机上安装的混合 Runbook 辅助角色
  • 要在本地运行的 Runbook
  • 父 runbook

若要与非 Azure 计算机交互,需在 Azure 上下文中运行父 runbook。 此 runbook 使用 Start-AzAutomationRunbook cmdlet 调用子 runbook。 必须指定 RunOn 参数,并提供运行脚本的混合 Runbook 辅助角色的名称。 请参阅 runbook 示例更新管理 - 在本地运行脚本

中止修补程序部署

如果操作前脚本返回错误,则可能需要中止部署。 为此,必须在脚本中为可能导致失败的所有逻辑的引发错误。

if (<My custom error logic>)
{
    #Throw an error to fail the patch deployment.
    throw "There was an error, abort deployment"
}

在 Python 2 中,如果要在发生特定状况时引发错误,请使用 raise 语句。

If (<My custom error logic>)
   raise Exception('Something happened.')

示例

可以在 Azure 自动化 GitHub 组织PowerShell 库中找到操作前脚本和操作后脚本的示例,也可以通过 Azure 门户导入这些示例。 为此,请在自动化帐户的“流程自动化”下,选择“Runbook 库”。 使用“更新管理”作为筛选器。

库列表

或者,可按脚本名称进行搜索,如以下列表中所示:

  • 更新管理 - 启用 VM
  • 更新管理 - 禁用 VM
  • 更新管理 - 本地运行脚本
  • 更新管理 - 前脚本/后脚本的模板
  • 更新管理 - 具有 Run 命令运行脚本

重要

导入 runbook 后,必须先发布,然后才可以使用它们。 为此,请在自动化帐户中找到该 runbook,选择“编辑”,然后选择“发布” 。

所有这些示例均基于以下示例中定义的基本模板。 使用此模板可以创建自己的 runbook 来配合操作前脚本和操作后脚本。 其中还包含用于在 Azure 中进行身份验证以及处理 SoftwareUpdateConfigurationRunContext 参数所需的逻辑。

<#
.SYNOPSIS
 Barebones script for Update Management Pre/Post

.DESCRIPTION
  This script is intended to be run as a part of Update Management pre/post-scripts.
  It requires the Automation account's system-assigned managed identity.

.PARAMETER SoftwareUpdateConfigurationRunContext
  This is a system variable which is automatically passed in by Update Management during a deployment.
#>

param(
    [string]$SoftwareUpdateConfigurationRunContext
)

#region BoilerplateAuthentication
# Ensures you do not inherit an AzContext in your runbook
Disable-AzContextAutosave -Scope Process

# Connect to Azure with system-assigned managed identity
$AzureContext = (Connect-AzAccount -Identity).context

# set and store context
$AzureContext = Set-AzContext -SubscriptionName $AzureContext.Subscription -DefaultProfile $AzureContext
#endregion BoilerplateAuthentication

#If you wish to use the run context, it must be converted from JSON
$context = ConvertFrom-Json $SoftwareUpdateConfigurationRunContext
#Access the properties of the SoftwareUpdateConfigurationRunContext
$vmIds = $context.SoftwareUpdateConfigurationSettings.AzureVirtualMachines | Sort-Object -Unique
$runId = $context.SoftwareUpdateConfigurationRunId

Write-Output $context

#Example: How to create and write to a variable using the pre-script:
<#
#Create variable named after this run so it can be retrieved
New-AzAutomationVariable -ResourceGroupName $ResourceGroup -AutomationAccountName $AutomationAccount -Name $runId -Value "" -Encrypted $false
#Set value of variable
Set-AutomationVariable -Name $runId -Value $vmIds
#>

#Example: How to retrieve information from a variable set during the pre-script
<#
$variable = Get-AutomationVariable -Name $runId
#>

如果希望 Runbook 使用系统分配的托管标识执行,请按原样保留代码。 如果希望使用用户分配的托管标识,则执行以下操作:

  1. 从第 22 行中删除 $AzureContext = (Connect-AzAccount -Identity).context
  2. 将其替换为 $AzureContext = (Connect-AzAccount -Identity -AccountId <ClientId>).context,然后
  3. 输入客户端 ID。

注意

对于非图形 PowerShell runbook,Add-AzAccountAdd-AzureRMAccountConnect-AzAccount 的别名。 可以使用这些 cmdlet,也可以在自动化帐户中将模块更新为最新版本。 即使刚刚创建了一个新的自动化帐户,也可能需要更新你的模块。

后续步骤

有关更新管理的详细信息,请参阅管理 VM 的更新和修补程序