name: Integration tests on: pull_request: push: branches: - main workflow_dispatch: inputs: ref: description: "The branch, tag, or SHA to checkout" required: true jobs: integration: name: Run API tests runs-on: ubuntu-latest environment: staging permissions: contents: read steps: - name: "check: require maintainer approval" if: github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name != github.repository run: | echo "::error::Integration tests from forked branches require maintainer approval." echo "::notice::Dispatch a test run at ${{ github.server_url }}/${{ github.repository }}/actions/workflows/integration.yml with ref 'pull/${{ github.event.pull_request.number }}/head'" exit 1 - name: "build: checkout the latest changes" uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: persist-credentials: false ref: ${{ inputs.ref || github.event.pull_request.head.sha || github.sha }} - name: "build: setup the node runtime" uses: actions/setup-node@820762786026740c76f36085b0efc47a31fe5020 # v7.0.0 with: cache: npm cache-dependency-path: package-lock.json node-version-file: .nvmrc - name: "build: install the required dependencies" run: npm ci - name: "build: package code for distribution" run: npm run build - name: "pretest(inputs): save the push event trigger commit URL" if: github.event_name == 'push' id: push run: | echo "url=$URL" >> "$GITHUB_OUTPUT" env: URL: ${{ github.event.head_commit.url }} - name: "pretest(inputs): save the pull request event trigger URL" if: github.event_name == 'pull_request' id: pull_request run: | echo "url=$URL" >> "$GITHUB_OUTPUT" env: URL: ${{ github.event.pull_request.html_url }} - name: "pretest(inputs): save the workflow dispatch event trigger commit URL" if: github.event_name == 'workflow_dispatch' id: workflow_dispatch run: | echo "url=https://github.com/${GITHUB_REPOSITORY}/commit/${INPUT_REF}" >> "$GITHUB_OUTPUT" env: INPUT_REF: ${{ inputs.ref }} - name: "test(wfb): send a payload to workflow builder via webhook trigger" id: wfb uses: ./ with: errors: true webhook: ${{ secrets.SLACK_WEBHOOK_TRIGGER }} webhook-type: webhook-trigger payload: | author: ${{ github.event.sender.login }} channel_id: ${{ secrets.SLACK_CHANNEL_ID }} event_url: ${{ steps.push.outputs.url || steps.pull_request.outputs.url || steps.workflow_dispatch.outputs.url }} repo_name: ${{ github.event.repository.full_name }} status: ${{ job.status }} - name: "test(wfb): confirm a payload was sent" run: test -n "$WFB_OUTPUT_TIME" env: WFB_OUTPUT_TIME: ${{ steps.wfb.outputs.time }} - name: "test(api): post a message to channel" id: message uses: ./ with: errors: true method: chat.postMessage token: ${{ secrets.SLACK_BOT_TOKEN }} payload: | channel: ${{ secrets.SLACK_CHANNEL_ID }} text: ":checkered_flag: Action happens at " - name: "test(api): confirm a message was posted" run: test -n "$MESSAGE_OUTPUT_TS" env: MESSAGE_OUTPUT_TS: ${{ steps.message.outputs.ts }} - name: "test(api): post a multiline message" # https://github.com/slackapi/slack-github-action/issues/637 id: multiline uses: ./ with: errors: true method: chat.postMessage token: ${{ secrets.SLACK_BOT_TOKEN }} payload: | channel: ${{ secrets.SLACK_CHANNEL_ID }} text: ":checkered_flag: A multiline message wraps across lines with a blank line before " - name: "test(api): confirm the multiline message was posted" run: test -n "$MULTILINE_OUTPUT_TS" env: MULTILINE_OUTPUT_TS: ${{ steps.multiline.outputs.ts }} - name: "test(api): post a message with blocks" id: blocks uses: ./ with: errors: true method: chat.postMessage token: ${{ secrets.SLACK_BOT_TOKEN }} payload: | channel: ${{ secrets.SLACK_CHANNEL_ID }} text: ":eyes: Event received..." attachments: - color: "dbab09" fields: - title: "Status" short: true value: "Processing" - name: "test(api): confirm the blocks were posted" run: test -n "$BLOCKS_OUTPUT_TS" env: BLOCKS_OUTPUT_TS: ${{ steps.blocks.outputs.ts }} - name: "test(api): post a threaded message" id: timer uses: ./ with: errors: true method: chat.postMessage token: ${{ secrets.SLACK_BOT_TOKEN }} payload: | channel: ${{ secrets.SLACK_CHANNEL_ID }} text: "Started at `${{ steps.blocks.outputs.time }}`" thread_ts: "${{ steps.blocks.outputs.ts }}" - name: "test(api): confirm the thread started" run: test -n "$TIMER_OUTPUT_TIME" env: TIMER_OUTPUT_TIME: ${{ steps.timer.outputs.time }} - name: "test(api): wait to mock event processing" run: sleep 3 - name: "test(api): update the original message" id: finished uses: ./ with: errors: true method: chat.update token: ${{ secrets.SLACK_BOT_TOKEN }} payload: | channel: ${{ secrets.SLACK_CHANNEL_ID }} ts: "${{ steps.blocks.outputs.ts }}" text: ":gear: Event processed!" attachments: - color: "28a745" fields: - title: "Status" short: true value: "Completed" - name: "test(api): post another threaded message" id: done uses: ./ with: errors: true method: chat.postMessage token: ${{ secrets.SLACK_BOT_TOKEN }} payload: | channel: ${{ steps.blocks.outputs.channel_id }} text: "Finished at `${{ steps.finished.outputs.time }}`" thread_ts: "${{ steps.timer.outputs.thread_ts }}" - name: "test(api): post a file into a channel" id: file uses: ./ with: errors: true method: files.uploadV2 token: ${{ secrets.SLACK_BOT_TOKEN }} payload: | channel_id: ${{ secrets.SLACK_CHANNEL_ID }} initial_comment: ":robot_face: The codes exists here" file: .github/workflows/integration.yml filename: integration.yml - name: "test(api): react to the completed update message" uses: ./ with: errors: true method: reactions.add token: ${{ secrets.SLACK_BOT_TOKEN }} payload: | channel: ${{ secrets.SLACK_CHANNEL_ID }} timestamp: ${{ steps.blocks.outputs.ts }} name: "tada" - name: "test(api): confirm the thread ended" run: test -n "$DONE_OUTPUT_TIME" env: DONE_OUTPUT_TIME: ${{ steps.done.outputs.time }} - name: "test(incoming): post a message via incoming webhook" id: incoming uses: ./ with: errors: true webhook: ${{ secrets.SLACK_INCOMING_WEBHOOK }} webhook-type: incoming-webhook payload: | text: "Incoming webhook test for the Slack GitHub Action" blocks: - type: section text: type: plain_text text: ":link: A message was received via incoming webhook" emoji: true - name: "test(incoming): confirm a webhook was posted" run: test -n "$INCOMING_WEBHOOK_OUTPUT_TIME" env: INCOMING_WEBHOOK_OUTPUT_TIME: ${{ steps.incoming.outputs.time }} - name: "test(incoming): reveal contents of the github payload" run: echo "$JSON" env: JSON: ${{ toJSON(github) }} - name: "test(incoming): post a message via payload file" id: payload_file uses: ./ with: errors: true payload-file-path: ./.github/resources/.slack/incoming-webhook.json payload-templated: true webhook: ${{ secrets.SLACK_INCOMING_WEBHOOK }} webhook-type: incoming-webhook env: JOB_STATUS: ${{ job.status }} ATTACHMENT_COLOR: ${{ (job.status == 'success' && 'good') || (job.status == 'failure' && 'danger') || 'warning' }} - name: "test(incoming): confirm a payload file was posted" run: test -n "$PAYLOAD_FILE_OUTPUT_TIME" env: PAYLOAD_FILE_OUTPUT_TIME: ${{ steps.payload_file.outputs.time }} cli: name: Run CLI tests runs-on: ${{ matrix.os }} environment: staging strategy: fail-fast: false matrix: os: - ubuntu-latest - macos-latest - windows-latest permissions: contents: read steps: - name: "build: checkout the latest changes" uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: persist-credentials: false ref: ${{ inputs.ref || github.event.pull_request.head.sha || github.sha }} - name: "test(cli): run a slack cli version check" id: version uses: ./cli with: command: "version" - name: "test(cli): confirm the version check outputs" shell: bash run: | set -ex [ "$CLI_OK" = "true" ] echo "$CLI_TIME" | grep -qE '^[0-9]+$' [ -n "$CLI_RESPONSE" ] env: CLI_OK: ${{ steps.version.outputs.ok }} CLI_RESPONSE: ${{ steps.version.outputs.response }} CLI_TIME: ${{ steps.version.outputs.time }} - name: "test(cli): run an unknown command" id: unknown continue-on-error: true uses: ./cli with: command: "off" - name: "test(cli): confirm the unknown command outputs" shell: bash run: | set -ex [ "$CLI_OK" = "false" ] echo "$CLI_TIME" | grep -qE '^[0-9]+$' [ -n "$CLI_RESPONSE" ] env: CLI_OK: ${{ steps.unknown.outputs.ok }} CLI_RESPONSE: ${{ steps.unknown.outputs.response }} CLI_TIME: ${{ steps.unknown.outputs.time }} - name: "chore: configure the actioneering application" shell: bash run: mv .github/resources/.slack .slack - name: "test(cli): validate the app manifest" uses: ./cli with: command: "manifest" token: ${{ secrets.SLACK_SERVICE_TOKEN }} - name: "test(cli): deploy the app" uses: ./cli with: command: "deploy --app ${{ vars.SLACK_APP_ID }} --hide-triggers --force" token: ${{ secrets.SLACK_SERVICE_TOKEN }}