You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Azure Pipeline代理分配优化配置问询:避免跨构建抢占

Azure Pipeline 配置问题解决指南

术语定义

  • Pipeline - 流水线(包含Automation、Fast、Slow类型)
  • Build - 针对特定提交的流水线单次运行实例
  • Job - 构建的组成步骤
  • Task - 作业的组成步骤
  • Agent - 运行作业的服务器

核心需求

  • 当某台Agent启动某个Build后,在该Build完成前不再承接其他Build的Job
  • 单个Build最多使用3台Agent
  • 优先让尽可能多的Agent同时处理同一个Build
  • 每个Build可使用1台或多台Agent

当前问题

Agent会在不同Build间切换,导致部分Build无人处理,现有YAML配置如下:

trigger:
  tags:
    include:
    - 2.*

parameters:
  - name: 'tests'
    type: object
    default:
      - "test_1"
      - "test_2"
      - "test_3"
      - "test_4"
      - "test_5"
      - "test_6"
      - "test_7"
      - "test_8"
      - "test_9"

stages:
  - stage: RunTests
    displayName: 'Run Tests'
    jobs:
      - job: ui
        timeoutInMinutes: 120
        pool:
          name: Nightly
          demands:
            - Cmd
            - DotNetFramework

        strategy:
          maxParallel: 3
          matrix:
            ${{ each test_case in parameters.tests }}:
              ${{ test_case }}:
                test: ${{ test_case }}

        steps:
          - task: DeleteFiles@1
            displayName: 'Delete past session artifacts'
            inputs:
              sourceFolder: 'C:/dev'
              contents: |
                /files/**/*
                /temp/**/*
            condition: always()

          - task: DeleteFiles@1
            displayName: 'Delete past session captures'
            inputs:
              sourceFolder: 'C:/test_capture'
              contents: |
                **/*
            condition: always()

          - task: BatchScript@1
            displayName: 'configure z'
            inputs:
              filename: 'scripts\configure_z.bat'
              modifyEnvironment: false
            timeoutInMinutes: 20

          - template: build_env.yaml

          - task: BatchScript@1
            displayName: 'Run script automation/run_tests.bat '
            inputs:
              filename: 'automation/run_tests.bat'
              arguments: $(test)
              modifyEnvironment: false
            condition: and(succeeded(), ne(variables['Agent.JobStatus'], 'Canceled'))

          - task: PublishPipelineArtifact@1
            displayName: 'Publish Pipeline Artifact'
            inputs:
              artifactName: Automation logs $(Agent.JobName) Attemp $(System.JobAttempt)
              targetPath: 'c:\test_capture'
            condition: always()

          - template: publish_test_results.yaml

  - stage: WrapUp
    displayName: 'Wrap Up'
    dependsOn: RunTests
    jobs:
      - job: PublishCompiledLogs
        displayName: 'Publish Compiled Logs'
        timeoutInMinutes: 20
        pool:
          name: Nightly
          demands:
            - Cmd
            - DotNetFramework

        steps:
          - task: DownloadPipelineArtifact@2
            inputs:
              patterns: '**/nosetest-*.xml'
              path: './tests-xml'
            condition: always()

          - task: CmdLine@1
            displayName: 'Combine Logs'
            inputs:
              filename: python
              arguments: 'scripts/merge_nosetest_logs.py --directory tests-xml --output tests-xml/nosetest-automation.xml --remove'
            continueOnError: true
            condition: always()

          - task: PublishPipelineArtifact@1
            displayName: 'Publish All Tests Artifact'
            inputs:
              artifactName: All Automatic Tests Logs
              targetPath: './tests-xml'
            condition: always()

解决方案

1. 实现Agent独占Build(解决跨Build切换问题)

在Job的pool配置中添加lockBehavior: exclusive,确保Agent被当前Build的Job独占,直到该Build所有作业完成:

pool:
  name: Nightly
  demands:
    - Cmd
    - DotNetFramework
  lockBehavior: exclusive # 锁定Agent为当前Build专属

