Créer un bot Discord avec Python

Dans cet article nous allons voir comment développer un bot pour Discord. L'API est disponible pour Javascript ou Python, ici nous allons nous intéresser au développement avec ce dernier.

Nous allons créer le Pepper Bot, qui permettra de distribuer des piments sur Discord ! Une application très simple qui permettra de voir comment le tout fonctionne.

Avant toute chose, il faut savoir que le bot que nous allons développer est un programme qui va tourner en continu et qui va aller se connecter à tous les serveurs Discord auxquels il sera inscrit (en fait comme n'importe quel utilisateur sauf qu'il sera de type "bot").

Il est tout à fait possible de le démarrer depuis votre ordinateur (c'est comme cela que nous allons le tester), mais il serait ensuite plus pratique de le lancer depuis un serveur, qui devra accepter de lancer des scripts Python.


Création du bot sur l'espace développeur de Discord

Pour créer notre bot il faut nous rendre sur l'espace dédié sur Discord. Ce qui est bien, c'est qu'aucune autorisation particulière n'est requise pour développer avec l'API fournie par Discord, il faut juste avoir un compte actif sur Discord.

On crée une nouvelle application (bouton "New Application") que l'on nomme Pepper Bot.

Depuis la page de l'application aller sur l'onglet "Bot" et configurer le nom du bot et l'icone si vous en voulez une. Faites attention à bien désactiver l'option "Public Bot", afin que vous seul puissiez l'ajouter sur un serveur Discord.

Il faudra créer un serveur Discord (si vous n'en avez pas déjà un) sur lequel vous allez inviter votre Bot.

Pour inviter le bot dans un serveur il va falloir générer l'url d'invitation depuis l'onglet "OAuth2", cocher le scope "bot", donner la permission "View Channels" ainsi que toutes les permissions textuelles :

Il faut ensuite copier l'url générée (ici https://discord.com/api/oauth2/authorize?client_id=802135555185704970&permissions=523328&scope=bot) dans un nouvel onglet de votre navigateur, puis sélectionner le serveur sur lequel inviter le bot :

Si tout se passe bien vous verrez apparaitre le Bot sur votre serveur (pour le moment déconnecté) :

Et voilà ! Il ne nous reste plus qu'à développer le bot ;)


Développement et test du bot

Le projet fini se trouve sur le github de TechWS.

Prérequis

Une version récente de Python doit être installée (>=3.6), si jamais vous ne l'avez pas installé vous pouvez le récupérer depuis le site officiel. L'outil de gestion de dépendances pip de Python est fourni avec l'installation.

Par défaut pip installe les dépendances de manière globale sur le poste de travail, il est recommandé d'isoler les dépendances pour chaque projet dans un environnement virtuel. L'outil recommandé pour cela est pipenv.

Pour l'installer on ouvre l'invite de commande :

$ pip install pipenv --user
# ou
$ python -m pip install pipenv --user

Puis pour tester que tout fonctionne (redémarrer l'invite de commande) :

$ pipenv --version
pipenv, version 2020.11.15

La version que vous verrez peut être différente, en revanche si il y a une erreur sous Linux il se peut qu'il faille l'installer en sudo :

$ sudo pip install pipenv

Développement du bot

Ouvrir un terminal pour générer le projet et installer les dépendances :

$ mkdir pepper-bot
$ cd pepper-bot/
$ pipenv install discord.py python-environ
$ pipenv lock --requirements > requirements.txt

Cela a pour effet de :

  • Créer le répertoire du projet et de se placer dedans
  • Télécharger les 2 dépendances au projet :
    • discord.py : pour utiliser l'API de Discord
    • python-environ : pour utiliser un fichier .env et y stocker la clé du bot Discord
  • Générer un fichier requirements.txt pour un environnement de production (généralement sans pipenv)

Nous allons maintenant créer 3 fichiers : .env, bot.py et run.py

Le projet doit ressembler à ce stade à ceci (depuis Visual Studio Code) :

Nous allons commencer par éditer le fichier .env, afin d'intégrer la clé de votre bot Discord (dans l'onglet "Bot" du portail développeur Discord, sous le libellé "Token") :

BOT_TOKEN=remplacer_par_votre_token

Ensuite attaquons le fichier bot.py, qui contient le code de notre Bot :

import discord
import re

class Bot(discord.Client):
    async def on_ready(self):
        print('Logged on as', self.user)

    async def on_message(self, message):
        # don't respond to ourselves
        if message.author == self.user:
            return

        # check call for !pepper command
        args = message.content.split()

        if args[0] == '!pepper':
            # 2 scenarios :
            # - 1 more argument and argument == help
            # - x more arguments of type user id
            if len(args) == 2 and args[1] == 'help':
                await message.channel.send('Pepper Bot send peppers to people like this:\n`!pepper @member1 @member2 @member3`')
            elif len(args) >= 2:
                # check if all arguments are valid member tags
                valid_member_tags = True
                for arg in args[1:]:
                    try:
                        member_id = re.search('<@!(.+?)>', arg).group(1)
                    except:
                        valid_member_tags = False
                        break

                if not valid_member_tags:
                    await message.channel.send('<@!{0}> all arguments must be valid user tags, for help please use `!pepper help`'.format(message.author.id))
                    return

                # if all is ok, send them a pepper, cheers !
                for member_tag in args[1:]:
                    await message.channel.send('{0}, here is a pepper for you ! :hot_pepper:'.format(member_tag))
            else:
                # with no argument send a notification to author
                await message.channel.send('<@!{0}> not enough arguments, for help please use `!pepper help`'.format(message.author.id))

On y crée la classe Bot, qui hérite de discord.Client. Le principe est de surcharger des fonctions qui écoutent des événements particuliers.

Ici on_ready() se déclenchera au démarrage de notre Bot, et on_message() se déclenchera à chaque message sur tous les salons disponibles au Bot.

La syntaxe async / await permet de faire des fonctions asynchrones, si cela vous intéresse, je vous renvoie vers la documentation.

La logique importante du Bot se trouve dans on_message() :

  • le if message.author == self.user: permet de vérifier que le Bot n'est pas l'auteur du message (afin de ne pas créer de boucle infinie)
  • on sépare le message en arguments, et on vérifie si la commande de notre Bot !pepper est appelée
  • ensuite on teste le cas !pepper help, qui permettra aux utilisateurs de consulter l'aide de la commande
  • ensuite, on vérifie que l'on reçoit bien une liste de tags d'utilisateurs, et si c'est bien le cas on écrit pour chaque utilisateur en envoyant une émoticon de piment.

Il ne nous reste plus qu'à faire le fichier run.py, qui servira à démarrer le projet :

import environ
from bot import Bot

# read the .env file
env = environ.Env()
environ.Env.read_env()

# run the discord bot
def main():
    bot_token = env.str('BOT_TOKEN')

    pepper_bot = Bot()
    pepper_bot.run(bot_token)

if __name__ == "__main__":
    main()

Tester que tout fonctionne bien

Une fois que tout est prêt, il ne nous reste plus qu'à lancer un terminal depuis le répertoire du projet :

# on charge l'environnement virtuel
$ pipenv shell

# démarrage du Bot, si tout se passe bien on obtient le message de la fonction on_ready()
$ python run.py
Logged on as Pepper Bot#1675

Depuis Discord vous pourrez tester que le Bot fonctionne correctement :

Et voilà ! A partir de là il ne vous reste plus qu'à explorer la documentation sur discord.py afin de créer de super fonctionnalités pour votre Bot ;)




Blog Comments powered by Disqus.