-
Notifications
You must be signed in to change notification settings - Fork 2
feat: implement the Probot App, Notification workflows #136
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,45 @@ | ||
| version: 2 | ||
| mergeable: | ||
| - when: pull_request.*, pull_request_review.* | ||
| validate: | ||
| # Validate PR title | ||
| - do: title | ||
| must_include: | ||
| regex: '^(feat|docs|chore|fix|refactor|test|style|perf)(\(\w+\))?: .{5,}' | ||
| message: "Semantic release conventions must be followed. Example: feat(auth): add login page. Title must be at least 5 characters after the prefix." | ||
|
|
||
| # Ensure PR description is provided | ||
| - do: description | ||
| must_include: | ||
| regex: "[\\s\\S]{20,}" # At least 20 characters | ||
| message: "Please provide a meaningful description of the PR (minimum 20 characters)." | ||
|
|
||
| # Ensure PR references an associated issue | ||
| - do: description | ||
| must_include: | ||
| regex: "(Closes|Fixes|Resolves|Addresses)\\s+#[0-9]+(,?\\s*#[0-9]+)*" | ||
| message: "PR must reference at least one issue (e.g., Closes #123, Fixes #123, #124)." | ||
|
|
||
| # Ensure at least one required label is applied | ||
| - do: label | ||
| must_include: | ||
| regex: "^(bug|enhancement|documentation|feature|refactor|performance|chore|wip|test|ci|security|dependencies)$" | ||
| message: "PR must include at least one valid label." | ||
| # Ensure PR has at least one assignee | ||
|
|
||
| - do: assignee | ||
| min: | ||
| count: 1 | ||
| message: "PR must have at least one assignee." | ||
| # Ensure PR has at least one reviewer requested | ||
| - do: approvals | ||
| min: | ||
| count: 1 | ||
| message: "PR must have at least one reviewer requested or approved." | ||
|
|
||
| pass: | ||
| - do: labels | ||
| add: | ||
| - "validated" | ||
| - do: checks | ||
| status: "success" |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,178 @@ | ||
| name: Notify (GitHub Events) | ||
|
|
||
| permissions: | ||
| issues: write | ||
| pull-requests: write | ||
| contents: read | ||
|
|
||
| on: | ||
| issues: | ||
| types: [opened, edited, reopened, closed, assigned, labeled] | ||
| pull_request: | ||
| types: [opened, closed, reopened, ready_for_review, review_requested] | ||
| pull_request_review: | ||
| types: [submitted, edited, dismissed] | ||
| issue_comment: | ||
| types: [created, edited] | ||
| pull_request_review_comment: | ||
| types: [created, edited] | ||
|
|
||
| jobs: | ||
| notify: | ||
| runs-on: ubuntu-latest | ||
| name: Send Notifications | ||
|
|
||
| steps: | ||
| - name: Determine Event Type | ||
| id: event_info | ||
| run: | | ||
| EVENT="${{ github.event_name }}" | ||
| ACTION="${{ github.event.action }}" | ||
| REPO="${{ github.repository }}" | ||
| ACTOR="${{ github.actor }}" | ||
| REPO_URL="${{ github.server_url }}/${{ github.repository }}" | ||
|
|
||
| if [[ "$EVENT" == "issues" ]]; then | ||
| TITLE="Issue $ACTION: ${{ github.event.issue.title }}" | ||
| URL="${{ github.event.issue.html_url }}" | ||
| NUMBER="${{ github.event.issue.number }}" | ||
| USER="${{ github.event.issue.user.login }}" | ||
| DESCRIPTION="Issue #$NUMBER by $USER" | ||
| STATE="${{ github.event.issue.state }}" | ||
| EMOJI="🐛" | ||
|
|
||
| elif [[ "$EVENT" == "pull_request" ]]; then | ||
| NUMBER="${{ github.event.pull_request.number }}" | ||
| USER="${{ github.event.pull_request.user.login }}" | ||
| URL="${{ github.event.pull_request.html_url }}" | ||
| STATE="${{ github.event.pull_request.state }}" | ||
| SOURCE="${{ github.event.pull_request.head.ref }}" | ||
| TARGET="${{ github.event.pull_request.base.ref }}" | ||
|
|
||
| if [[ "$ACTION" == "closed" && "${{ github.event.pull_request.merged }}" == "true" ]]; then | ||
| TITLE="PR merged: ${{ github.event.pull_request.title }}" | ||
| EMOJI="✅" | ||
| STATE="merged" | ||
| elif [[ "$ACTION" == "closed" ]]; then | ||
| TITLE="PR closed: ${{ github.event.pull_request.title }}" | ||
| EMOJI="❌" | ||
| else | ||
| TITLE="PR $ACTION: ${{ github.event.pull_request.title }}" | ||
| EMOJI="🔀" | ||
| fi | ||
| DESCRIPTION="PR #$NUMBER by $USER: $SOURCE → $TARGET" | ||
|
|
||
| elif [[ "$EVENT" == "pull_request_review" ]]; then | ||
| TITLE="PR Review: ${{ github.event.pull_request.title }}" | ||
| URL="${{ github.event.review.html_url }}" | ||
| NUMBER="${{ github.event.pull_request.number }}" | ||
| USER="${{ github.event.review.user.login }}" | ||
| REVIEW_STATE="${{ github.event.review.state }}" | ||
| STATE="${{ github.event.review.state }}" | ||
| SOURCE="${{ github.event.pull_request.head.ref }}" | ||
| TARGET="${{ github.event.pull_request.base.ref }}" | ||
| DESCRIPTION="Review by $USER on PR #$NUMBER" | ||
| EMOJI="👀" | ||
|
|
||
| elif [[ "$EVENT" == "issue_comment" ]]; then | ||
| NUMBER="${{ github.event.issue.number }}" | ||
| USER="${{ github.event.comment.user.login }}" | ||
| URL="${{ github.event.comment.html_url }}" | ||
| STATE="commented" | ||
|
|
||
| if [[ "${{ github.event.issue.pull_request }}" != "" ]]; then | ||
| TITLE="Comment on PR: ${{ github.event.issue.title }}" | ||
| EMOJI="💬" | ||
| else | ||
| TITLE="Comment on Issue: ${{ github.event.issue.title }}" | ||
| EMOJI="💬" | ||
| fi | ||
| DESCRIPTION="Comment by $USER on #$NUMBER" | ||
|
|
||
| elif [[ "$EVENT" == "pull_request_review_comment" ]]; then | ||
| TITLE="Comment on PR: ${{ github.event.pull_request.title }}" | ||
| URL="${{ github.event.comment.html_url }}" | ||
| NUMBER="${{ github.event.pull_request.number }}" | ||
| USER="${{ github.event.comment.user.login }}" | ||
| STATE="commented" | ||
| SOURCE="${{ github.event.pull_request.head.ref }}" | ||
| TARGET="${{ github.event.pull_request.base.ref }}" | ||
| DESCRIPTION="Review comment by $USER on PR #$NUMBER" | ||
| EMOJI="💬" | ||
| else | ||
| TITLE="GitHub Event: $EVENT" | ||
| URL="${{ github.event.repository.html_url }}" | ||
| DESCRIPTION="Event triggered in $REPO" | ||
| STATE="N/A" | ||
| NUMBER="N/A" | ||
| USER="$ACTOR" | ||
| EMOJI="📢" | ||
| fi | ||
|
|
||
| echo "title=$TITLE" >> $GITHUB_OUTPUT | ||
| echo "url=$URL" >> $GITHUB_OUTPUT | ||
| echo "description=$DESCRIPTION" >> $GITHUB_OUTPUT | ||
| echo "emoji=$EMOJI" >> $GITHUB_OUTPUT | ||
| echo "number=${NUMBER:-N/A}" >> $GITHUB_OUTPUT | ||
| echo "user=${USER:-$ACTOR}" >> $GITHUB_OUTPUT | ||
| echo "state=${STATE:-N/A}" >> $GITHUB_OUTPUT | ||
| echo "source=${SOURCE:-N/A}" >> $GITHUB_OUTPUT | ||
| echo "target=${TARGET:-N/A}" >> $GITHUB_OUTPUT | ||
| echo "repo_url=$REPO_URL" >> $GITHUB_OUTPUT | ||
|
|
||
| - name: Google Chat Notification | ||
| if: always() | ||
| uses: Co-qn/google-chat-notification@releases/v1 | ||
| with: | ||
| name: ${{ steps.event_info.outputs.title }} | ||
| url: ${{ secrets.GOOGLE_CHAT_WEBHOOK }} | ||
| status: ${{ job.status }} | ||
|
|
||
| - name: Slack Notification | ||
| if: always() | ||
| uses: slackapi/slack-github-action@v1.24.0 | ||
| with: | ||
| channel-id: ${{ secrets.SLACK_CHANNEL_ID }} | ||
| payload: | | ||
| { | ||
| "text": "${{ steps.event_info.outputs.title }}", | ||
| "blocks": [ | ||
| { | ||
| "type": "header", | ||
| "text": { | ||
| "type": "plain_text", | ||
| "text": "${{ steps.event_info.outputs.emoji }} ${{ steps.event_info.outputs.title }}" | ||
| } | ||
| }, | ||
| { | ||
| "type": "section", | ||
| "fields": [ | ||
| { "type": "mrkdwn", "text": "*Repository:*\n<${{ steps.event_info.outputs.repo_url }}|${{ github.repository }}>" }, | ||
| { "type": "mrkdwn", "text": "*Event:*\n${{ github.event_name }}" }, | ||
| { "type": "mrkdwn", "text": "*Author:*\n${{ steps.event_info.outputs.user }}" }, | ||
| { "type": "mrkdwn", "text": "*Action:*\n${{ github.event.action }}" }, | ||
| { "type": "mrkdwn", "text": "*Number:*\n<${{ steps.event_info.outputs.url }}|#${{ steps.event_info.outputs.number }}>" }, | ||
| { "type": "mrkdwn", "text": "*State:*\n${{ steps.event_info.outputs.state }}" } | ||
| ] | ||
| }, | ||
| { | ||
| "type": "section", | ||
| "text": { "type": "mrkdwn", "text": "${{ steps.event_info.outputs.description }}" } | ||
| }, | ||
| { | ||
| "type": "actions", | ||
| "elements": [ | ||
| { "type": "button", "text": { "type": "plain_text", "text": "View on GitHub" }, "url": "${{ steps.event_info.outputs.url }}", "style": "primary" }, | ||
| { "type": "button", "text": { "type": "plain_text", "text": "View Repository" }, "url": "${{ steps.event_info.outputs.repo_url }}" } | ||
| ] | ||
| }, | ||
| { | ||
| "type": "context", | ||
| "elements": [ | ||
| { "type": "mrkdwn", "text": "Triggered by ${{ github.actor }} • ${{ github.event_name }} event" } | ||
| ] | ||
| } | ||
| ] | ||
| } | ||
| env: | ||
| SLACK_BOT_TOKEN: ${{ secrets.SLACK_BOT_TOKEN }} | ||
| Original file line number | Diff line number | Diff line change | ||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,137 @@ | ||||||||||||||||||
| name: Pre-Commit Checks | ||||||||||||||||||
|
|
||||||||||||||||||
| on: | ||||||||||||||||||
| push: | ||||||||||||||||||
| branches: | ||||||||||||||||||
| - main | ||||||||||||||||||
| - develop | ||||||||||||||||||
| - 'feat/**' | ||||||||||||||||||
| - 'feature/**' | ||||||||||||||||||
| - 'test/**' | ||||||||||||||||||
| - 'chore/**' | ||||||||||||||||||
| - 'fix/**' | ||||||||||||||||||
| - 'hotfix/**' | ||||||||||||||||||
| - 'docs/**' | ||||||||||||||||||
| pull_request: | ||||||||||||||||||
| types: [opened, synchronize, reopened] | ||||||||||||||||||
|
|
||||||||||||||||||
| jobs: | ||||||||||||||||||
| precommit: | ||||||||||||||||||
| runs-on: ubuntu-latest | ||||||||||||||||||
|
|
||||||||||||||||||
| steps: | ||||||||||||||||||
| - name: Checkout Repository | ||||||||||||||||||
| uses: actions/checkout@v4 | ||||||||||||||||||
|
|
||||||||||||||||||
| - name: Set up Go | ||||||||||||||||||
| uses: actions/setup-go@v4 | ||||||||||||||||||
| with: | ||||||||||||||||||
| go-version: '1.24' | ||||||||||||||||||
|
Comment on lines
+26
to
+29
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🧩 Analysis chain🌐 Web query:
💡 Result: The latest stable Go release as of December 8, 2025 is Go 1.25 (released August 12, 2025). Yes — Go 1.24 does exist (released February 11, 2025). [1][2] Sources: 🌐 Web query:
💡 Result: The latest release is actions/setup-go v6.0.0. [1][2] Sources: Update actions/setup-go to v6 (latest version). The workflow uses Apply this diff: - name: Set up Go
- uses: actions/setup-go@v4
+ uses: actions/setup-go@v6
with:
go-version: '1.24'Consider updating to Go 1.25 if you need the latest features and fixes. 📝 Committable suggestion
Suggested change
🧰 Tools🪛 actionlint (1.7.9)27-27: the runner of "actions/setup-go@v4" action is too old to run on GitHub Actions. update the action's version to fix this issue (action) 🤖 Prompt for AI Agents |
||||||||||||||||||
|
|
||||||||||||||||||
| - name: Install goimports | ||||||||||||||||||
| run: | | ||||||||||||||||||
| go install golang.org/x/tools/cmd/goimports@latest | ||||||||||||||||||
| echo "$HOME/go/bin" >> $GITHUB_PATH | ||||||||||||||||||
|
|
||||||||||||||||||
| - name: Add Go bin to PATH | ||||||||||||||||||
| run: echo "$HOME/go/bin" >> $GITHUB_PATH | ||||||||||||||||||
|
|
||||||||||||||||||
| - name: Install goimports | ||||||||||||||||||
| run: go install golang.org/x/tools/cmd/goimports@latest | ||||||||||||||||||
|
Comment on lines
+31
to
+40
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Remove duplicate steps for goimports installation and PATH setup. Lines 31–34 install goimports and add Go bin to PATH, but lines 36–37 and 39–40 repeat this work verbatim. Consolidate these into a single, cohesive step to reduce redundancy and improve clarity. Apply this diff to consolidate: - name: Install goimports
run: |
go install golang.org/x/tools/cmd/goimports@latest
echo "$HOME/go/bin" >> $GITHUB_PATH
- - name: Add Go bin to PATH
- run: echo "$HOME/go/bin" >> $GITHUB_PATH
-
- - name: Install goimports
- run: go install golang.org/x/tools/cmd/goimports@latest
-
- name: Install golangci-lint v2.7.2🤖 Prompt for AI Agents |
||||||||||||||||||
|
|
||||||||||||||||||
| - name: Install golangci-lint v2.7.2 | ||||||||||||||||||
| run: | | ||||||||||||||||||
| curl -sSL https://github.com/golangci/golangci-lint/releases/download/v2.7.2/golangci-lint-2.7.2-linux-amd64.tar.gz \ | ||||||||||||||||||
| | tar -xz -C $HOME/go/bin --strip-components=1 | ||||||||||||||||||
|
|
||||||||||||||||||
| - name: Set up Python | ||||||||||||||||||
| uses: actions/setup-python@v5 | ||||||||||||||||||
| with: | ||||||||||||||||||
| python-version: "3.11" | ||||||||||||||||||
|
|
||||||||||||||||||
| - name: Install pre-commit | ||||||||||||||||||
| run: | | ||||||||||||||||||
| python -m pip install --upgrade pip | ||||||||||||||||||
| pip install pre-commit | ||||||||||||||||||
|
|
||||||||||||||||||
| - name: Load Pre-commit Config | ||||||||||||||||||
| run: | | ||||||||||||||||||
| if [ ! -f ".pre-commit-config.yaml" ]; then | ||||||||||||||||||
| echo " No .pre-commit-config.yaml found — downloading BerryBytes global config..." | ||||||||||||||||||
| curl -sSL \ | ||||||||||||||||||
| https://raw.githubusercontent.com/BerryBytes/precommit-util/main/global/precommitFile/.pre-commit-config.yaml \ | ||||||||||||||||||
| -o .pre-commit-config.yaml | ||||||||||||||||||
| else | ||||||||||||||||||
| echo "✔ Using project's existing .pre-commit-config.yaml" | ||||||||||||||||||
| fi | ||||||||||||||||||
|
|
||||||||||||||||||
| - name: Inject temporary Stylelint config for CI | ||||||||||||||||||
| run: | | ||||||||||||||||||
| if [ ! -f ".stylelintrc.json" ]; then | ||||||||||||||||||
| echo " Creating temporary .stylelintrc.json for CI..." | ||||||||||||||||||
| cat <<EOF > .stylelintrc.json | ||||||||||||||||||
| { | ||||||||||||||||||
| "extends": "stylelint-config-standard", | ||||||||||||||||||
| "rules": { | ||||||||||||||||||
| "no-duplicate-selectors": true, | ||||||||||||||||||
| "color-hex-length": "short", | ||||||||||||||||||
| "selector-no-qualifying-type": true, | ||||||||||||||||||
| "selector-max-id": 0 | ||||||||||||||||||
| } | ||||||||||||||||||
| } | ||||||||||||||||||
| EOF | ||||||||||||||||||
| else | ||||||||||||||||||
| echo "✔ .stylelintrc.json already exists — skipping" | ||||||||||||||||||
| fi | ||||||||||||||||||
|
|
||||||||||||||||||
| # -------------------------------------------------------------------- | ||||||||||||||||||
| # STEP 1: Run pre-commit (capture full logs and exit code safely) | ||||||||||||||||||
| # -------------------------------------------------------------------- | ||||||||||||||||||
| - name: Run pre-commit (full logs) | ||||||||||||||||||
| id: runprecommit | ||||||||||||||||||
| run: | | ||||||||||||||||||
| echo "🔍 Running full pre-commit checks..." | ||||||||||||||||||
|
|
||||||||||||||||||
| set +e # allow failure | ||||||||||||||||||
| pre-commit run --all-files --verbose --show-diff-on-failure --color never \ | ||||||||||||||||||
| | tee full_precommit.log | ||||||||||||||||||
| exit_code=${PIPESTATUS[0]} | ||||||||||||||||||
|
|
||||||||||||||||||
| echo "Pre-commit exit code: $exit_code" | ||||||||||||||||||
| echo "$exit_code" > precommit_exit_code.txt | ||||||||||||||||||
|
|
||||||||||||||||||
| # -------------------------------------------------------------------- | ||||||||||||||||||
| # STEP 2: Summary of FAILED hooks | ||||||||||||||||||
| # -------------------------------------------------------------------- | ||||||||||||||||||
| - name: Pre-commit summary of failed hooks | ||||||||||||||||||
| run: | | ||||||||||||||||||
| echo "=====================================================" | ||||||||||||||||||
| echo " PRE-COMMIT SUMMARY" | ||||||||||||||||||
| echo "=====================================================" | ||||||||||||||||||
|
|
||||||||||||||||||
| exit_code=$(cat precommit_exit_code.txt) | ||||||||||||||||||
|
|
||||||||||||||||||
| if [ "$exit_code" = "0" ]; then | ||||||||||||||||||
| echo " All hooks passed!" | ||||||||||||||||||
| exit 0 | ||||||||||||||||||
| fi | ||||||||||||||||||
|
|
||||||||||||||||||
| echo " Hooks failed — showing summary:" | ||||||||||||||||||
| echo "" | ||||||||||||||||||
|
|
||||||||||||||||||
| echo " FAILED HOOKS:" | ||||||||||||||||||
| grep -E "^\w.*\.{3,}Failed" full_precommit.log || echo " None" | ||||||||||||||||||
| echo "-----------------------------------------------------" | ||||||||||||||||||
|
|
||||||||||||||||||
| echo " FILES WITH ISSUES:" | ||||||||||||||||||
| grep -E "files were modified by this hook" -A3 full_precommit.log \ | ||||||||||||||||||
| | sed 's/^/ - /' || echo " None" | ||||||||||||||||||
| echo "-----------------------------------------------------" | ||||||||||||||||||
|
|
||||||||||||||||||
| echo " ERROR DETAILS:" | ||||||||||||||||||
| grep -Ei "(error|failed|violation|missing|line too long|could not|warning)" full_precommit.log \ | ||||||||||||||||||
| | grep -Ev "^(---|\+\+\+|@@|diff --git|index )" \ | ||||||||||||||||||
| | sed 's/^/ • /' || echo " None" | ||||||||||||||||||
| echo "-----------------------------------------------------" | ||||||||||||||||||
|
|
||||||||||||||||||
| exit $exit_code | ||||||||||||||||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Critical: Script injection vulnerability in inline shell script.
The workflow directly interpolates untrusted GitHub event data (issue titles, PR titles, user inputs) into an inline shell script, creating a script injection vulnerability. An attacker could craft malicious titles or descriptions containing shell commands that would be executed in the workflow context.
For example, a malicious issue title like:
Fix: Pass all untrusted inputs through environment variables instead of direct interpolation.
Apply this diff:
- name: Determine Event Type id: event_info + env: + EVENT_NAME: ${{ github.event_name }} + EVENT_ACTION: ${{ github.event.action }} + ISSUE_TITLE: ${{ github.event.issue.title }} + ISSUE_URL: ${{ github.event.issue.html_url }} + ISSUE_NUMBER: ${{ github.event.issue.number }} + ISSUE_USER: ${{ github.event.issue.user.login }} + ISSUE_STATE: ${{ github.event.issue.state }} + PR_TITLE: ${{ github.event.pull_request.title }} + PR_NUMBER: ${{ github.event.pull_request.number }} + PR_USER: ${{ github.event.pull_request.user.login }} + PR_URL: ${{ github.event.pull_request.html_url }} + PR_STATE: ${{ github.event.pull_request.state }} + PR_SOURCE: ${{ github.event.pull_request.head.ref }} + PR_TARGET: ${{ github.event.pull_request.base.ref }} + PR_MERGED: ${{ github.event.pull_request.merged }} + REVIEW_URL: ${{ github.event.review.html_url }} + REVIEW_USER: ${{ github.event.review.user.login }} + REVIEW_STATE: ${{ github.event.review.state }} + COMMENT_USER: ${{ github.event.comment.user.login }} + COMMENT_URL: ${{ github.event.comment.html_url }} + REPO: ${{ github.repository }} + ACTOR: ${{ github.actor }} + REPO_URL: ${{ github.server_url }}/${{ github.repository }} run: | - EVENT="${{ github.event_name }}" - ACTION="${{ github.event.action }}" - REPO="${{ github.repository }}" - ACTOR="${{ github.actor }}" - REPO_URL="${{ github.server_url }}/${{ github.repository }}" + EVENT="$EVENT_NAME" + ACTION="$EVENT_ACTION" if [[ "$EVENT" == "issues" ]]; then - TITLE="Issue $ACTION: ${{ github.event.issue.title }}" - URL="${{ github.event.issue.html_url }}" - NUMBER="${{ github.event.issue.number }}" - USER="${{ github.event.issue.user.login }}" + TITLE="Issue $ACTION: $ISSUE_TITLE" + URL="$ISSUE_URL" + NUMBER="$ISSUE_NUMBER" + USER="$ISSUE_USER" DESCRIPTION="Issue #$NUMBER by $USER" - STATE="${{ github.event.issue.state }}" + STATE="$ISSUE_STATE" EMOJI="🐛" elif [[ "$EVENT" == "pull_request" ]]; then - NUMBER="${{ github.event.pull_request.number }}" - USER="${{ github.event.pull_request.user.login }}" - URL="${{ github.event.pull_request.html_url }}" - STATE="${{ github.event.pull_request.state }}" - SOURCE="${{ github.event.pull_request.head.ref }}" - TARGET="${{ github.event.pull_request.base.ref }}" + NUMBER="$PR_NUMBER" + USER="$PR_USER" + URL="$PR_URL" + STATE="$PR_STATE" + SOURCE="$PR_SOURCE" + TARGET="$PR_TARGET" - if [[ "$ACTION" == "closed" && "${{ github.event.pull_request.merged }}" == "true" ]]; then - TITLE="PR merged: ${{ github.event.pull_request.title }}" + if [[ "$ACTION" == "closed" && "$PR_MERGED" == "true" ]]; then + TITLE="PR merged: $PR_TITLE" EMOJI="✅" STATE="merged" elif [[ "$ACTION" == "closed" ]]; then - TITLE="PR closed: ${{ github.event.pull_request.title }}" + TITLE="PR closed: $PR_TITLE" EMOJI="❌" else - TITLE="PR $ACTION: ${{ github.event.pull_request.title }}" + TITLE="PR $ACTION: $PR_TITLE" EMOJI="🔀" fi DESCRIPTION="PR #$NUMBER by $USER: $SOURCE → $TARGET" elif [[ "$EVENT" == "pull_request_review" ]]; then - TITLE="PR Review: ${{ github.event.pull_request.title }}" - URL="${{ github.event.review.html_url }}" - NUMBER="${{ github.event.pull_request.number }}" - USER="${{ github.event.review.user.login }}" - REVIEW_STATE="${{ github.event.review.state }}" - STATE="${{ github.event.review.state }}" - SOURCE="${{ github.event.pull_request.head.ref }}" - TARGET="${{ github.event.pull_request.base.ref }}" + TITLE="PR Review: $PR_TITLE" + URL="$REVIEW_URL" + NUMBER="$PR_NUMBER" + USER="$REVIEW_USER" + REVIEW_STATE="$REVIEW_STATE" + STATE="$REVIEW_STATE" + SOURCE="$PR_SOURCE" + TARGET="$PR_TARGET" DESCRIPTION="Review by $USER on PR #$NUMBER" EMOJI="👀" elif [[ "$EVENT" == "issue_comment" ]]; then - NUMBER="${{ github.event.issue.number }}" - USER="${{ github.event.comment.user.login }}" - URL="${{ github.event.comment.html_url }}" + NUMBER="$ISSUE_NUMBER" + USER="$COMMENT_USER" + URL="$COMMENT_URL" STATE="commented" if [[ "${{ github.event.issue.pull_request }}" != "" ]]; then - TITLE="Comment on PR: ${{ github.event.issue.title }}" + TITLE="Comment on PR: $ISSUE_TITLE" EMOJI="💬" else - TITLE="Comment on Issue: ${{ github.event.issue.title }}" + TITLE="Comment on Issue: $ISSUE_TITLE" EMOJI="💬" fi DESCRIPTION="Comment by $USER on #$NUMBER" elif [[ "$EVENT" == "pull_request_review_comment" ]]; then - TITLE="Comment on PR: ${{ github.event.pull_request.title }}" - URL="${{ github.event.comment.html_url }}" - NUMBER="${{ github.event.pull_request.number }}" - USER="${{ github.event.comment.user.login }}" + TITLE="Comment on PR: $PR_TITLE" + URL="$COMMENT_URL" + NUMBER="$PR_NUMBER" + USER="$COMMENT_USER" STATE="commented" - SOURCE="${{ github.event.pull_request.head.ref }}" - TARGET="${{ github.event.pull_request.base.ref }}" + SOURCE="$PR_SOURCE" + TARGET="$PR_TARGET" DESCRIPTION="Review comment by $USER on PR #$NUMBER" EMOJI="💬" else TITLE="GitHub Event: $EVENT" - URL="${{ github.event.repository.html_url }}" + URL="$REPO_URL" DESCRIPTION="Event triggered in $REPO" STATE="N/A" NUMBER="N/A" USER="$ACTOR" EMOJI="📢" fi🧰 Tools
🪛 actionlint (1.7.9)
28-28: "github.event.issue.title" is potentially untrusted. avoid using it directly in inline scripts. instead, pass it through an environment variable. see https://docs.github.com/en/actions/reference/security/secure-use#good-practices-for-mitigating-script-injection-attacks for more details
(expression)