Automate your Workflow. Learn About GitHub Actions and Slack Webhooks

Get in the action, don't slack!

Automate your Workflow. Learn About GitHub Actions and Slack Webhooks

So, recently I have been trying to automate most of my work and it has made me become more familiar with certain technologies. More specifically, CI/CD tools. I hope to write more about them soon.

Introduction

There are lots of things to cover, I'll try to touch on as much as I can without being too verbose or drain you out.

Slack is a platform initially developed for professional and organizational communication between teams. It has since been adopted also as a community platform, replacing message boards or social media groups.

Webhooks are a simple way your online accounts can "speak" to each other and get notified automatically when something new happens. Much like SMS notifications from your bank whenever you make a transaction. Webhooks has more technical definitions but this will do.

A repository is a location for storage, often for safety or preservation.

A Version Control System ⁠— VCS — allows users to keep track of the changes in their projects, and enables them to collaborate on those projects.

Generally, in software development, there is a repository per project controlled by a Version Control System like Git, which is hosted locally or with a service (where GitHub comes in).

GitHub Actions come into play when you want to automate certain parts of your development workflow — like Continuous Integration (CI) and Continuous Deployment (CD). In our case, send a simple message to a Slack channel.

Automate, customize, and execute your software development workflows right in your repository with GitHub Actions.

An event is a possible activity (push, pull_request, cron) that a user can perform which is monitored by GitHub. A specific event of a repository can trigger a specific workflow.

A workflow is a collection of jobs that can perform configurable automated processes.

A job is made of small sub-tasks called steps. Jobs run in parallel by default and can do entirely different things in different environments. For example, running three jobs:

  • Testing one application on Windows 10 with Nodejs 10.
  • Testing another application running Nodejs 12 on macOS Mojave.
  • Sending notification updates to teams via Email, Discord, Glitch, SMS, and so on.

Each step is responsible for performing a task. In our case, two tasks (steps) of processing the repository files and sending a message on Slack.

Okay that is quite enough to get started.

Set Up Slack Webhook

Now let's set up an app on Slack to accept webhooks.

Create an app on Slack

You can use an existing app or create a new one. To create a new app on Slack:

  1. Go to api.slack.com/apps/new.
  2. Sign in and a popup shows automatically.

    • In case the popup does not show, or blurs out for some reason, Click Create New App.
  3. Choose From scratch option.

  4. Add a name and workspace.
  5. Click Create App.

Create a new Slack app

Enable Incoming Webhooks

Incoming Webhook gives you a unique URL to which you send a JSON payload with the message text and some options.

You will automatically be redirected to the app page. If not so, go to your Slack Apps Dashboard and click the preferred app. You can also change the current app at the top left of the app page.

When you are in the app page:

  1. Select Incoming Webhooks under Features and switch on Activate Incoming Webhooks.
  2. Scroll down to click on Add New Webhook to Workspace which does a bunch of stuff that can also be done programmatically.
  3. You'll see a screen like the one below, select the channel you want to send messages to.
  4. Click Allow.

Select a channel to send messages

Yay!🎉🎇 You have successfully generated your Incoming Webhook URL. Keep this a secret, do not share it online or in a Version Control System.

Test the Incoming Webhook URL

You can use an api testing tool like Insomnia or Postman, an IDE extension/plugin or a command line tool like cURL.

I'll be using curl in a terminal:

curl \
  -sSL \
  --request POST \
  --header "Content-type: application/json" \
  --data '{"text": "Going well"}' \
  your_slack_webhook_url

The response is should be ok.

  • Check the channel for a message from your Slack app.

Message successfully sent to channel

Set Up GitHub Actions

There isn’t a special process to setup GitHub Actions for a repository. The only thing we need is one or more workflow files in the repository. These workflow files (actions) are YAML files with a .yml or .yaml extension and can be named anything.

All workflow files should be placed inside the .github/workflows folder of your project and committed to version control.

Once you commit a workflow file, GitHub will be able to set up a workflow process for you. However, it won’t be visible under Actions tab until an event which causes the workflow to start is triggered.

