当我将提交推送到 PR 时,我会为此提交触发测试。之后,如果我向此 PR 推送其他提交,Github Actions 中的测试将在这两个提交上运行。
我需要取消之前的运行并仅在最近推送的提交上运行。
如何配置我的 yaml 文件来实现这一目标?
要在触发新工作流程时从同一 PR、分支或标签取消当前正在运行的工作流程,您可以使用:
name: Workflow X
on: # ...
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
cancel-in-progress: true
jobs: # ...
说明:
${{ github.workflow }}
:工作流名称用于生成并发组(例如Workflow 1
)。这允许您在同一事件(例如 PR)上触发多个不同的工作流程(例如 workflow1.yaml
和 workflow2.yaml
)。否则,workflow1.yaml
将取消 workflow2.yaml
,反之亦然。${{ github.event.pull_request.number
:当触发事件是PR时,会使用PR号生成并发组(如workflow1-33
)。|| github.ref }}
:当触发器不是 PR 而是推送时,会使用分支或标签名称来生成并发组(例如 workflow1-branch1
)。cancel-in-progress: true
:如果cancel-in-progress被省略或设置为false,当触发新的工作流程时,当前正在运行的工作流程不会被取消,新的工作流程将排队等候,直到前一个工作流程完成。 参考:https://docs.github.com/en/actions/using-jobs/using-concurrency
您可以使用并发:
并发确保一次仅运行使用同一并发组的单个作业或工作流程。
concurrency:
group: ${{ github.head_ref }}
cancel-in-progress: true
您还需要确保在同一存储库中拥有多个工作流程,以便您只取消同一工作流程的正在进行的运行。
来自使用并发 GitHub 文档的片段:
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
完整的工作示例(来源):
name: CI with in-progress cancellations
on:
pull_request:
branches: [ main ]
workflow_dispatch:
# This is what will cancel the workflow
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Print concurrency group
run: echo '${{ github.workflow }}-${{ github.ref }}'
- name: Sleep 15s
run: sleep 15s
这不再有效,GitHub Actions 自此改进了这种体验。 先查看替代答案。
就像我们以前的“有一个应用程序可以做到这一点!”,现在是“有一个可以做到这一点的操作!”:
jobs:
test:
runs-on: ubuntu-latest
steps:
- name: Cancel Previous Runs
uses: styfle/[email protected]
with:
access_token: ${{ github.token }}
#- name: Run Tests
# uses: actions/setup-node@v1
# run: node test.js
# ... etc
我的情况是为push 和pull_request 运行相同的工作流程。我希望之前运行的任何操作都停止。如果操作在 pull_request 打开之前运行,则同样适用。
我发现我可以将它们全部设置为一组,就像这样..
group: ${ {github.ref} || refs/heads/{github.href} }
现在,即使在拉取请求之前,它也会停止之前的任何操作。