[Dpy]on_messageをDMでだけ動かす

この記事は約2分で読めます。

on_messageをDMでだけ動かしたいとき、単純に

@bot.event
async def on_message(message):
    if message.guild:
        return
    hoge() # DMのon_messageで動かしたい処理

とすると、@bot.commandsが動かなくなってしまう。
そのため、公式リファレンスには末尾にbot.process_commands(message)を追加しろと書いてある。

が、DMでコマンドが動くようにはなるものの、末尾に入れるだけでは全てのコマンド前にif message.guild is not None:が挿入されてしまい、全コマンドが@dm_only扱いになってしまう。

単純な解決法

@bot.event
async def on_message(message):
    if message.guild:
        return await bot.process_commands(message)
    hoge() # DMのon_messageで動かしたい処理
    await bot.process_commands(message)

のように、returnの戻り値としてもprocess_commands()をつけてやれば、この問題は解消される。他の条件分岐を付ける場合も、戻り値にprocess_commands()を入れるのを忘れないようにしよう。

Listenerを使おう

ただ、そもそもそんな面倒を解決する、@listenerというものが用意されている。基本的にはこちらを使おう。使い方は簡単で、任意の関数の前に@bot.listen(name=”on_message”)デコレータをつけるだけ。nameには任意のイベント名を入れる。
※慣例に従いbot = commands.Bot()で定義している前提とする。

@bot.listen(name="on_message")
async def DM_only(message):
    if message.guild:
        retrn
    hoge()
このようにすれば、任意の関数がon_messageとして動き、かつ複数の関数に処理を分散してわかりやすくでき、また互いに干渉せず、process_commands()も必要ない。

コメント

タイトルとURLをコピーしました