你当前正在访问 Microsoft Azure Global Edition 技术文档网站。 如果需要访问由世纪互联运营的 Microsoft Azure 中国技术文档网站,请访问 https://docs.azure.cn。
使用 Azure Pipelines 部署到应用服务
Azure DevOps Services | Azure DevOps Server 2020 | Azure DevOps Server 2019
注意
从 2024 年 6 月 1 日开始,所有新创建的应用服务应用都可以选择生成唯一的默认主机名,命名约定为 <app-name>-<random-hash>.<region>.azurewebsites.net
。 现有应用名称将保持不变。
示例: myapp-ds27dh7271aah175.westus-01.azurewebsites.net
有关更多详细信息,请参阅应用服务资源的唯一默认主机名。
每次成功生成后,使用 Azure Pipelines 自动将 Web 应用部署到 Azure 应用服务。 利用 Azure Pipelines,可以使用 Azure DevOps 通过持续集成 (CI) 和持续交付 (CD) 来进行生成、测试和部署。
YAML 管道是使用存储库中的 YAML 文件定义的。 步骤是管道的最小组成要素,并且可以是脚本或任务(预打包的脚本)。 了解构成管道的关键概念和组件。
你将在管道中使用 Azure Web 应用任务 (AzureWebApp
) 部署到 Azure 应用服务。 对于更复杂的方案(例如需要在部署中使用 XML 参数),可以使用 Azure 应用服务部署任务 (AzureRmWebAppDeployment)。
先决条件
- 具有活动订阅的 Azure 帐户。 免费创建帐户。
- Azure DevOps 组织。 免费创建一个。
- 能够在 Microsoft 托管的代理上运行管道。 可以购买并行作业,也可以请求免费层。
- 一个有效的 Azure 应用服务应用,其代码托管在 GitHub 或 Azure Repos 上。
- .NET:在 Azure 中创建 ASP.NET Core Web 应用
- ASP.NET:在 Azure 中创建 ASP.NET Framework Web 应用
- JavaScript:在 Azure 应用服务中创建 Node.js Web 应用
- Java:在 Azure 应用服务中创建 Java 应用
- Python:在 Azure 应用服务中创建 Python 应用
1.为堆栈创建管道
本部分的代码示例假设你正在部署一个 ASP.NET Web 应用。 可以调整适用于其他框架的说明。
详细了解 Azure Pipelines 生态系统支持。
登录到 Azure DevOps 组织,并导航到你的项目。
转到“管道”,然后选择“新建管道”。
出现提示时,请选择源代码的位置:Azure Repos Git 或 GitHub。
可能会重定向到 GitHub 进行登录。 如果是这样,请输入 GitHub 凭据。
显示存储库列表时,选择你的存储库。
你可能会被重定向到 GitHub 来安装 Azure Pipelines 应用。 如果是,请选择批准并安装。
出现“配置”选项卡时,选择“ASP.NET Core”。
当新管道出现时,请查看 YAML 以了解其功能。 准备就绪后,选择“保存并运行”。
2.添加部署任务
单击 YAML 文件的末尾,然后选择“显示助手”。
使用任务助手添加 Azure Web 应用任务。
或者,可以添加 Azure 应用服务部署 (AzureRmWebAppDeployment) 任务。
选择你的 Azure 订阅。 确保为连接授权。 该授权可创建所需的服务连接。
根据应用服务应用选择应用类型、应用名称和运行时堆栈。 完整的 YAML 应如以下代码所示。
variables: buildConfiguration: 'Release' steps: - task: DotNetCoreCLI@2 inputs: command: 'publish' publishWebProjects: true - task: AzureWebApp@1 inputs: azureSubscription: '<service-connection-name>' appType: 'webAppLinux' appName: '<app-name>' package: '$(System.DefaultWorkingDirectory)/**/*.zip'
- azureSubscription:与 Azure 订阅的授权服务连接的名称。
- appName:现有应用的名称。
- package:包含应用服务内容的包或文件夹的文件路径。 支持通配符。
示例:部署 .NET 应用
若要将 .zip Web 包(例如,从 ASP.NET Web 应用)部署到 Azure Web 应用,请使用以下代码片段将生成部署到应用。
variables:
buildConfiguration: 'Release'
steps:
- task: DotNetCoreCLI@2
inputs:
command: 'publish'
publishWebProjects: true
- task: AzureWebApp@1
inputs:
azureSubscription: '<service-connection-name>'
appType: 'webAppLinux'
appName: '<app-name>'
package: '$(System.DefaultWorkingDirectory)/**/*.zip'
- azureSubscription:你的 Azure 订阅。
- appType:你的 Web 应用类型。
- appName:现有应用服务的名称。
- package:包的文件路径或包含应用服务内容的文件夹。 支持通配符。
示例:部署到虚拟应用程序
默认情况下,部署发生在 Azure Web 应用中的根应用程序。 可以使用 Azure 应用服务 (AzureRmWebAppDeployment
) 任务的 VirtualApplication
属性部署到特定虚拟应用程序:
- task: AzureRmWebAppDeployment@4
inputs:
VirtualApplication: '<name of virtual application>'
- VirtualApplication:在 Azure 门户中配置的虚拟应用程序的名称。 有关详细信息,请参阅在 Azure 门户中配置应用服务应用。
示例:部署到槽
以下示例演示如何部署到过渡槽,然后交换到生产槽:
- task: AzureWebApp@1
inputs:
azureSubscription: '<service-connection-name>'
appType: webAppLinux
appName: '<app-name>'
deployToSlotOrASE: true
resourceGroupName: '<name of resource group>'
slotName: staging
package: '$(Build.ArtifactStagingDirectory)/**/*.zip'
- task: AzureAppServiceManage@0
inputs:
azureSubscription: '<service-connection-name>'
appType: webAppLinux
WebAppName: '<app-name>'
ResourceGroupName: '<name of resource group>'
SourceSlot: staging
SwapWithProduction: true
- azureSubscription:你的 Azure 订阅。
- appType:(可选)使用
webAppLinux
部署到 Linux 上的 Web 应用。 - appName:现有应用服务的名称。
- deployToSlotOrASE:布尔值。 部署到现有部署槽或 Azure 应用服务环境。
- resourceGroupName:资源组的名称。 如果
deployToSlotOrASE
为 true,则是必需的。 - slotName:槽的名称,默认为
production
。 如果deployToSlotOrASE
为 true,则是必需的。 - package:包的文件路径或包含应用服务内容的文件夹。 支持通配符。
- SourceSlot:当
SwapWithProduction
为 true 时发送到生产环境的槽。 - SwapWithProduction:布尔值。 交换源槽与生产槽的流量。
示例:部署到多个 Web 应用
可以使用 YAML 文件中的作业来设置部署管道。 使用作业可以控制部署到多个 Web 应用时所遵循的顺序。
jobs:
- job: buildandtest
pool:
vmImage: ubuntu-latest
steps:
# publish an artifact called drop
- task: PublishPipelineArtifact@1
inputs:
targetPath: '$(Build.ArtifactStagingDirectory)'
artifactName: drop
# deploy to Azure Web App staging
- task: AzureWebApp@1
inputs:
azureSubscription: '<service-connection-name>'
appType: <app type>
appName: '<staging-app-name>'
deployToSlotOrASE: true
resourceGroupName: <group-name>
slotName: 'staging'
package: '$(Build.ArtifactStagingDirectory)/**/*.zip'
- job: deploy
dependsOn: buildandtest
condition: succeeded()
pool:
vmImage: ubuntu-latest
steps:
# download the artifact drop from the previous job
- task: DownloadPipelineArtifact@2
inputs:
source: 'current'
artifact: 'drop'
path: '$(Pipeline.Workspace)'
- task: AzureWebApp@1
inputs:
azureSubscription: '<service-connection-name>'
appType: <app type>
appName: '<production-app-name>'
resourceGroupName: <group-name>
package: '$(Pipeline.Workspace)/**/*.zip'
示例:进行变量替换
对于大多数语言堆栈,可以在运行时将应用设置和连接字符串设置为环境变量。
但还有其他原因需要对 Web.config 进行变量替换。在此示例中,Web.config 文件包含名为 connectionString
的连接字符串。 在部署到每个 Web 应用之前,可以更改其值。 为此,可以应用 Web.config 转换或者替换 Web.config 文件中的变量。
以下代码片段使用 Azure 应用服务部署 (AzureRmWebAppDeployment
) 任务演示了变量替换的示例:
jobs:
- job: test
variables:
connectionString: <test-stage connection string>
steps:
- task: AzureRmWebAppDeployment@4
inputs:
azureSubscription: '<Test stage Azure service connection>'
WebAppName: '<name of test stage web app>'
enableXmlVariableSubstitution: true
- job: prod
dependsOn: test
variables:
connectionString: <prod-stage connection string>
steps:
- task: AzureRmWebAppDeployment@4
inputs:
azureSubscription: '<Prod stage Azure service connection>'
WebAppName: '<name of prod stage web app>'
enableXmlVariableSubstitution: true
示例:有条件部署
若要在 YAML 中执行此操作,可使用以下方法之一:
- 将部署步骤隔离到单独的作业中,并向该作业添加条件。
- 向步骤添加条件。
以下示例演示如何使用步骤条件来仅部署源自主分支的生成:
- task: AzureWebApp@1
condition: and(succeeded(), eq(variables['Build.SourceBranch'], 'refs/heads/main'))
inputs:
azureSubscription: '<service-connection-name>'
appName: '<app-name>'
若要详细了解条件,请参阅指定条件。
示例:使用 Web 部署进行部署
Azure 应用服务部署 (AzureRmWebAppDeployment
) 任务可以使用 Web 部署部署到应用服务。
trigger:
- main
pool:
vmImage: windows-latest
variables:
buildConfiguration: 'Release'
steps:
- task: DotNetCoreCLI@2
inputs:
command: 'publish'
publishWebProjects: true
arguments: '--configuration $(buildConfiguration)'
zipAfterPublish: true
- task: AzureRmWebAppDeployment@4
inputs:
ConnectionType: 'AzureRM'
azureSubscription: '<service-connection-name>'
appType: 'webApp'
WebAppName: '<app-name>'
packageForLinux: '$(System.DefaultWorkingDirectory)/**/*.zip'
enableCustomDeployment: true
DeploymentType: 'webDeploy'
常见问题
AzureWebApp
和 AzureRmWebAppDeployment
任务之间有何差异?
Azure Web 应用任务 (AzureWebApp
) 是部署到 Azure Web 应用的最简单方法。 默认情况下,部署发生在 Azure Web 应用中的根应用程序。
Azure 应用服务部署任务 (AzureRmWebAppDeployment
) 可以处理更多自定义方案,例如:
- 修改 Web 包和 XML 参数文件中的配置设置。
- 如果习惯于 IIS 部署过程,请使用 Web 部署进行部署。
- 部署到虚拟应用程序。
- 部署到其他应用类型,例如容器应用、函数应用、WebJobs 或 API 和移动应用。
注意
用于 Azure Pipelines 的单独文件转换任务也支持文件转换和变量替换。 可以使用文件转换任务对任何配置文件及参数文件应用文件转换和变量替换。
我收到消息“提供的应用服务包或文件夹路径无效。”
在 YAML 管道中,根据管道的不同,生成的 Web 包的保存位置和部署任务的查找位置之间可能不匹配。 例如,AzureWebApp
任务为部署选取 Web 包。 例如,AzureWebApp 任务在 $(System.DefaultWorkingDirectory)/**/*.zip
中进行查找。 如果 Web 包存放在其他位置,请修改 package
的值。
我收到消息“仅当使用 Windows 代理时才支持使用 webdeploy 选项进行发布。”
将任务配置为使用 Web 部署进行部署,但代理未运行 Windows 时,AzureRmWebAppDeployment 任务中会出现此错误。 验证你的 YAML 具有如下所示的代码:
pool:
vmImage: windows-latest
禁用基本身份验证时,Web 部署不起作用
有关配合使用 Microsoft Entra ID 身份验证与 AzureRmWebAppDeployment
任务的故障排除信息,请参阅无法从 Windows 代理使用 Microsoft Entra ID 身份验证将 Web 部署到 Azure 应用服务
后续步骤
- 自定义 Azure DevOps 管道。