Especificar condições
Azure DevOps Services | Azure DevOps Server | 2020 Azure DevOps Server | 2019 TFS 2018
Pode especificar as condições em que cada fase, trabalho ou passo corre. Por defeito, um trabalho ou estágio funciona se não depender de qualquer outro trabalho ou estágio, ou se todos os trabalhos ou fases de que depende tiverem concluído e sucedido. Por defeito, um passo corre se nada no seu trabalho ainda falhou e o passo imediatamente anterior a ter terminado. Você pode personalizar este comportamento forçando um estágio, trabalho ou passo para correr mesmo que uma dependência anterior falhe ou especificando uma condição personalizada.
Nota
No Microsoft Team Foundation Server (TFS) 2018 e nas versões anteriores, os oleodutos de construção e libertação são chamados definições, as corridas são chamadas de construções, as ligações de serviço são chamadas pontos finais de serviço, as fases são chamadas de ambientes, e os empregos são chamados de fases.
Pode especificar as condições em que um passo, trabalho ou estágio serão executados.
Só quando todas as dependências anteriores com o mesmo grupo de agentes foram bem sucedidas. Se tiver piscinas de agentes diferentes, essas fases ou empregos serão executados simultaneamente. Este é o padrão se não houver uma condição definida no YAML.
Mesmo que uma dependência anterior tenha falhado, a menos que a corrida tenha sido cancelada. Utilização
succeededOrFailed()
no YAML para esta condição.Mesmo que uma dependência anterior tenha falhado, mesmo que a corrida tenha sido cancelada. Utilização
always()
no YAML para esta condição.Só quando uma dependência anterior falhou. Utilização
failed()
no YAML para esta condição.
- Condições personalizadas
Por defeito, as etapas, os postos de trabalho e as etapas funcionam se todos os passos/postos de trabalho anteriores tiverem sido bem sucedidos. É como se tivesse especificado "condição: bem sucedida".
jobs:
- job: Foo
steps:
- script: echo Hello!
condition: always() # this step will always run, even if the pipeline is canceled
- job: Bar
dependsOn: Foo
condition: failed() # this job will only run if Foo fails
Também pode utilizar variáveis em condições.
variables:
isMain: $[eq(variables['Build.SourceBranch'], 'refs/heads/main')]
stages:
- stage: A
jobs:
- job: A1
steps:
- script: echo Hello Stage A!
- stage: B
condition: and(succeeded(), eq(variables.isMain, 'true'))
jobs:
- job: B1
steps:
- script: echo Hello Stage B!
- script: echo $(isMain)
As condições são avaliadas para decidir se iniciam uma fase, trabalho ou passo.
Isto significa que nada calculado no tempo de funcionação dentro dessa unidade de trabalho estará disponível.
Por exemplo, se tiver um trabalho que define uma variável usando uma expressão de tempo de execução usando $[ ]
sintaxe, não pode usar essa variável na sua condição personalizada.
A YAML ainda não está apoiada na TFS.
Ativar uma condição personalizada
Se as condições incorporadas não satisfaçam as suas necessidades, então pode especificar as condições personalizadas.
As condições são escritas como expressões nos oleodutos YAML. O agente avalia a expressão começando com a função mais interna e trabalha para sair. O resultado final é um valor booleano que determina se a tarefa, o trabalho ou o estágio devem ou não funcionar. Consulte o tópico das expressões para obter um guia completo da sintaxe.
Alguma das suas condições permite que a tarefa seja executada mesmo depois de a construção ser cancelada por um utilizador? Em caso afirmativo, especifique um valor razoável para cancelar o tempo limite de modo a que este tipo de tarefas tenha tempo suficiente para completar após o utilizador cancelar uma execução.
Exemplos
Correr para o ramo principal, se tiver sucesso
and(succeeded(), eq(variables['Build.SourceBranch'], 'refs/heads/main'))
Corra se o ramo não for principal, se tiver sucesso
and(succeeded(), ne(variables['Build.SourceBranch'], 'refs/heads/main'))
Corra para os ramos de tópicos de utilizador, se tiver sucesso
and(succeeded(), startsWith(variables['Build.SourceBranch'], 'refs/heads/users/'))
Executar para integração contínua (CI) constrói se for bem sucedido
and(succeeded(), in(variables['Build.Reason'], 'IndividualCI', 'BatchedCI'))
Executar se a construção é gerida por uma política de filial para um pedido de puxar, se falhar
and(failed(), eq(variables['Build.Reason'], 'PullRequest'))
Corra se a construção estiver programada, mesmo que falhe, mesmo que cancelada
and(always(), eq(variables['Build.Reason'], 'Schedule'))
Release.Artifacts. {artefacto-alias}. SourceBranch é equivalente a Build.SourceBranch.
Executar se uma variável é definida como verdadeira
condition: eq(variables['System.debug'], 'true')
Executar se uma variável for nula (corda vazia)
Uma vez que todas as variáveis são tratadas como cordas em Gasodutos Azure, uma corda vazia é equivalente a null
neste oleoduto.
variables:
- name: testEmpty
value: ''
jobs:
- job: A
steps:
- script: echo testEmpty is blank
condition: eq(variables.testEmpty, '')
Use um parâmetro de modelo como parte de uma condição
Quando declara um parâmetro no mesmo oleoduto de que tem uma condição, a expansão dos parâmetros ocorre antes de as condições serem consideradas. Neste caso, pode incorporar parâmetros dentro das condições. O script neste ficheiro YAML será executado porque parameters.doThing
é verdade.
parameters:
- name: doThing
default: true
type: boolean
steps:
- script: echo I did a thing
condition: and(succeeded(), eq('${{ parameters.doThing }}', 'true'))
No entanto, quando se passa um parâmetro para um modelo, o parâmetro não terá um valor quando a condição for avaliada. Como resultado, se definir o valor do parâmetro tanto no modelo como nos ficheiros YAML do pipeline, o valor do modelo será utilizado na sua condição.
# parameters.yml
parameters:
- name: doThing
default: true # value passed to the condition
type: boolean
jobs:
- job: B
steps:
- script: echo I did a thing
condition: and(succeeded(), eq('${{ parameters.doThing }}', 'true'))
# azure-pipeline.yml
parameters:
- name: doThing
default: true
type: boolean
trigger:
- none
extends:
template: parameters.yml
A saída deste oleoduto é I did a thing
porque o parâmetro doThing
é verdadeiro.
Use a variável de saída de um trabalho em uma condição em um trabalho subsequente
Pode disponibilizar uma variável para empregos futuros e especificá-la em condições. As variáveis disponíveis para empregos futuros devem ser marcadas como variáveis de produção multi-emprego utilizando isOutput=true
.
jobs:
- job: Foo
steps:
- bash: |
echo "This is job Foo."
echo "##vso[task.setvariable variable=doThing;isOutput=true]Yes" #set variable doThing to Yes
name: DetermineResult
- job: Bar
dependsOn: Foo
condition: eq(dependencies.Foo.outputs['DetermineResult.doThing'], 'Yes') #map doThing and check the value
steps:
- script: echo "Job Foo ran and doThing is Yes."
Use a variável de gasoduto criada a partir de um passo em uma condição em um passo subsequente
Pode disponibilizar uma variável para passos futuros e especificá-la em condições. Por padrão, as variáveis criadas a partir de um passo estão disponíveis para etapas futuras e não precisam de ser marcadas como variáveis de saída multi-trabalho utilizando isOutput=true
.
Há algumas coisas importantes a notar sobre a abordagem acima e scoping:
- As variáveis criadas num passo num trabalho serão adidas aos passos no mesmo trabalho.
- As variáveis criadas num passo só estarão disponíveis em etapas subsequentes como variáveis ambientais.
- As variáveis criadas num passo não podem ser usadas no passo que as define.
Abaixo está um exemplo de criação de uma variável de pipeline em um passo e usar a variável em uma condição e script subsequente.
steps:
# This step creates a new pipeline variable: doThing. This variable will be available to subsquent steps.
- bash: |
echo "##vso[task.setvariable variable=doThing]Yes"
displayName: Step 1
# This step is able to use doThing, so it uses it in its condition
- script: |
# You can access the variable from Step 1 as an environment variable.
echo "Value of doThing (as DOTHING env var): $DOTHING."
displayName: Step 2
condition: and(succeeded(), eq(variables['doThing'], 'Yes')) # or and(succeeded(), eq(variables.doThing, 'Yes'))
FAQ
Tenho um passo condicional que corre mesmo quando um trabalho é cancelado. O meu passo condicional afeta um trabalho que cancelei na fila?
N.º Se cancelares um trabalho enquanto está na fila, todo o trabalho está cancelado, incluindo passos condicional.
Tenho um passo condicional que deve ser executado mesmo quando a implantação for cancelada. Como devo proceder para especificar isto?
Se definiu os oleodutos utilizando um ficheiro YAML, então este é suportado. Este cenário ainda não é suportado para os oleodutos de libertação.
Como posso desencadear um emprego se um trabalho anterior foi bem sucedido com problemas?
Pode usar o resultado do trabalho anterior. Por exemplo, neste ficheiro YAML, a condição eq(dependencies.A.result,'SucceededWithIssues')
permite que o trabalho seja executado porque Job A conseguiu problemas.
jobs:
- job: A
displayName: Job A
continueOnError: true # next job starts even if this one fails
steps:
- script: echo Job A ran
- script: exit 1
- job: B
dependsOn: A
condition: eq(dependencies.A.result,'SucceededWithIssues') # targets the result of the previous job
displayName: Job B
steps:
- script: echo Job B ran
Tenho um passo condicional que corre mesmo quando um trabalho é cancelado. Como devo proceder para consegue cancelar todos os empregos ao mesmo tempo?
Você vai experimentar este problema se a condição configurada no palco não incluir uma função de verificação do estado do trabalho. Para resolver o problema, adicione uma função de verificação do estado do trabalho à condição. Se cancelar um trabalho enquanto está na fila, todo o trabalho é cancelado, incluindo todas as outras fases, com esta função configurada. Para mais informações, consulte as funções de estado do trabalho.
stages:
- stage: Stage1
displayName: Stage 1
dependsOn: []
condition: and(contains(variables['build.sourceBranch'], 'refs/heads/main'), succeeded())
jobs:
- job: ShowVariables
displayName: Show variables
steps:
- task: CmdLine@2
displayName: Show variables
inputs:
script: 'printenv'
- stage: Stage2
displayName: stage 2
dependsOn: Stage1
condition: contains(variables['build.sourceBranch'], 'refs/heads/main')
jobs:
- job: ShowVariables
displayName: Show variables 2
steps:
- task: CmdLine@2
displayName: Show variables 2
inputs:
script: 'printenv'
- stage: Stage3
displayName: stage 3
dependsOn: Stage2
condition: and(contains(variables['build.sourceBranch'], 'refs/heads/main'), succeeded())
jobs:
- job: ShowVariables
displayName: Show variables 3
steps:
- task: CmdLine@2
displayName: Show variables 3
inputs:
script: 'printenv'