Skip to main content

How to build a Slack Bot

Creating your own Slack integration is fairly easy.

To deploy a Slash Command - bot which interacts with user after issuing /command on your chat - you need two thing:

  1. Slack with permission to add integrations

  2. Some place to deploy bot code

Integration is very simple. Additionally if you don't need sophisticated functionality or high level of security for you solution, you can create working bot withing few minutes.

You can check siara bot code. It's simple version of more sophisticated SiaraBot.

App code

Slack bot is basically simple app which is able to receive HTTP POST and quickly answer them:

require('dotenv').config();
const express = require('express');
const bodyParser = require('body-parser');
const request = require('request');

const app = express();
const PORT = 3000;

app.listen(process.env.PORT || PORT, function() {
    console.log('Bot is listening on port ' + PORT);
});
app.use(bodyParser.urlencoded({
    extended: true
}));
app.use(bodyParser.json());
app.post('/', (req, res) => {
    var data = {
        response_type: 'in_channel', // public to the channel

        text: 'Something'
    };
    res.json(data);
});

Heroku

I've decided to upload bot code to Heroku. The process is straightforward - just create you app at Heroku Dashboard, download Heroku CLI and push your code:

$ heroku login
$ heroku git:remote -a my-bot-name
$ git push heroku master

It will be uploaded, built and executed. Next, let's configure Slack.

Slack

Go to Slack API page Your Apps. Create your app, set it's name, short description. Next, add new Slash Command, for example: /whatever. You have to specify Request URL on which Slack will post when someone will use this command. It should point to your app URL created earlier, eg. https://whatever-bot.herokuapp.com/

Finally add your app to your workspace. Now you can use /whatever

Delayed response

When using free Heroku dyno app is goint to sleep after 30 min of inactivity. After this time, when request is sent, it is cached and dyno instace is started again. Unfortunately it takes some time and Slack have only 3000ms window for response. To minimize timeout errors we can use delayed response Slack API. Basically we have to take response_url from request and send our answer on this URL. In such case we will get only one timeout error when bot is not used for a long time.

app.post('/', (req, res) => {
  res.status(200).end();

  request.post(req.body.response_url, {
      json: {
        response_type: 'in_channel', // public to the channel
        text: 'Something.'
      }
  }, (error, res, body) => {
    if (error) {
        console.error(error);
        return;
    }
  });
});

Have fun with your bot!