workflows: Consolidate pr-subscriber and issue-subscriber#200503
workflows: Consolidate pr-subscriber and issue-subscriber#200503tstellar wants to merge 1 commit into
Conversation
This consolidates duplicate logic from the pr-subscriber and issue-subscriber workflows into a new workflow called subscriber-write. This workflow uses the workflow_run trigger and is triggered by another new workflow called subscriber. The subscriber workflow collects the label name and issue number from the labeled issue/pull requests and sends it to the subscriber-write workflow via artifacts. Besides removing some duplicate code this change also allows us to switch from using the pull_request_target event to the pull_request event for handling pull request subscribers. pull_request executes in an untrusted context and helps protect us from some security risks.
|
@llvm/pr-subscribers-github-workflow Author: Tom Stellard (tstellar) ChangesThis consolidates duplicate logic from the pr-subscriber and issue-subscriber workflows into a new workflow called subscriber-write. This workflow uses the workflow_run trigger and is triggered by another new workflow called subscriber. The subscriber workflow collects the label name and issue number from the labeled issue/pull requests and sends it to the subscriber-write workflow via artifacts. Besides removing some duplicate code this change also allows us to switch from using the pull_request_target event to the pull_request event for handling pull request subscribers. pull_request executes in an untrusted context and helps protect us from some security risks. Full diff: https://github.com/llvm/llvm-project/pull/200503.diff 4 Files Affected:
diff --git a/.github/workflows/issue-subscriber.yml b/.github/workflows/issue-subscriber.yml
deleted file mode 100644
index 4af255b4f8039..0000000000000
--- a/.github/workflows/issue-subscriber.yml
+++ /dev/null
@@ -1,52 +0,0 @@
-name: Issue Subscriber
-
-on:
- issues:
- types:
- - labeled
-
-permissions:
- contents: read
-
-jobs:
- auto-subscribe:
- environment:
- name: main-branch-only
- deployment: false
- runs-on: ubuntu-24.04
- if: github.repository == 'llvm/llvm-project'
- steps:
- - name: Checkout Automation Script
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
- with:
- persist-credentials: false
- sparse-checkout: llvm/utils/git/
- ref: main
-
- - name: Setup Automation Script
- working-directory: ./llvm/utils/git/
- run: |
- pip install --require-hashes -r requirements.txt
-
- - id: app-token
- uses: actions/create-github-app-token@1b10c78c7865c340bc4f6099eb2f838309f1e8c3 # v3.1.1
- with:
- client-id: ${{ secrets.LLVM_TOKEN_GENERATOR_CLIENT_ID }}
- private-key: ${{ secrets.LLVM_TOKEN_GENERATOR_PRIVATE_KEY }}
- owner: ${{ github.repository_owner }}
- permission-members: read
- permission-contents: read
- permission-issues: write
-
- - name: Update watchers
- working-directory: ./llvm/utils/git/
- # https://docs.github.com/en/actions/security-guides/security-hardening-for-github-actions#using-an-intermediate-environment-variable
- env:
- LABEL_NAME: ${{ github.event.label.name }}
- ISSUE_SUBSCRIBER_TOKEN: ${{ steps.app-token.outputs.token }}
- run: |
- python3 ./github-automation.py \
- --token "$ISSUE_SUBSCRIBER_TOKEN" \
- issue-subscriber \
- --issue-number '${{ github.event.issue.number }}' \
- --label-name "$LABEL_NAME"
diff --git a/.github/workflows/pr-subscriber.yml b/.github/workflows/pr-subscriber.yml
deleted file mode 100644
index 04a5e2cfb0d29..0000000000000
--- a/.github/workflows/pr-subscriber.yml
+++ /dev/null
@@ -1,52 +0,0 @@
-name: PR Subscriber
-
-on:
- pull_request_target:
- types:
- - labeled
-
-permissions:
- contents: read
-
-jobs:
- auto-subscribe:
- # See https://github.blog/changelog/2025-11-07-actions-pull_request_target-and-environment-branch-protections-changes/
- environment:
- name: main-branch-only
- deployment: false
- runs-on: ubuntu-24.04
- if: github.repository == 'llvm/llvm-project'
- steps:
- - name: Checkout Automation Script
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
- with:
- persist-credentials: false
- sparse-checkout: llvm/utils/git/
- ref: main
-
- - name: Setup Automation Script
- working-directory: ./llvm/utils/git/
- run: |
- pip install --require-hashes -r requirements.txt
-
- - id: app-token
- uses: actions/create-github-app-token@1b10c78c7865c340bc4f6099eb2f838309f1e8c3 # v3.1.1
- with:
- client-id: ${{ secrets.LLVM_TOKEN_GENERATOR_CLIENT_ID }}
- private-key: ${{ secrets.LLVM_TOKEN_GENERATOR_PRIVATE_KEY }}
- owner: ${{ github.repository_owner }}
- permission-members: read
- permission-contents: read
- permission-pull-requests: write
-
- - name: Update watchers
- working-directory: ./llvm/utils/git/
- env:
- LABEL_NAME: ${{ github.event.label.name }}
- PR_SUBSCRIBER_TOKEN: ${{ steps.app-token.outputs.token }}
- run: |
- python3 ./github-automation.py \
- --token "$PR_SUBSCRIBER_TOKEN" \
- pr-subscriber \
- --issue-number "${{ github.event.number }}" \
- --label-name "$LABEL_NAME"
diff --git a/.github/workflows/subscriber-write.yml b/.github/workflows/subscriber-write.yml
new file mode 100644
index 0000000000000..a0b4c7866f437
--- /dev/null
+++ b/.github/workflows/subscriber-write.yml
@@ -0,0 +1,114 @@
+name: Subscriber Write
+
+on:
+ workflow_run:
+ workflows:
+ - "Subscriber"
+ types:
+ - completed
+
+permissions:
+ contents: read
+
+jobs:
+ subscriber-write:
+ environment:
+ name: main-branch-only
+ deployment: false
+ runs-on: ubuntu-24.04
+ if: >-
+ github.event.workflow_run.conclusion == 'success'
+ steps:
+ - name: Checkout Scripts
+ uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
+ with:
+ persist-credentials: false
+ sparse-checkout: |
+ llvm/utils/git/
+ .github/workflows/unprivileged-download-artifact/
+
+ - name: Download Data
+ uses: ./.github/workflows/unprivileged-download-artifact
+ id: download-artifact
+ with:
+ run-id: ${{ github.event.workflow_run.id }}
+ artifact-name: subscriber-data
+
+ - name: Collect Data
+ id: data
+ env:
+ DATA_FILE: subscriber-data
+ run: |
+ echo "issue-number=$(head -n1 $DATA_FILE)" >> $GITHUB_OUTPUT
+ echo "label-name=$(tail -n1 $DATA_FILE)" >> $GITHUB_OUTPUT
+
+ # Data coming from the pull_request event should be consider untrusted
+ # since the PR author will have full control of the information in the
+ # subscriber-data file. To validate the data we just need to check that
+ # the label actually exists on the given PR. We probably don't need to
+ # do this for the issues event, but we do it in anyway just to be
+ # extra safe.
+ - name: Validate Data
+ id: validated-label
+ uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
+ env:
+ ISSUE_NUMBER: ${{ steps.data.outputs.issue-number }}
+ LABEL_NAME: ${{ steps.data.outputs.label-name }}
+ with:
+ github-token: ${{ secrets.GITHUB_TOKEN }}
+ result-encoding: string
+ script: |
+ let labels = await github.rest.issues.listLabelsOnIssue({
+ owner: context.repo.owner,
+ repo: context.repo.repo,
+ issue_number: process.env.ISSUE_NUMBER
+ });
+
+ const hasLabel = labels.data.some((label) => label.name === process.env.LABEL_NAME);
+ if (hasLabel) {
+ return process.env.LABEL_NAME;
+ }
+ throw new Error(`Label ${process.env.LABEL_NAME} does not exist on issue ${process.env.ISSUE_NUMBER}.`);
+
+ - name: Setup Automation Script
+ working-directory: ./llvm/utils/git/
+ run: |
+ pip install --require-hashes -r requirements.txt
+
+ - id: app-token
+ uses: actions/create-github-app-token@1b10c78c7865c340bc4f6099eb2f838309f1e8c3 # v3.1.1
+ with:
+ client-id: ${{ secrets.LLVM_TOKEN_GENERATOR_CLIENT_ID }}
+ private-key: ${{ secrets.LLVM_TOKEN_GENERATOR_PRIVATE_KEY }}
+ owner: ${{ github.repository_owner }}
+ repositories: llvm-project
+ permission-members: read
+ permission-contents: read
+ permission-issues: write
+ permission-pull-requests: write
+
+ - name: Update subscribers
+ working-directory: ./llvm/utils/git/
+ env:
+ EVENT_TRIGGER: ${{ github.event.workflow_run.event }}
+ ISSUE_SUBSCRIBER_TOKEN: ${{ steps.app-token.outputs.token }}
+ LABEL_NAME: ${{ steps.validated-label.outputs.result }}
+ ISSUE_NUMBER: ${{ steps.data.outputs.issue-number }}
+ run: |
+ case "$EVENT_TRIGGER" in
+ pull_request)
+ command="pr-subscriber"
+ ;;
+ issues)
+ command="issue-subscriber"
+ ;;
+ *)
+ echo "Unknown event trigger: $EVENT_TRIGGER"
+ exit 1
+ ;;
+ esac
+ python3 ./github-automation.py \
+ --token "$ISSUE_SUBSCRIBER_TOKEN" \
+ "$command" \
+ --issue-number "$ISSUE_NUMBER" \
+ --label-name "$LABEL_NAME"
diff --git a/.github/workflows/subscriber.yml b/.github/workflows/subscriber.yml
new file mode 100644
index 0000000000000..b98a4a8c6cc18
--- /dev/null
+++ b/.github/workflows/subscriber.yml
@@ -0,0 +1,36 @@
+name: Subscriber
+
+on:
+ pull_request:
+ types:
+ - labeled
+ issues:
+ types:
+ - labeled
+
+permissions:
+ contents: read
+
+jobs:
+ subscriber:
+ runs-on: ubuntu-24.04
+ if: github.repository == 'llvm/llvm-project'
+ steps:
+ - id: data
+ env:
+ # github.event.number is for pull_request events and
+ # github.event.issue.number is for issues events.
+ ISSUE_NUMBER: ${{ github.event.number || github.event.issue.number }}
+ LABEL_NAME: ${{ github.event.label.name }}
+ run: |
+ filename=subscriber-data
+ echo "$ISSUE_NUMBER" >> $filename
+ echo "$LABEL_NAME" >> $filename
+ echo "filename=$filename" >> $GITHUB_OUTPUT
+
+
+ - name: Upload data
+ uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
+ with:
+ name: subscriber-data
+ path: ${{ steps.data.outputs.filename }}
|
| on: | ||
| workflow_run: | ||
| workflows: | ||
| - "Subscriber" | ||
| types: | ||
| - completed |
There was a problem hiding this comment.
GitHub recommends using workflow_run as a more secure alternative to pull_request_target. I disagree with this review.
|
One thing to note is that we merge this as-is, then existing pull requests will not trigger this new workflow and so it won't send out the notifications for new labels. We could temporarily add support for the pull_request_target event to workaround this, but I felt that the chances of a PR being updated and having a new label added without it being also rebased or merge origin/main was low. |
This consolidates duplicate logic from the pr-subscriber and issue-subscriber workflows into a new workflow called subscriber-write. This workflow uses the workflow_run trigger and is triggered by another new workflow called subscriber.
The subscriber workflow collects the label name and issue number from the labeled issue/pull requests and sends it to the subscriber-write workflow via artifacts.
Besides removing some duplicate code this change also allows us to switch from using the pull_request_target event to the pull_request event for handling pull request subscribers. pull_request executes in an untrusted context and helps protect us from some security risks.