To get started, just create a new GitHub repository or use an existing one. You can initialize the new repository with a README, .gitignore and/or license

Add Token Secret

GitHub lets you add secrets (sensitive variables) to your repository through the Settings tab:

  1. On GitHub, navigate to the main page of the repository.
  2. Under your repository name, click Settings tab.
  3. In the left sidebar, click Secrets.
  4. Click New repository secret next to "Actions secrets".
  5. Type a name for your secret in the Name input box. In our case it is SLACK_TOKEN.
  6. Enter the value for your secret. Suppose the webhook URL is "hooks.slack.com/services/token", we only paste in "token". Surrounding quotes aren't added.
  7. Click Add secret.

Add Message Payload

As we know, APIs nowadays use JSON to send payload. We are going to send a simple hello world text. Add the following to a slack_message.json file in the root directory:

{
  "text": "A simple hello world text!"
}

Slack has its own schema on how to structure the JSON payload sent to the webhook URL. You can find out more in the Slack Documentation.

Slack schema for JSON payload to webhook URL

Add Notify Script

Let's add a shell script to send a request using curl. Add the following to a slack_notify.sh file in the root directory:

curl \
  -sSL \
  -X POST \
  -H "Content-type: application/json" \
  --data @"${JSON_PATH}" \
    https://hooks.slack.com/services/${SLACK_TOKEN}

Note: You can use a programming language to do this. Just install the relevant packages in your project. You definitely should use anyone that suits your needs.

JSON_PATH and SLACK_TOKEN environment variables are populated by setting their values in the workflow file. We will take a look at the workflow file next.

We are using only the SLACK_TOKEN instead of the full Slack Incoming Webhook URL to leave less room for error.

Add Slack Workflow

  1. Create a new file in the .github/workflows folder. Any valid name you can give a file can be used here. We'll name it slack.yml.

    • I don't think you should make it a hidden file.
  2. Add the following:

name: "Notify Slack: New git push"

on: push

jobs:
  slack:
    runs-on: ubuntu-latest
    steps:
      - name: Checkout
        uses: actions/checkout@v2

      - name: Post message on Slack
        env:
          SLACK_TOKEN: ${{ secrets.SLACK_TOKEN }}
          JSON_PATH: ./slack_message.json
        run: sh ./slack_notify.sh

Okay, let's break it down.

  • name : This is used by the GitHub to display a friendly name in the Actions tab.

  • on : The name of the GitHub event that triggers the workflow. More here.

  • jobs : Specify the jobs to be run in the workflow.

  • slack : The name of the current job. It can be any name in snake_case and is used to differentiate the different jobs in the workflow.

  • runs-on : Specifies a runner or the environment where the job will run.

  • steps : The different tasks a specific job will execute.

  • uses : When a runner is loaded for a job, it doesn’t contain the repository source code. We might need to write a complex run command to pull the repository into the working directory of the runner before we do anything else. Luckily, we can use a free predefined checkout GitHub Action from the GitHub Marketplace.

  • env : Set the environment variables for the current step.

  • run : Run a command.

We can see that the Checkout job does not have a run command. Instead, it uses a predefined actions/checkout GitHub Action created by GitHub. The GitHub Action names are usually the same names as its repositories.

The name keys are just friendly names given to each unit for easier referencing.

Wrap Up

The folder structure should look like this:

.
├── .github
│   └── workflows
│       └── slack.yml
├── slack_message.json
└── slack_notify.sh

2 directories, 3 files

Now whenever we make a git push to the repository, the GitHub workflow is triggered and our actions will run. You can check the Actions tab in the repository to see logs.

GitHub + Slack

There is a lot that can be done with GitHub and Slack together, a robust GitHub app for Slack is available for more complex stuff.

Slack Code Blocks

You can also add a little extra to the slack_message.json to prettify the updates sent to slack using Slack Code Blocks.

Useful Resources

Some helpful links to improve your knowledge on topics talked about.

More on Webhooks

Workflow syntax for GitHub Actions

Events that trigger workflows

Contexts and Expressions

Cover image from: slack.github.com