Slack Bot Python – #3 Handling Events

As you learned about creating a basic slack bot python and added slash commands features to it in our previous tutorials, today you’ll learn to add event handling features to the same bot.

Getting Started with Slack Bot Python – Handling Events

This is the third part of our Slack Bot Python tutorial series and if you’re a newbie creating a slack bot, it is highly recommended to go through the first and second parts of this tutorial. If you’re not familiar with slack, you can check Slack’s Official website to know about it. In this tutorial today, you’ll learn to add event handling features to our slack bot which we created in the previous tutorials. This time you’ll not create a different code but you’ll edit the same Repl which you created while creating slash commands.

What is Event Handling?

There are different events occurring in your workspace like sending a message, reacting or unreacting to a message, joining of a new member, pinning or unpinning a message and more. You can make your Slack bot python to handle responses for such events. For example: if you want to send a welcome message on joining of a new member in your workspace, you can do it simply using event handling methods, or if you want to send direct messages to a user who pins or unpins a message, you can make your bot do that for you using event handling.

They are completely different from slash commands and that is why event handling is a very important part of Slack bot python and must be learned if you’re creating a slack bot python.

Algorithm

In order to create event handlers for your Slack bot Python, you’ll have to follow the following algorithm:

  1. Create a Flask Server for the request URL.
  2. Create a Flask server route for slack events.
  3. Get the signing secret of your API.
  4. Add the request URL to Bot settings, provide necessary permissions and re-install the app to the workspace.
  5. Import Slack’s Event Handler library for python.
  6. Start creating responses for various events in your slack workspace for your Slack Bot Python.
  7. Run the flask server.

Get the Signing Secret of your Bot

1. In order to add the URL to our API settings for our slack bot, we’ll need to go to slack’s API site and click on the Your Apps button on the top right corner of the page and select the bot by its name (here Webmatrices Bot).

Selecting the Bot
Selecting the Bot

2. Scroll the page down and you’ll see your Signing Secret under App Credentials section. Copy the secret and add it as an environment variable in your Repl with signing_token as the variable name and the copied signing secret value as the variable value and import it to your code as you did last time.

Signing Secret
Signing Secret

Add Request URL and permissions to your Bot API

Creating Request URL

As you did in the previous tutorial, again you need to create a Flask server in a similar way and add the request URL to the API settings of your bot. You can also use different tools like ngrok to create a server for yourself. But here we’ll be using the same Repl to create a request URL and add a route for event handles to the same URL.

