diff --git a/.github/workflows/pull-request-commit.yml b/.github/workflows/pull-request-commit.yml new file mode 100644 index 00000000..76dc4327 --- /dev/null +++ b/.github/workflows/pull-request-commit.yml @@ -0,0 +1,185 @@ +# Credit https://github.com/expo/expo +# https://github.com/expo/expo/blob/main/.github/workflows/pr-labeler.yml +--- +name: PR labeler + +on: + push: + branches: [main] + pull_request: + types: [opened, synchronize] + +concurrency: + group: ${{ github.workflow }}-${{ github.event_name }}-${{ github.ref }} + cancel-in-progress: true + +jobs: + test-suite-fingerprint: + runs-on: ubuntu-22.04 + if: ${{ github.event.pull_request.head.repo.full_name == github.repository || github.event_name == 'push' }} + # REQUIRED: limit concurrency when pushing main(default) branch to prevent conflict for this action to update its fingerprint database + concurrency: fingerprint-${{ github.event_name != 'pull_request' && 'main' || github.run_id }} + permissions: + # REQUIRED: Allow comments of PRs + pull-requests: write + # REQUIRED: Allow updating fingerprint in acton caches + actions: write + steps: + - name: ⬇️ Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 100 + + - name: ⬇️ Fetch commits from base branch + run: git fetch origin main:main --depth 100 + if: github.event_name == 'pull_request' + + - name: 🔧 Setup Node + uses: actions/setup-node@v4 + with: + node-version-file: .nvmrc + cache: yarn + + - name: ⚙️ Install Dependencies + run: yarn install + + - name: Get the base commit + id: base-commit + run: | + # Since we limit this pr-labeler workflow only triggered from limited paths, we should use custom base commit + echo base-commit=$(git log -n 1 main --pretty=format:'%H' -- .github/workflows/pr-labeler.yml packages yarn.lock) >> "$GITHUB_OUTPUT" + + - name: 📷 Check fingerprint + id: fingerprint + uses: expo/expo-github-action/fingerprint@main + with: + previous-git-commit: ${{ steps.base-commit.outputs.base-commit }} + + - name: 👀 Debug fingerprint + run: | + echo "previousGitCommit=${{ steps.fingerprint.outputs.previous-git-commit }} currentGitCommit=${{ steps.fingerprint.outputs.current-git-commit }}" + echo "isPreviousFingerprintEmpty=${{ steps.fingerprint.outputs.previous-fingerprint == '' }}" + + - name: 🏷️ Labeling PR + uses: actions/github-script@v6 + if: ${{ github.event_name == 'pull_request' && steps.fingerprint.outputs.fingerprint-diff == '[]' }} + with: + script: | + try { + await github.rest.issues.removeLabel({ + issue_number: context.issue.number, + owner: context.repo.owner, + repo: context.repo.repo, + name: ['bot: fingerprint changed'] + }) + } catch (e) { + if (e.status != 404) { + throw e; + } + } + github.rest.issues.addLabels({ + issue_number: context.issue.number, + owner: context.repo.owner, + repo: context.repo.repo, + labels: ['bot: fingerprint compatible'] + }) + + - name: 🏷️ Labeling PR + uses: actions/github-script@v6 + if: ${{ github.event_name == 'pull_request' && steps.fingerprint.outputs.fingerprint-diff != '[]' }} + with: + script: | + try { + await github.rest.issues.removeLabel({ + issue_number: context.issue.number, + owner: context.repo.owner, + repo: context.repo.repo, + name: ['bot: fingerprint compatible'] + }) + } catch (e) { + if (e.status != 404) { + throw e; + } + } + github.rest.issues.addLabels({ + issue_number: context.issue.number, + owner: context.repo.owner, + repo: context.repo.repo, + labels: ['bot: fingerprint changed'] + }) + + - name: 🔍 Find old comment if it exists + uses: peter-evans/find-comment@v2 + if: ${{ github.event_name == 'pull_request' }} + id: old_comment + with: + issue-number: ${{ github.event.pull_request.number }} + comment-author: 'expo-bot' + body-includes: + + - name: 💬 Add comment with fingerprint + if: ${{ github.event_name == 'pull_request' && steps.fingerprint.outputs.fingerprint-diff != '[]' && steps.old_comment.outputs.comment-id == '' }} + uses: actions/github-script@v6 + with: + script: | + const diff = JSON.stringify(${{ steps.fingerprint.outputs.fingerprint-diff}}, null, 2); + const body = ` + The Pull Request introduced fingerprint changes against the base commit: ${{ steps.fingerprint.outputs.previous-git-commit }} +
Fingerprint diff + + \`\`\`json + ${diff} + \`\`\` + +
+ + --- + *Generated by [PR labeler](https://github.com/expo/expo/actions/workflows/pr-labeler.yml) 🤖* + `; + + github.rest.issues.createComment({ + issue_number: context.issue.number, + owner: context.repo.owner, + repo: context.repo.repo, + body: body, + }); + + - name: 💬 Update comment with fingerprint + if: ${{ github.event_name == 'pull_request' && steps.fingerprint.outputs.fingerprint-diff != '[]' && steps.old_comment.outputs.comment-id != '' }} + uses: actions/github-script@v6 + with: + script: | + const diff = JSON.stringify(${{ steps.fingerprint.outputs.fingerprint-diff}}, null, 2); + const body = ` + The Pull Request introduced fingerprint changes against the base commit: ${{ steps.fingerprint.outputs.previous-git-commit }} +
Fingerprint diff + + \`\`\`json + ${diff} + \`\`\` + +
+ + --- + *Generated by [PR labeler](https://github.com/expo/expo/actions/workflows/pr-labeler.yml) 🤖* + `; + + github.rest.issues.updateComment({ + issue_number: context.issue.number, + comment_id: '${{ steps.old_comment.outputs.comment-id }}', + owner: context.repo.owner, + repo: context.repo.repo, + body: body, + }); + + - name: 💬 Delete comment with fingerprint + if: ${{ github.event_name == 'pull_request' && steps.fingerprint.outputs.fingerprint-diff == '[]' && steps.old_comment.outputs.comment-id != '' }} + uses: actions/github-script@v6 + with: + script: | + github.rest.issues.deleteComment({ + issue_number: context.issue.number, + comment_id: '${{ steps.old_comment.outputs.comment-id }}', + owner: context.repo.owner, + repo: context.repo.repo, + }); \ No newline at end of file