Conditional steps in jobs and conditional workflows

Overview

Users can conditionally trigger a workflow or steps using Advanced Logic in their config.yml file.  

Specific logic statements can be used to create multiple nested conditions that will always, at the top level, result in true or false -- which in turn determines if the workflow or steps are triggered.

 

Logic statements are evaluated to boolean values at configuration compilation time, that is, before the workflow is run.

 

Example config with conditional steps: 

 steps:
    - when:
        condition:
          or:
            - and:
              - equal: [ main, << pipeline.git.branch >> ]
              - or: [ << pipeline.parameters.param1 >>, << pipeline.parameters.param2 >> ]
            - or:
              - equal: [ false, << pipeline.parameters.param1 >> ]
        steps:
          - run: echo "I am on main AND param1 is true OR param2 is true -- OR param1 is false"

Example config A with a conditional workflow: 

workflows:
  conditional-workflow:
    when:
      and: # All must be true to trigger
        - equal: [ main, << pipeline.git.branch >> ]
        - not: << pipeline.parameters.param1 >>
        - or: [ << pipeline.parameters.param1 >>, << pipeline.parameters.param2 >> ]

    jobs:
      - job-on-condition
 

Example config B with a conditional workflow using parameters:

version: 2.1 # Use version 2.1 to enable Orb usage.

parameters:
  skipUnitTests:
    description: if set to true will not build the c++ unit tests
    type: boolean
    default: true
  skipSystemTests:
    description: if set to true will not build the c++ system tests
    type: boolean
    default: true
  updateTranslation:
    description: if set to true will update the translation files
    type: boolean
    default: true


jobs:
  build_cpp_unit_tests:
    docker:
      - image: cimg/base:edge
    steps:
      - checkout
      - run: echo "This was triggered by << pipeline.trigger_source >>"
  artifacts_build_only_job:
    docker:
      - image: cimg/base:edge
    steps:
      - checkout
      - run: echo "This was triggered by << pipeline.trigger_source >>"
  system_tests_job:
    docker:
      - image: cimg/base:edge
    steps:
      - checkout
      - run: echo "This was triggered by << pipeline.trigger_source >>"
  updateTranslation_job:
    docker:
      - image: cimg/base:edge
    steps:
      - checkout
      - run: echo "This was triggered by << pipeline.trigger_source >>"


workflows:
  unit_tests_workflow: 
    when: # All must be true to trigger
      and:
        - equal: [ false, <<pipeline.parameters.skipUnitTests>> ]
        - equal: [ true, <<pipeline.parameters.skipSystemTests>> ]
        - equal: [ false, <<pipeline.parameters.updateTranslation>> ]
    jobs:
    - build_cpp_unit_tests
  artifacts_build_only_workflow: 
    when: # All must be true to trigger
      and:
        - equal: [ true, <<pipeline.parameters.skipUnitTests>> ]
        - equal: [ true, <<pipeline.parameters.skipSystemTests>> ]
        - equal: [ false, <<pipeline.parameters.updateTranslation>> ]
    jobs:
    - artifacts_build_only_job
  artifacts_build_and_unittest:
    when: # All must be true to trigger
      and:
        - equal: [ false, <<pipeline.parameters.skipUnitTests>> ]
        - equal: [ true, <<pipeline.parameters.skipSystemTests>> ]
        - equal: [ false, <<pipeline.parameters.updateTranslation>> ]
    jobs:
    - build_cpp_unit_tests
    - artifacts_build_only_job
  artifacts_build_and_systemtest:
    when:  # All must be true to trigger
      and:
        - equal: [ true, <<pipeline.parameters.skipUnitTests>> ]
        - equal: [ false, <<pipeline.parameters.skipSystemTests>> ]
        - equal: [ false, <<pipeline.parameters.updateTranslation>> ]
    jobs:
    - artifacts_build_only_job
    - system_tests_job
  updateTranslation_workflow:
    when: # All must be true to trigger
      and:
        - equal: [ true, <<pipeline.parameters.skipUnitTests>> ]
        - equal: [ true, <<pipeline.parameters.skipSystemTests>> ]
        - equal: [ true, <<pipeline.parameters.updateTranslation>> ]
    jobs:
    - updateTranslation_job

Nested Conditional Logic statements: 

Conditions can be nested in an arbitrary fashion, according to their argument specifications, and to a maximum depth of 100 levels. This allows for some complex logic, as an example of multiple nested conditions:

- when:
    condition:
      or:
        - and:
          - or:
              - and:
                  - equal: [ main, << pipeline.git.branch >> ]
                  - equal: [ false, << pipeline.parameters.param1 >> ]
              - or:
                  - not: << pipeline.parameters.param3 >>
          - or:
              - equal: [ false, << pipeline.parameters.param3 >> ]
              - or: [ << pipeline.parameters.param1 >>, << pipeline.parameters.param2 >> ]  
        - or:
            - equal: [ true, << pipeline.parameters.param4 >> ]

    steps:
      - run: echo "param 4 is true OR the other nested conditions are true"

Expression-Based Job Filters:

Conditions that allow jobs to run based on pipeline values and parameters. This allows for jobs to be run based on their source or context of the triggering change.

String matching such as starts-with can be used to analyse values used in the conditionals.

workflows:
  deploy:
    jobs:
      - dry-run-service:
          filters: pipeline.git.branch != "main" and pipeline.git.branch != "canary"
      - publish-service:
          filters: pipeline.git.branch == "main" or pipeline.git.tag starts-with "release"
      - deploy-service:
          filters: pipeline.git.branch == "main" and pipeline.parameters.my-custom-param starts-with "DEPLOY:"

 

 

Additional Resources:

Was this article helpful?
72 out of 285 found this helpful

Comments

0 comments

Article is closed for comments.