DEV Community

Cover image for A step-by-step guide to creating a bot that publishes push events on a GitHub repository to a slack channel using nodejs
Femi Fatokun
Femi Fatokun

Posted on

A step-by-step guide to creating a bot that publishes push events on a GitHub repository to a slack channel using nodejs

Introduction

If you are familiar with Slack, I believe you should have seen some Slackbots in action, these actions are very vast and include things like calendar event reminders, standup updates, meeting overviews, and so on. Our main focus in this article is to build a nodejs application that listens to push events on our GitHub repo and publishes a message to our slack channel, hence we are building a slack bot for GitHub push events.

Prerequisites

  1. Nodejs development environment.
  2. Basic knowledge of Expressjs.
  3. A slack workspace.
  4. A GitHub repository for testing.
  5. An ngrok account.

Table of Contents

  1. Create a Slack channel in a workspace.
  2. Set up incoming webhook for the slack channel.
  3. Run code locally.
  4. Code breakdown.
  5. Set GitHub webhook.
  6. Conclusion.

Create a Slack channel in your workspace

This step is quite straightforward, login to your Slack workspace on any of your Slack clients (web, mobile, or desktop) and follow the steps to create a Slack channel.

Setup incoming webhook for slack channel

We need to generate a webhook that will be used to publish messages to our Slack channel, we will do this by following these steps.

  1. Make sure you are logged in to your Slack account on your browser.
  2. Enter https://api.slack.com/apps?new_app=1
  3. Once you open the page you will get a modal where you will choose whether to create an app from scratch or use a manifest, please click the first option. Create an app from scratch
  4. Next enter the name of your app and select your desired workspace. Enter app name and workspace
  5. You will be redirected to the app page, scroll down and click on the Incoming webhooks card. Allow incoming webhooks
  6. Then scroll down to the bottom of the page and click the Add New Webhook to Workspace button. Add new webhook to workspace
  7. Select the channel to want to publish the message to and click Allow. Allow webhook on channel
  8. After step 6 you will be redirected to the app page, if you scroll to the Webhook URLs for Your Workspace, you will find that a new webhook has been created. Confirm new slack webhook
  9. In order to test the webhook, we can copy the curl script on the script and try to execute it in our terminal, if everything works fine a message should be sent to your slack channel.

Run code locally

Our major intention for this article is to listen for push events on a GitHub repo and publish a message to our Slack channel. In order to achieve this we need to run a very simple backend API that will serve as an intermediary between github and Slack. In this section, we will run our backend API locally.

  1. Clone the git repo by simply running git clone https://github.com/talibackend/slack-bot.git in our terminal.
  2. Change the directory in your terminal by running cd slack-bot.
  3. Once inside the directory run npm install to install all the dependencies needed by our application.
  4. Run npm start, Server is running on port 8080 should be printed to the console, this signifies that our application is running.

Code breakdown

Our app is simply a nodejs app, therefore it contains all the basic files and directories of every other nodejs application. We will only focus on explaining the content of the index.js file in the base of our directory.

  1. From lines 1 to 4 we imported all the required modules for our application.
const express = require('express');
const bp = require('body-parser');
const app = express();
const fetch = require('node-fetch');
Enter fullscreen mode Exit fullscreen mode
  1. On lines 6 and 8 we used the necessary middleware to allow JSON object in the body and then declared a get route to / respectively.
app.use(bp.json());

app.get('/', (req, res)=>{ return res.send("Hello world"); });
Enter fullscreen mode Exit fullscreen mode
  1. From line 10 to 31 we declared a post route named /webhook, this is where the actual action happens.

    From lines 11 to 16 we extracted the necessary information out of the body object of the req object inside the route definition callback.

    let body = req.body;
    let branch = body.ref.replace('refs/heads/', '');
    let added = body.head_commit.added.join(', ');
    let modified = body.head_commit.modified.join(', ');
    let removed = body.head_commit.removed.join(', ');
    let commit_link = body.head_commit.url;
    

    On line 18 we use the extracted data to construct a simple string called message.

    let message = `New Push\n\nBranch : ${branch}\nAdded : ${added}\nModified : ${modified}\nRemoved : ${removed}\nLink : ${commit_link}`;
    

    From line 20 to 26 we defined an object called options, this object is required for calling the slack webhook.

    let options = {
        method : "POST",
        headers : {
            'Content-Type' : 'application/json'
        },
        body : JSON.stringify({text : message})
    }
    

    On line 28 we made a request to our slack webhook from step 1 with our own options object.

    fetch('https://hooks.slack.com/services/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', options).then().catch(err=>console.log(err))
    

    On line 30 marking the end of our request, we simply returned a string.

    return res.send("Working");
    
  2. On line 33 we simply initialized our application on port 8080.

app.listen(8080, ()=>{console.log("Server is running on port 8080")});
Enter fullscreen mode Exit fullscreen mode

Setup GitHub webhook

At this point, we've been able to set up a Slack webhook and also run our application locally. The last thing we must do is connect our application(running locally) to our GitHub repo.

This task seems impossible because at this point our application is only accessible on our computer(or local network), but we need to expose our application to the rest of the whole world, we can achieve this by using ngrok, ngrok is an open source software that uses a reverse proxy to expose locally running application to the internet. If you've not set up ngrok on your system, please head to https://ngrok.com/ and follow the required steps.

Now we will use ngrok to expose our application to the internet by following these steps.

  1. Make sure our application is running.
  2. Run ngrok http 8080, a link will be printed to the console.
  3. Copy the link and try to access it in your browser, Hello World should be printed on your screen.
  4. Navigate to your GitHub repository in your browser.
  5. Navigate to the settings tab of the repo and click on Webhooks from the sidebar.
  6. Then click Add Webhook Add GitHub webhook
  7. Fill in the necessary information, the Payload URL should be {{ngrok_generated_link}}/webhook, Content Type should be application/json then click Add Webhook. Enter webhook details
  8. At this point we are ready to test our bot, we can simply test it by pushing commits to our GitHub repo, on every push a simple message containing pieces of information about the push event will be sent to our slack channel.

Conclusion

It is very important to note that the link generated using ngrok will only be available for 2 hours if you are on their free plan, therefore what we did in this article was simply experimental, to something like this in a production environment, you will have to deploy your backend application to a server, I have a comprehensive tutorial on that - https://dev.to/talibackend/deploying-and-securing-your-nodejs-app-on-a-digitalocean-droplet-a-comprehensive-step-by-step-deployment-guide-with-ssl-1bhn.

If you prefer to watch me do this on youtube please check out the video here

Thanks for Reading.....

Top comments (0)