In the previous tutorial, we generated an URL (https://Slack-Bot-Creating-Slash-Commands.ahens.repl.co/greet) and added a route (/greet) to create a page for the greet slash command, we’ll use the same URL here again but we’ll create a new page (here /slack/events) for slack events. So now, we have the request URL as (https://Slack-Bot-Creating-Slash-Commands.ahens.repl.co/slack/events) and we can add this request URL to our API settings.

Create Flask Route for Events page

Now as you’ve named the page for slack events as /slack/events, you need to create a route for the same page in your flask server. To do this, you’ll need to import slackeventsapi library of python to your code and edit the keep_alive.py file you created while creating slash commands and add the following code to the file.

from slackeventsapi import SlackEventAdapter

The slackeventsapi has an inbuilt function called SlackEventAdapter that handles workspace events taking three parameters: first is the signing secret of your bot, second is the page for handling slack events and third is the main flask server or app.

#Note that this piece of code should be added just after the assigning of app variable
slack_event_adapter=SlackEventAdapter(os.environ['signing_token'], '/slack/events', app)
Re-run the Repl before you add the request URL to your App Settings.

Adding Request URL to Bot API Settings

1. In order to add the URL to our API settings for our slack bot, we’ll need to go to slack’s API site and click on the Your Apps button on the top right corner of the page and select the bot by its name (here Webmatrices Bot).

Selecting the bot
Selecting the bot

2. Now, click on Event Subscriptions on the left sidebar of the page and then click on the Off button to enable events for your bot.

Enable Events
Enable Events

3. Now add the request URL you just created to the Request URL section.

Adding Request URL
Adding Request URL

4. Now you’ve added the request URL and you now have to select the event you need to respond to (here: reaction_added) by scrolling the page down and clicking on Add Bot User Event under Subscribe to Bot Events Section and Save Changes.

Add Bot events
Add Bot events

5. Now you’ve saved the changes, so you need to re-install the app to your workspace as usual.

Diving into the Code

As you’ve created the request URL and added it to the API settings now you can start creating functions to be executed in response to the events you added in the API settings (here: reaction_added).

For handling a react or unreact on a message in a channel on your workspace, you can simply use slackeventsapi‘s SlackEventHandler class. For this you can use @slack_event_adapter.on('reaction_add') and attach the function you want to execute with it as follows:

@slack_event_adapter.on('reaction_added')
def reaction(payload):
  event = payload.get('event', {})
  channel_id = event.get('item', {}).get('channel')
  user_id = event.get('user')
  client.chat_postMessage(channel=channel_id, text=f"<@{user_id}>, you just reacted to a message.")
Here in this code, @slack_event_adapter.on('reaction_added') creates a event handler response for reaction_added event and you can replace it with the event you want to handle according to your choice. Then you define a function to be executed def reaction(payload): taking a payload argument. Now, you create an event variable to get the reaction_added event from the payload and then you extract the channel id and user id from the event variable and store it as channel_id and user_id. Now you post the message as you did in the first tutorial taking channel_id as first parameter and text/message as the second parameter and tag the user with his/her user_id. 

Complete Code

from keep_alive import keep_alive
keep_alive()
from flask import Flask, request, Response
from threading import Thread
import slack_sdk as slack
import os
from pathlib import Path
from dotenv import load_dotenv
from slackeventsapi import SlackEventAdapter

#Set the path of .env file using pathlib
token_path=Path('.') / '.env'
#loading env with load_dotenv function of python-dotenv module
load_dotenv(dotenv_path=token_path)
#saving bot api token as variable
bot_api_token=os.environ['bot_token']

client=slack.WebClient(token=bot_api_token)

app = Flask('')
#Note that this piece of code should be added just after the assigning of app variable
slack_event_adapter=SlackEventAdapter(os.environ['signing_token'], '/slack/events', app)

@app.route('/')
def home():
    return "The bot is alive!!"

@app.route('/greet', methods=['POST'])
def greet_command():
  data = request.form
  channel_id = data.get('channel_id')
  client.chat_postMessage(channel=channel_id, text="Howdy, How are you doing?")
  return Response(), 200

@slack_event_adapter.on('reaction_added')
def reaction(payload):
  event = payload.get('event', {})
  channel_id = event.get('item', {}).get('channel')
  user_id = event.get('user')
  client.chat_postMessage(channel=channel_id, text=f"<@{user_id}>, you just reacted to a message.")

def run():
  app.run(host='0.0.0.0',port=8080)

def keep_alive():
    t = Thread(target=run)
    t.start()

You can also find the complete code on my Repl or GitHub workspace.

Output:

Slack Bot Python - Handling Events Output
Slack Bot Python – Handling Events Output

Conclusion

So, now you’ve learned to handle events for your slack bot python. Now you can use this script to create your own event handles. You can create such bots and host them on different servers to keep them alive 24×7 and you can sell them to companies to earn from your bot.

Posted by Awebisam

I am Awebisam, a tech and economics enthusiast with native roots in Python and JS. Apart from those, TS and Golang are also my type of things.
I work with Django, FastAPI, Vue and Nestjs. Also slightly familiar with Flask, Express, and Svelte.

~ Awebisam, Aashish Bhandari

One thought on “Slack Bot Python – #3 Handling Events”

Leave a Reply

Your email address will not be published. Required fields are marked *