Consider findings and reports from related pipelines in policy evaluation

What does this MR do and why?

When a related pipeline has security artifacts after MR is created, use it to update approvals to unblock the MR in case the head pipeline for the same ref has no security artifacts.

These changes are done behind feature flag use_related_pipelines_for_policy_evaluation.

This fixes the following issues:

  • If there's a merge request pipeline without security artifacts, approvals are required even though a branch pipeline for the diff_head_sha contains security artifacts and no findings (#519532 (closed))
    • note: Adding another commit to the MR will trigger "artifacts missing" error if merge request pipeline doesn't contain the artifacts, I think this is OK and is expected
  • Policy bot comment is not posted (#519529 (closed)) because the merge request pipeline without artifacts doesn't trigger policy evaluation, and at the same time the MR is not evaluated as unenforceable because we look for "related pipelines" when we post the bot comment here.
  • scan_result_policy_violations are stuck in running state because no code path leads to the policy evaluation:
    • Branch pipeline which would have triggered the policy evaluation finishes before MR is created
    • MR pipeline doesn't have artifacts so UpdateApprovalsService exits early
    • UnenforceablePolicyRulesNotificationService exits early because it's not considered "unenforceable" due to the related pipeline containing a security report

References

Please include cross links to any resources that are relevant to this MR. This will give reviewers and future readers helpful context to give an efficient review of the changes introduced.

MR acceptance checklist

Please evaluate this MR against the MR acceptance checklist. It helps you analyze changes to reduce risks in quality, performance, reliability, security, and maintainability.

Screenshots or screen recordings

Screenshots are required for UI changes, and strongly recommended for all other merge requests.

Before After
CleanShot_2025-03-05_at_13.49.51 CleanShot_2025-03-05_at_13.47.37

How to set up and validate locally

  1. Enable the feature flag:
    Feature.enable(:use_related_pipelines_for_policy_evaluation)
  2. Create a project
  3. Create a scan_finding policy
    approval_policy:
      - name: Secrets
        description: ''
        enabled: true
        rules:
          - type: scan_finding
            scanners:
              - secret_detection
            vulnerabilities_allowed: 0
            severity_levels: []
            vulnerability_states: []
            branch_type: protected
        actions:
          - type: require_approval
            approvals_required: 1
            role_approvers:
              - developer
          - type: send_bot_message
            enabled: true
        approval_settings:
          block_branch_modification: false
          prevent_pushing_and_force_pushing: false
          prevent_approval_by_author: true
          prevent_approval_by_commit_author: true
          remove_approvals_with_new_commit: true
          require_password_to_approve: false
        fallback_behavior:
          fail: closed
    
  4. Create .gitlab-ci.yml which prevents duplicate pipelines (uses MR pipelines when MR is created, otherwise branch pipelines):
    workflow:
      rules:
        - if: $CI_PIPELINE_SOURCE == "merge_request_event"
        - if: $CI_COMMIT_BRANCH && $CI_OPEN_MERGE_REQUESTS
          when: never
        - if: $CI_COMMIT_BRANCH
    
    include:
      - template: 'Jobs/Secret-Detection.gitlab-ci.yml'
      - template: 'Jobs/Dependency-Scanning.gitlab-ci.yml'
    
    project-job:
      stage: test
      script: echo "Project job"
  5. Update README.md, push the changes, wait until the branch pipeline finishes and then create the merge request
  6. Verify that approvals are optional and no MergeRequest.last.scan_result_policy_violations are associated with the merge request.
  7. Add an empty requirements.txt file into the project to trigger dependency scanning
  8. Create a license_scanning policy:
    approval_policy:
      - name: Licenses
        description: ''
        enabled: true
        actions:
          - type: require_approval
            approvals_required: 1
            role_approvers:
              - developer
          - type: send_bot_message
            enabled: true
        rules:
          - type: license_finding
            match_on_inclusion_license: true
            licenses:
              denied:
                - name: MIT License
            license_states:
              - newly_detected
            branch_type: protected
        approval_settings:
          block_branch_modification: false
          prevent_pushing_and_force_pushing: false
          prevent_approval_by_author: false
          prevent_approval_by_commit_author: false
          remove_approvals_with_new_commit: false
          require_password_to_approve: false
        fallback_behavior:
          fail: closed
    
  9. Update README.md, push the changes, wait until the branch pipeline finishes and then create the merge request
  10. Verify that approvals are optional and no MergeRequest.last.scan_result_policy_violations are associated with the merge request.

MR acceptance checklist

Evaluate this MR against the MR acceptance checklist. It helps you analyze changes to reduce risks in quality, performance, reliability, security, and maintainability.

Related to #519532 (closed) and #519529 (closed)

Edited by Martin Cavoj

Merge request reports

Loading