同时进入Azure DevOps代理池管理页面(组织设置→代理池→Nightly),将每个Agent的最大并行作业数设为1,彻底避免Agent同时处理多个Job。

2. 保持单Build最大Agent数限制

你现有配置中的strategy: maxParallel: 3已经实现了单个Build最多使用3台Agent的需求,无需修改。

3. 强化同Build作业优先分配逻辑

在Azure DevOps代理池的作业队列设置中(组织设置→代理池→Nightly→作业队列),开启“同一流水线的作业优先”选项,确保可用Agent优先分配给当前正在运行的Build作业。

4. 支持动态Agent数量

现有矩阵策略会根据测试用例数量自动调整并行Agent数(测试用例≤3时使用对应数量的Agent),完全满足“Build可使用1台或多台Agent”的需求,无需额外配置。

调整后的完整YAML配置

trigger:
  tags:
    include:
    - 2.*

parameters:
  - name: 'tests'
    type: object
    default:
      - "test_1"
      - "test_2"
      - "test_3"
      - "test_4"
      - "test_5"
      - "test_6"
      - "test_7"
      - "test_8"
      - "test_9"

stages:
  - stage: RunTests
    displayName: '运行测试'
    jobs:
      - job: ui
        timeoutInMinutes: 120
        pool:
          name: Nightly
          demands:
            - Cmd
            - DotNetFramework
          lockBehavior: exclusive
        strategy:
          maxParallel: 3
          matrix:
            ${{ each test_case in parameters.tests }}:
              ${{ test_case }}:
                test: ${{ test_case }}

        steps:
          - task: DeleteFiles@1
            displayName: '删除历史会话产物'
            inputs:
              sourceFolder: 'C:/dev'
              contents: |
                /files/**/*
                /temp/**/*
            condition: always()

          - task: DeleteFiles@1
            displayName: '删除历史会话捕获文件'
            inputs:
              sourceFolder: 'C:/test_capture'
              contents: |
                **/*
            condition: always()

          - task: BatchScript@1
            displayName: '配置环境Z'
            inputs:
              filename: 'scripts\configure_z.bat'
              modifyEnvironment: false
            timeoutInMinutes: 20

          - template: build_env.yaml

          - task: BatchScript@1
            displayName: '运行自动化测试脚本 run_tests.bat'
            inputs:
              filename: 'automation/run_tests.bat'
              arguments: $(test)
              modifyEnvironment: false
            condition: and(succeeded(), ne(variables['Agent.JobStatus'], 'Canceled'))

          - task: PublishPipelineArtifact@1
            displayName: '发布流水线产物'
            inputs:
              artifactName: 自动化日志_$(Agent.JobName)_尝试_$(System.JobAttempt)
              targetPath: 'c:\test_capture'
            condition: always()

          - template: publish_test_results.yaml

  - stage: WrapUp
    displayName: '收尾处理'
    dependsOn: RunTests
    jobs:
      - job: PublishCompiledLogs
        displayName: '发布合并后的测试日志'
        timeoutInMinutes: 20
        pool:
          name: Nightly
          demands:
            - Cmd
            - DotNetFramework
          lockBehavior: exclusive

        steps:
          - task: DownloadPipelineArtifact@2
            inputs:
              patterns: '**/nosetest-*.xml'
              path: './tests-xml'
            condition: always()

          - task: CmdLine@1
            displayName: '合并测试日志'
            inputs:
              filename: python
              arguments: 'scripts/merge_nosetest_logs.py --directory tests-xml --output tests-xml/nosetest-automation.xml --remove'
            continueOnError: true
            condition: always()

          - task: PublishPipelineArtifact@1
            displayName: '发布所有测试日志产物'
            inputs:
              artifactName: 所有自动化测试日志
              targetPath: './tests-xml'
            condition: always()

内容的提问来源于stack exchange,提问作者bimBamBom

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.24 22:17:56