From 55ddcd38bde7fd2a1b294368b4d22d6b0c73b584 Mon Sep 17 00:00:00 2001 From: Kevin Duret Date: Thu, 19 Dec 2024 13:58:03 +0100 Subject: [PATCH] enh(ci): skip workflow when no change on PR (#1927) (#1940) --- .github/workflows/centreon-collect.yml | 26 +++- .github/workflows/docker-builder.yml | 14 +- .github/workflows/docker-gorgone-testing.yml | 12 ++ .github/workflows/get-environment.yml | 122 ++++++++++++++++++ .github/workflows/gorgone.yml | 38 +++++- .github/workflows/libzmq.yml | 30 ++++- .github/workflows/lua-curl.yml | 28 +++- .../workflows/set-pull-request-skip-label.yml | 26 ++++ 8 files changed, 282 insertions(+), 14 deletions(-) create mode 100644 .github/workflows/set-pull-request-skip-label.yml diff --git a/.github/workflows/centreon-collect.yml b/.github/workflows/centreon-collect.yml index f5472bc9966..fe9ce07fef5 100644 --- a/.github/workflows/centreon-collect.yml +++ b/.github/workflows/centreon-collect.yml @@ -126,8 +126,10 @@ jobs: unit-test: needs: [get-environment] - if: ${{ github.event.inputs.unit_tests == 'true' && ! contains(fromJson('["stable"]'), needs.get-environment.outputs.stability) }} - + if: | + github.event.inputs.unit_tests == 'true' && + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' strategy: fail-fast: false matrix: @@ -240,7 +242,9 @@ jobs: package: needs: [get-environment] - if: ${{ ! contains(fromJson('["stable"]'), needs.get-environment.outputs.stability) }} + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' strategy: fail-fast: false matrix: @@ -292,6 +296,8 @@ jobs: robot-test: needs: [get-environment, package] if: | + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' && (github.event_name == 'schedule' || (github.event_name == 'workflow_dispatch' && github.event.inputs.is_nightly == 'true')) && ! cancelled() && ! contains(needs.*.result, 'failure') && @@ -364,7 +370,7 @@ jobs: needs: [get-environment, package] if: | github.event_name != 'workflow_dispatch' && - contains(fromJson('["stable"]'), needs.get-environment.outputs.stability) && + needs.get-environment.outputs.stability == 'stable' && ! cancelled() && ! contains(needs.*.result, 'failure') && ! contains(needs.*.result, 'cancelled') @@ -387,6 +393,7 @@ jobs: deliver-rpm: if: | + needs.get-environment.outputs.skip_workflow == 'false' && contains(fromJson('["unstable", "testing"]'), needs.get-environment.outputs.stability) && ! cancelled() && ! contains(needs.*.result, 'failure') && @@ -421,6 +428,7 @@ jobs: deliver-deb: if: | + needs.get-environment.outputs.skip_workflow == 'false' && contains(fromJson('["unstable", "testing"]'), needs.get-environment.outputs.stability) && ! cancelled() && ! contains(needs.*.result, 'failure') && @@ -454,6 +462,7 @@ jobs: promote: needs: [get-environment, deliver-rpm, deliver-deb] if: | + needs.get-environment.outputs.skip_workflow == 'false' && (contains(fromJson('["stable", "testing"]'), needs.get-environment.outputs.stability) && github.event_name != 'workflow_dispatch') && ! cancelled() && ! contains(needs.*.result, 'failure') && @@ -478,3 +487,12 @@ jobs: github_ref_name: ${{ github.ref_name }} release_type: ${{ needs.get-environment.outputs.release_type }} is_cloud: ${{ needs.get-environment.outputs.is_cloud }} + + set-skip-label: + needs: [get-environment, deliver-rpm, deliver-deb, promote] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') + uses: ./.github/workflows/set-pull-request-skip-label.yml diff --git a/.github/workflows/docker-builder.yml b/.github/workflows/docker-builder.yml index 5944ace9e7f..fbfef3539bc 100644 --- a/.github/workflows/docker-builder.yml +++ b/.github/workflows/docker-builder.yml @@ -22,8 +22,11 @@ jobs: with: version_file: CMakeLists.txt - create-and-push-docker: + dockerize: needs: [get-environment] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' strategy: fail-fast: false @@ -122,3 +125,12 @@ jobs: pull: true push: true tags: ${{ vars.DOCKER_INTERNAL_REGISTRY_URL }}/${{ matrix.image }}:${{ matrix.tag }} + + set-skip-label: + needs: [get-environment, dockerize] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') + uses: ./.github/workflows/set-pull-request-skip-label.yml diff --git a/.github/workflows/docker-gorgone-testing.yml b/.github/workflows/docker-gorgone-testing.yml index bbdaeb4859e..4bdd36e3c54 100644 --- a/.github/workflows/docker-gorgone-testing.yml +++ b/.github/workflows/docker-gorgone-testing.yml @@ -24,6 +24,9 @@ jobs: dockerize: needs: [get-environment] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' runs-on: ubuntu-24.04 strategy: @@ -51,3 +54,12 @@ jobs: pull: true push: true tags: ${{ vars.DOCKER_INTERNAL_REGISTRY_URL }}/gorgone-testing-${{ matrix.distrib }}:${{ needs.get-environment.outputs.gorgone_docker_version }} + + set-skip-label: + needs: [get-environment, dockerize] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') + uses: ./.github/workflows/set-pull-request-skip-label.yml diff --git a/.github/workflows/get-environment.yml b/.github/workflows/get-environment.yml index c33fad5fe5f..c135f03d17f 100644 --- a/.github/workflows/get-environment.yml +++ b/.github/workflows/get-environment.yml @@ -42,6 +42,9 @@ on: gorgone_docker_version: description: "md5 of gorgone dockerfile" value: ${{ jobs.get-environment.outputs.gorgone_docker_version }} + skip_workflow: + description: "if the current workflow should be skipped" + value: ${{ jobs.get-environment.outputs.skip_workflow }} jobs: get-environment: @@ -59,10 +62,37 @@ jobs: img_version: ${{ steps.get_docker_images_version.outputs.img_version }} test_img_version: ${{ steps.get_docker_images_version.outputs.test_img_version }} gorgone_docker_version: ${{ steps.get_docker_images_version.outputs.gorgone_docker_version }} + skip_workflow: ${{ steps.skip_workflow.outputs.result }} steps: + - name: Check if PR has skip label + id: has_skip_label + uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1 + with: + script: | + let hasSkipLabel = false; + if (${{ contains(fromJSON('["pull_request", "pull_request_target"]') , github.event_name) }} === true) { + try { + const labels = await github.rest.issues.listLabelsOnIssue({ + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: context.issue.number + }); + labels.data.forEach(({ name }) => { + if (name === '${{ format('skip-workflow-{0}', github.workflow) }}') { + hasSkipLabel = true; + } + }); + } catch (e) { + core.warning(`failed to list labels: ${e}`); + } + } + return hasSkipLabel; + - name: Checkout sources (current branch) uses: actions/checkout@d632683dd7b4114ad314bca15554477dd762a938 # v4.2.0 + with: + fetch-depth: ${{ steps.has_skip_label.outputs.result == 'true' && 100 || 1 }} # get latest major version to detect cloud / on-prem versions - name: Checkout sources (develop branch) @@ -72,6 +102,97 @@ jobs: path: centreon-develop sparse-checkout: .version + - if: ${{ steps.has_skip_label.outputs.result == 'true' }} + name: Get workflow triggered paths + id: get_workflow_triggered_paths + uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1 + with: + script: | + const fs = require('fs'); + + let paths = []; + + const workflowFilePath = '${{ github.workflow_ref }}'.replace('${{ github.repository }}/', '').split('@').shift(); + + if (fs.existsSync(workflowFilePath)) { + const workflowFileContent = fs.readFileSync(workflowFilePath, 'utf8'); + const workflowFileContentLines = workflowFileContent.split('\n'); + + let hasReadOn = false; + let hasReadPullRequest = false; + let hasReadPaths = false; + for (const line of workflowFileContentLines) { + if (line.match(/^on:\s*$/)) { + hasReadOn = true; + continue; + } + if (line.match(/^\s{2}pull_request(_target)?:\s*$/)) { + hasReadPullRequest = true; + continue; + } + if (line.match(/^\s{4}paths:\s*$/)) { + hasReadPaths = true; + continue; + } + + if (hasReadOn && hasReadPullRequest && hasReadPaths) { + const matches = line.match(/^\s{6}-\s['"](.+)['"]\s*$/); + if (matches) { + paths.push(matches[1].trim()); + } else { + break; + } + } + } + } + + if (paths.length === 0) { + paths = ['**']; + } + + console.log(paths); + + return paths; + + - if: ${{ steps.has_skip_label.outputs.result == 'true' }} + name: Get push changes + id: get_push_changes + uses: tj-actions/changed-files@bab30c2299617f6615ec02a68b9a40d10bd21366 # v45.0.5 + with: + since_last_remote_commit: true + json: true + escape_json: false + files: ${{ join(fromJSON(steps.get_workflow_triggered_paths.outputs.result), ';') }} + files_separator: ';' + + - name: Check if current workflow should be skipped + id: skip_workflow + uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1 + with: + script: | + if (${{ steps.has_skip_label.outputs.result }} === false) { + return false; + } + + const label = '${{ format('skip-workflow-{0}', github.workflow) }}'; + if ('${{ steps.get_push_changes.outputs.any_changed }}' === 'true') { + try { + await github.rest.issues.removeLabel({ + name: label, + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: context.issue.number + }); + core.notice(`label ${label} removed because changes were detected on last push.`); + } catch (e) { + core.warning(`failed to remove label ${label}: ${e}`); + } + + return false; + } + + return true; + - name: Store latest major version id: latest_major_version run: | @@ -261,6 +382,7 @@ jobs: ['img_version', '${{ steps.get_docker_images_version.outputs.img_version }}'], ['test_img_version', '${{ steps.get_docker_images_version.outputs.test_img_version }}'], ['gorgone_docker_version', '${{ steps.get_docker_images_version.outputs.gorgone_docker_version }}'], + ['skip_workflow', '${{ steps.skip_workflow.outputs.result }}'], ]; outputTable.push(['target_stability', '${{ steps.get_stability.outputs.target_stability || 'not defined because current run is not triggered by pull request event' }}']); diff --git a/.github/workflows/gorgone.yml b/.github/workflows/gorgone.yml index be050f782aa..64658fe5893 100644 --- a/.github/workflows/gorgone.yml +++ b/.github/workflows/gorgone.yml @@ -57,7 +57,9 @@ jobs: package: needs: [get-environment] - if: ${{ needs.get-environment.outputs.stability != 'stable' }} + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' strategy: fail-fast: false @@ -133,6 +135,9 @@ jobs: test-gorgone: needs: [get-environment, package] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' strategy: fail-fast: false @@ -245,7 +250,12 @@ jobs: deliver-sources: runs-on: [self-hosted, common] needs: [get-environment, package] - if: ${{ contains(fromJson('["stable"]'), needs.get-environment.outputs.stability) && github.event_name != 'workflow_dispatch' }} + if: | + github.event_name != 'workflow_dispatch' && + needs.get-environment.outputs.stability == 'stable' && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') steps: - name: Checkout sources @@ -264,7 +274,12 @@ jobs: deliver-rpm: runs-on: [self-hosted, common] needs: [get-environment, package] - if: ${{ contains(fromJson('["testing", "unstable"]'), needs.get-environment.outputs.stability) }} + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + contains(fromJson('["unstable", "testing"]'), needs.get-environment.outputs.stability) && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') strategy: matrix: @@ -289,7 +304,12 @@ jobs: deliver-deb: runs-on: [self-hosted, common] needs: [get-environment, package] - if: ${{ contains(fromJson('["testing", "unstable"]'), needs.get-environment.outputs.stability) }} + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + contains(fromJson('["unstable", "testing"]'), needs.get-environment.outputs.stability) && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') strategy: matrix: @@ -314,6 +334,7 @@ jobs: promote: needs: [get-environment, deliver-rpm, deliver-deb] if: | + needs.get-environment.outputs.skip_workflow == 'false' && (contains(fromJson('["stable", "testing"]'), needs.get-environment.outputs.stability) && github.event_name != 'workflow_dispatch') && ! cancelled() && ! contains(needs.*.result, 'failure') && @@ -338,3 +359,12 @@ jobs: github_ref_name: ${{ github.ref_name }} release_type: ${{ needs.get-environment.outputs.release_type }} is_cloud: ${{ needs.get-environment.outputs.is_cloud }} + + set-skip-label: + needs: [get-environment, deliver-rpm, deliver-deb, promote] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') + uses: ./.github/workflows/set-pull-request-skip-label.yml diff --git a/.github/workflows/libzmq.yml b/.github/workflows/libzmq.yml index 8a2edc89659..7c6c03cdfa1 100644 --- a/.github/workflows/libzmq.yml +++ b/.github/workflows/libzmq.yml @@ -24,6 +24,9 @@ jobs: package-rpm: needs: [get-environment] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' strategy: fail-fast: false @@ -74,6 +77,9 @@ jobs: package-deb: needs: [get-environment] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' strategy: fail-fast: false @@ -138,8 +144,13 @@ jobs: key: ${{ github.run_id }}-${{ github.sha }}-deb-libzmq-${{ matrix.distrib }}-${{ matrix.arch }} deliver-rpm: - if: ${{ contains(fromJson('["testing", "unstable"]'), needs.get-environment.outputs.stability) }} needs: [get-environment, package-rpm] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + contains(fromJson('["unstable", "testing"]'), needs.get-environment.outputs.stability) && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') runs-on: [self-hosted, common] strategy: matrix: @@ -168,8 +179,13 @@ jobs: is_cloud: ${{ needs.get-environment.outputs.is_cloud }} deliver-deb: - if: ${{ contains(fromJson('["testing", "unstable"]'), needs.get-environment.outputs.stability) }} needs: [get-environment, package-deb] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + contains(fromJson('["unstable", "testing"]'), needs.get-environment.outputs.stability) && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') runs-on: [self-hosted, common] strategy: matrix: @@ -198,6 +214,7 @@ jobs: promote: needs: [get-environment, deliver-rpm, deliver-deb] if: | + needs.get-environment.outputs.skip_workflow == 'false' && (contains(fromJson('["stable", "testing"]'), needs.get-environment.outputs.stability) && github.event_name != 'workflow_dispatch') && ! cancelled() && ! contains(needs.*.result, 'failure') && @@ -222,3 +239,12 @@ jobs: github_ref_name: ${{ github.ref_name }} release_type: ${{ needs.get-environment.outputs.release_type }} is_cloud: ${{ needs.get-environment.outputs.is_cloud }} + + set-skip-label: + needs: [get-environment, deliver-rpm, deliver-deb, promote] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') + uses: ./.github/workflows/set-pull-request-skip-label.yml diff --git a/.github/workflows/lua-curl.yml b/.github/workflows/lua-curl.yml index 90d98e32487..223438040e0 100644 --- a/.github/workflows/lua-curl.yml +++ b/.github/workflows/lua-curl.yml @@ -29,7 +29,9 @@ jobs: package: needs: [get-environment] - if: ${{ needs.get-environment.outputs.stability != 'stable' }} + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + needs.get-environment.outputs.stability != 'stable' strategy: fail-fast: false @@ -129,7 +131,12 @@ jobs: stability: ${{ needs.get-environment.outputs.stability }} deliver-rpm: - if: ${{ contains(fromJson('["testing", "unstable"]'), needs.get-environment.outputs.stability) }} + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + contains(fromJson('["unstable", "testing"]'), needs.get-environment.outputs.stability) && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') needs: [get-environment, package] runs-on: ubuntu-24.04 strategy: @@ -158,7 +165,12 @@ jobs: is_cloud: ${{ needs.get-environment.outputs.is_cloud }} deliver-deb: - if: ${{ contains(fromJson('["testing", "unstable"]'), needs.get-environment.outputs.stability) }} + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + contains(fromJson('["unstable", "testing"]'), needs.get-environment.outputs.stability) && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') needs: [get-environment, package] runs-on: ubuntu-24.04 strategy: @@ -188,6 +200,7 @@ jobs: promote: needs: [get-environment, deliver-rpm, deliver-deb] if: | + needs.get-environment.outputs.skip_workflow == 'false' && (contains(fromJson('["stable", "testing"]'), needs.get-environment.outputs.stability) && github.event_name != 'workflow_dispatch') && ! cancelled() && ! contains(needs.*.result, 'failure') && @@ -212,3 +225,12 @@ jobs: github_ref_name: ${{ github.ref_name }} release_type: ${{ needs.get-environment.outputs.release_type }} is_cloud: ${{ needs.get-environment.outputs.is_cloud }} + + set-skip-label: + needs: [get-environment, deliver-rpm, deliver-deb, promote] + if: | + needs.get-environment.outputs.skip_workflow == 'false' && + ! cancelled() && + ! contains(needs.*.result, 'failure') && + ! contains(needs.*.result, 'cancelled') + uses: ./.github/workflows/set-pull-request-skip-label.yml diff --git a/.github/workflows/set-pull-request-skip-label.yml b/.github/workflows/set-pull-request-skip-label.yml new file mode 100644 index 00000000000..ffab0b955e2 --- /dev/null +++ b/.github/workflows/set-pull-request-skip-label.yml @@ -0,0 +1,26 @@ +name: set-pull-request-skip-label + +on: + workflow_call: + +jobs: + set-pull-request-skip-label: + if: ${{ success() && contains(fromJSON('["pull_request", "pull_request_target"]') , github.event_name) }} + runs-on: ubuntu-24.04 + + steps: + - name: Set PR skip label + uses: actions/github-script@60a0d83039c74a4aee543508d2ffcb1c3799cdea # v7.0.1 + with: + script: | + const label = '${{ format('skip-workflow-{0}', github.workflow) }}'; + try { + await github.rest.issues.addLabels({ + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: context.issue.number, + labels: [label] + }); + } catch (e) { + core.warning(`failed to add label ${label}: ${e}`); + }